1
votes

Im trying to pass a credential to another powershell script but i get an error as

"Cannot convert the "System.Management.Automation.PSCredential" value of type "System.String" to type "System.Management.Automation.PSCredential""

This is the script which invoke the psscript

param(
$vcenterserver,
[System.Management.Automation.Credential()]$vccredential
)


#New-Item C:\dcpromotxt\1.ps1 -ItemType file -Force


#Start-Process powershell.exe -ArgumentList "-NoExit -File '& 'C:\dcpromotxt\1.ps1''" -vcenterserver $vcenterserver -vccredential $vccredential


Start-Process powershell -ArgumentList "-NoExit -File '& 'C:\dcpromotxt\1.ps1''","$vcenterserver","$vccredential"

and here is the 1.ps1

param(
$vcenterserver,
$vccredential
)

Connect-VIServer $vcenterserver -Credential $vccredential


start-sleep 120
3
Why do you want to start another copy of PowerShell instead of invoking .ps1 file in current session?user4003407
@PetSerAl, that is the requirementPowerShell
Sharing credentials is a risky path. Can you explain more on how it's going to be used, ex. in the same context or on different machines by different users?AlexPawlak

3 Answers

2
votes

You can try this method then, save the cred to disk with different key, then modify the ps1 file to load the cred from disk, like this:

First: Save the Cred to disk

$credential = Get-Credential
$Key = [byte]1..16
$credential.Password | ConvertFrom-SecureString -Key $Key | Set-Content c:\cred.key

then edit the ps1 file like this for example:

param(
$vcenterserver
)

Add-PSSnapin VMware.VimAutomation.Core
$Key = [byte]1..16
$username = "type the username"
$encrypted = Get-Content c:\cred.key | ConvertTo-SecureString -Key $Key
$credential = New-Object System.Management.Automation.PsCredential($username, $encrypted)

Connect-VIServer $vcenterserver -Credential $credential

then run it:

Start-Process powershell -ArgumentList "-noExit -File c:\vcenter.ps1 -vcenterserver vcenter"
2
votes

You cannot pass a Powershell object via comand line, these will be converted to strings and become unusable. Worse, "$vccredential" returns the type name due to toString() implementation. You can pass a PSCredential object to your script if you invoke it in your current session, like this:

& 'C:\dcpromotxt\1.ps1' $vcenterserver $vccredential

This way your parameters won't be converted and will retain internal structure.

If, however, you require a separate Powershell process to work with the new script, you can convert a PSCredential into two strings, namely $cred.username and (ConvertFrom-SecureString $cred.password), which you can reassemble on the destination side via $cred=new-object PSCredential($username,(convertto-securestring $password)). The restriction with this process is that your other Powershell process should run under the same user account and on the same computer. But you can optionally supply the conversion cmdlets with -key parameter that contains 128, 192 or 256 bits (384 probably on Win8+) which will be used in AES encryption algorithm, this will allow you to run that Powershell process as another user or on another PC and use shared key to encrypt/decrypt sensitive data. As a matter of extra precaution, you can use this module to add additional "salt" (named "entropy" in that article) to your encryption, so that even intercepting the secure string and the key won't make an attacker to decrypt your data without known entropy.

0
votes

You can't pass a credential object in an argument string. Call your second script like this:

& 'C:\dcpromotxt\1.ps1' $vcenterserver $vccredential

A requirement to run the second script via Start-Process doesn't make sense.