I'd prefer using the AllSigned execution policy with PowerShell, but self-signing my scripts seems to require several hundreds of megabytes of downloading and installation and the signing process seems to be a hassle.

Is there a simpler way to sign a PowerShell script than described in the documentation?


To do the signing you can use the Set-AuthenticodeSignature cmdlet. This, of course, requires a certificate. If you have a Certificate Authority (unlikely) that will be able to create a code signing certificate. Otherwise there are various tools to create a self-signed certificate.

You install the certificate in your certificate store (open the .cer or .pfx file in Windows Explorer to do this), and then pass it to Set-AuthenticodeSignature (the cert: provider/drive gives access to certificates in your store).


help about_signing

or the online version of that help topic for details (including creating a self-signed certificate using the Windows SDK tools[1]).

[1] I assume this is the big download you're referring to: you can just install the bits you need, or make use of other tools (OpenSSL includes certificate generation). Getting the SDK is, for this purpose, a one-off activity.

  • I'm accepting this answer and assuming that there is no shortcut and signing just needs to be done as mentioned in the docs. – Ville Koskinen Jan 19 '10 at 12:30
  • 1
    Like quite a few "developer-y" things the initial set up and learning is hard, but the actual practice (especially if done regularly) isn't. – Richard Jan 20 '10 at 10:31

I use this PowerShell script:

## sign-script.ps1
## Sign a powershell script with a Thawte certificate and 
## timestamp the signature
## usage: ./sign-script.ps1 c:\foo.ps1 

param([string] $file=$(throw “Please specify a script filepath.”)) 

$certFriendlyName = "Thawte Code Signing"
$cert = gci cert:\CurrentUser\My -codesigning | where -Filter 
  {$_.FriendlyName -eq $certFriendlyName}

# https://www.thawte.com/ssl-digital-certificates/technical-  
#   support/code/msauth.html#timestampau
# We thank VeriSign for allowing public use of their timestamping server.
# Add the following to the signcode command line: 
# -t http://timestamp.verisign.com/scripts/timstamp.dll 
$timeStampURL = "http://timestamp.verisign.com/scripts/timstamp.dll"

if($cert) {
    Set-AuthenticodeSignature -filepath $file -cert $cert -IncludeChain All -   
      TimeStampServer $timeStampURL
else {
    throw "Did not find certificate with friendly name of `"$certFriendlyName`""

Once I had the certificate, I wanted to use imported on my user account. This regkey gave me an option, Sign, in the context menu (I'm using Windows 7). If the certificate you want to sign with is stored differently, just change the PowerShell command at the end.

Windows Registry Editor Version 5.00




@="C:\\\Windows\\\System32\\\WindowsPowerShell\\\v1.0\\\powershell.exe -command Set-AuthenticodeSignature '%1' @(Get-ChildItem cert:\\\CurrentUser\\\My -codesigning)[0]"

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.