There are some issues that simply lose interest due to not being pertinent enough, I believe I have found one.
I mentioned this issue is the MSDN forums back in August of 2012, and it persists today (June 2014). http://social.msdn.microsoft.com/Forums/windowsazure/en-US/9e60ef77-2574-4c32-ae41-5ef208520356/addpssnapin-microsoftwindowsazureserviceruntime-fails-in-workerrole-2008-r2?forum=windowsazuretroubleshooting
And I can see from searching that I am not alone here.
The thing that is going on is that I am using startup tasks in a Worker Role to install an MSI and configure it.
When the script being executed by my startup task attempts to: add-pssnapin
microsoft.windowsazure.serviceruntime
I receive the error:
add-pssnapin :
Cannot load Windows PowerShell snap-in microsoft.windowsazure.serviceruntime
because of the following error: The Windows PowerShell snap-in module
F:\plugins\RemoteAccess\Microsoft.WindowsAzure.ServiceRuntime.Commands.dll
does not have the required Windows PowerShell snap-in strong name
Microsoft.WindowsAzure.ServiceRuntime.Commands, Version=1.0.0.0,
Culture=neutral,
My impression of this workaround is this: "So, now I have to script a work around for an MSFT provided DLL because no one is updating the DLL registration for the snap-in in MSFT provided Gallery Images in Azure."
A workaround is great, but there are caveats to all of the workarounds posted thus far;
- if I update the registry key with the incorrect version number, it still won’t load.
- I have to get the right version number and fix the registry entry.
- And edit both the Assembly Name string and the version string.
Each posted workaround that I can find through search is a point version, and a point version edit. A lasting workaround (since it seems like this bug is not going to get fixed anytime soon) is to dynamically deal with any version of the DLL and strong name enforcement in the OS.
I always preface that my solution might not be the most elegant thing that a developer comes up with, but I hope that folks can follow it and understand what I did.
# Get the current execution path
$exPath = Split-Path -parent $MyInvocation.MyCommand.Definition
$exPath # Echo for logging
######################################################################################
### Before we can load the service runtime, we must fix the broken registry information for the DLL
### and the version must be right, or it will continue to be broken.
$runtimeDllReg = Get-Item HKLM:\SOFTWARE\Microsoft\PowerShell\1\PowerShellSnapIns\Microsoft.WindowsAzure.ServiceRuntime
$runtimeDll = Get-Item $runtimeDllReg.GetValue('ModuleName')
$exportPath = $expath + "\AzureServiceRuntime.reg"
& $env:SystemRoot\System32\regedt32.exe /E $exportPath 'HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\PowerShell\1\PowerShellSnapIns\Microsoft.WindowsAzure.ServiceRuntime'
$exPath = Split-Path -parent $MyInvocation.MyCommand.Definition
$exPath # Echo for logging
######################################################################################
### Before we can load the service runtime, we must fix the broken registry information for the DLL
### and the version must be right, or it will continue to be broken.
$runtimeDllReg = Get-Item HKLM:\SOFTWARE\Microsoft\PowerShell\1\PowerShellSnapIns\Microsoft.WindowsAzure.ServiceRuntime
$runtimeDll = Get-Item $runtimeDllReg.GetValue('ModuleName')
$exportPath = $expath + "\AzureServiceRuntime.reg"
& $env:SystemRoot\System32\regedt32.exe /E $exportPath 'HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\PowerShell\1\PowerShellSnapIns\Microsoft.WindowsAzure.ServiceRuntime'
# This is because the wait does not wait until regedit actually completes.
Do {
Start-Sleep 10
$regFile = Get-Item -Path $exportPath -ErrorAction SilentlyContinue
} Until ($regFile.Exists)
$runtimeRegFile Get-Content -Path $exportPath
$newRuntimeRegFile = @()
foreach ($e in $runtimeRegFile) {
switch -wildcard ($e) {
"*1.0.0.0*" { $e = $e -replace "1.0.0.0", ($runtimeDll.VersionInfo.FileMajorPart.ToString() + '.' + $runtimeDll.VersionInfo.FileMinorPart.ToString() + '.0.0') }
}
$newRuntimeRegFile += $e
}
Set-Content -Value $newRuntimeRegFile -Path $exportPath -Force
Start-Sleep 2
& $env:SystemRoot\System32\regedt32.exe /S $exportPath
Start-Sleep 2
# Load the necessary PowerShell modules for configuration and management Web and Work Roles
add-pssnapin microsoft.windowsazure.serviceruntime
# Take the VM Instance offline with Azure, or else Azure will keep attempting to start the script
Set-RoleInstanceStatus -Busy
You might wonder why I am using regedit.exe instead of the PowerShell cmdlets to set the value. What I found is that I kept running into permissions issues. And using regedit to export and import is a way around that.