Photo by Branko Stancevic on Unsplash
So there I was, trying to run a perfectly harmless deployment script at some ungodly hour, and PowerShell just throws this at me:
cannot be loaded because running scripts is disabled on this system
Classic. If you've ever stared at that error message, you know the specific kind of frustration it brings — because the fix sounds simple, but if you just Google "how to fix PowerShell execution policy" and blindly paste whatever command shows up first, you can actually create a real security problem on a production machine. I've seen this done wrong more times than I care to admit.
Let's actually understand what's going on here and fix it the right way.
What the Execution Policy Is Actually Doing
The PowerShell execution policy isn't really a security feature — Microsoft themselves say as much in the docs. It's more of a safety guardrail to stop you (or some random downloaded script) from accidentally running something destructive. It's not going to stop a determined attacker, but it'll stop a tired sysadmin from fat-fingering something catastrophic at 1am. Been there.
There are a handful of policy levels you'll encounter. The main ones you'll actually deal with:
Restricted — Default on Windows clients. No scripts run. Period. Not even your own.
RemoteSigned — This is the sweet spot for most people. Scripts you write locally run fine. Scripts downloaded from the internet need to be digitally signed. Honestly, this is what most workstations should be running.
AllSigned — Every single script must be signed, even ones you wrote yourself. More secure, but also more annoying for day-to-day work.
Unrestricted — Everything runs. You'll get a warning for downloaded scripts, but it won't block them. Don't set this on anything you care about.
Bypass — Nothing is blocked, nothing is warned. This one is useful in very specific automation scenarios, but if someone tells you to just set your machine to Bypass as a general fix, walk away.
Checking What You're Currently Set To
Before you change anything, check your current situation. Open PowerShell and run:
Get-ExecutionPolicy -List
This is the command most tutorials skip, and it's actually the most important one. You'll see the policy for different scopes — MachinePolicy, UserPolicy, Process, CurrentUser, and LocalMachine. Here's the thing though — PowerShell evaluates these in order, and the most restrictive one wins. So even if you set LocalMachine to RemoteSigned, a Group Policy pushing MachinePolicy to Restricted will override you every single time. I've had junior admins spend an hour troubleshooting this exact scenario.
Actually Changing the Policy
For most situations — like running your own scripts on a work machine — you want to change it at the CurrentUser scope. This way you're not touching the machine-wide setting, which is less risky and doesn't require you to think too hard about other users on the box:
Set-ExecutionPolicy -ExecutionPolicy RemoteSigned -Scope CurrentUser
If you're setting up a server or a shared machine and you have admin rights, you might want LocalMachine scope instead:
Set-ExecutionPolicy -ExecutionPolicy RemoteSigned -Scope LocalMachine
Run that from an elevated PowerShell window (right-click, Run as Administrator) or it'll just complain at you.
The Insider Trick: Run a One-Off Without Changing Anything
Here's something a lot of people don't know — if you just need to run one specific script and you don't want to mess with the execution policy at all, you can bypass it for just that session or just that script invocation:
powershell.exe -ExecutionPolicy Bypass -File "C:\Scripts\myscript.ps1"
This doesn't change your system settings. It just runs that one script with the policy temporarily lifted for that process. Really handy for scheduled tasks where you want to keep your system policy locked down but still need a specific script to fire.
Another one I use constantly — if you're already inside a PowerShell session and you just want to temporarily change the policy for that session only:
Set-ExecutionPolicy -ExecutionPolicy RemoteSigned -Scope Process
Close the window, it's gone. Nothing permanent written anywhere. This is great for testing scripts on a locked-down machine without leaving footprints.
The "Unblock" Thing Nobody Tells You About
Alright so here's one that's bitten me more than once. You've set your execution policy to RemoteSigned, your script lives on your local machine, and PowerShell is still blocking it. What gives?
Windows tags files downloaded from the internet with a hidden NTFS stream called the "Zone Identifier" — basically a mark that says "this came from the internet, be suspicious." Even if you downloaded a script and saved it locally, it might still carry that tag. You can strip it with:
Unblock-File -Path "C:\Scripts\myscript.ps1"
Or right-click the file in Explorer, go to Properties, and check the "Unblock" checkbox at the bottom of the General tab. Same thing, different method. I've wasted embarrassing amounts of time troubleshooting execution policy issues that were actually Zone Identifier issues in disguise.
Group Policy Is Probably the Culprit on Corporate Machines
If you're on a domain-joined machine and none of the above is working, don't keep banging your head against it. When Get-ExecutionPolicy -List shows something set at MachinePolicy or UserPolicy scope, that's Group Policy and you can't override it from PowerShell — full stop. You'd need to talk to your domain admin or change the GPO itself.
The GPO setting lives at: Computer Configuration > Administrative Templates > Windows Components > Windows PowerShell > Turn on Script Execution
Worth knowing even if you can't change it yourself — at least you know where to point your admin.
One last thing: when you're done with whatever you were doing and security matters on that machine, you can always reset to default with Set-ExecutionPolicy -ExecutionPolicy Restricted -Scope CurrentUser. Good habit to get into, especially on shared boxes.
Hope this saves you the hour of confusion I went through the first time I ran into this.
Related: PowerShell Tips and Tricks: Commands Every Developer Should Know
๋๊ธ
๋๊ธ ์ฐ๊ธฐ