VMware Cloud Community
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

invoke-vmscript issues

I have a hash containing drive data, the key is the disc number and the values are (in order size, drive letter, and datastore)

$datahash

Name                       Value
----                       -----
2                          {3, q, datastore1}
1                          {4, f, datastore2}
0                          {40, c, datastore3}

I'm trying to partition the drives through powercli, but I'm not sure $datahash is actually being pushed to the remote server

$script = @'

            $NumDisks = (Get-Wmiobject -class "Win32_DiskDrive").count

            for($CurrentDisk = 1; $NumDisks -gt $CurrentDisk; $CurrentDisk++)

            {

                out-file c:\diskpartscript$currentdisk.txt -Encoding ASCII -InputObject "select disk $CurrentDisk`r`n online disk noerr`r`n attributes disk clear readonly`r`n clean`r`n create partition primary`r`n format fs=ntfs quick`r`n assign letter=$datahash[$currentdisk][1]"

                diskpart /s c:\diskpartscript$currentdisk.txt

            }

            '@   

        Invoke-VMScript -ScriptText $script -VM $displayname -GuestCredential $localadmincreds -scripttype powershell

When i check c:\diskpartscript$currentdisk.txt at the drive letter section i just see the following:

select disk 1

online disk noerr

attributes disk clear readonly

clean

create partition primary

format fs=ntfs quick

assign letter=[1][1]

Where assign letter should have in this case 'f'

Is $datahash not being pushed to the script block or something?

0 Kudos
1 Solution

Accepted Solutions
LucD
Leadership
Leadership
Jump to solution

There are but a few simple rules for variable substitution in here-strings.

As an example

$u = 2

$t1 = @"

Value $u

"@

$t2 = @'

Value $u

'@

$t3 = @"

Value `$u

"@

$t1

$t2

$t3

  • In $t1, a here-string with double quotes, the variable gets substituted
  • In $t2, a here-string with single quotes, no variable substitution will take place
  • In $t3, a here-string with double quotes, we avoid the substitution of $u by escaping (back-tick) the $-sign


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

View solution in original post

0 Kudos
9 Replies
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

Forgot to add I'm calling it with:

Invoke-VMScript -ScriptText $script -VM $displayname -GuestCredential $localadmincreds -scripttype powershell

0 Kudos
LucD
Leadership
Leadership
Jump to solution

It's to do with operator priority.

Try as

($datahash[$currentdisk])[1]


What is in the parenthesis will return the array, then you take the 2nd (index 1) element of that array


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

It seems like it isnt passing $datahash at all...the output of diskpartscript1.txt has the 'assign letter' field as:

assign letter = ([1])[1]

Am I doing something incorrect with my quotes?

$script = @'

            $NumDisks = (Get-Wmiobject -class Win32_DiskDrive).count

            for($CurrentDisk = 1; $NumDisks -gt $CurrentDisk; $CurrentDisk++)

            {

                out-file c:\diskpartscript$currentdisk.txt -Encoding ASCII -InputObject "select disk $CurrentDisk`r`n online disk noerr`r`n attributes disk clear readonly`r`n clean`r`n create partition primary`r`n format fs=ntfs quick`r`n assign letter=($datahash[$currentdisk])[1]"

                diskpart /s c:\diskpartscript$currentdisk.txt

            }

            '@

0 Kudos
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

               $hi = "hi"

                $script = @'

                        add-content c:\out.txt $hi

                        '@

Invoke-VMScript -ScriptText $script -VM $displayname -GuestCredential $localadmincreds -scripttype powershell

This also results in a blank out.txt file....the OS is windows 2012 R2, would that have anything to do with vmscript not being able to pass the $datahash hash?

0 Kudos
LucD
Leadership
Leadership
Jump to solution

That is due to the inline string with single quotes (@'...'@).

With single quotes there will be no variable substitution.

Use double quotes


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

Using this code:

   $script = @"
        $NumDisks = (Get-Wmiobject -class Win32_DiskDrive).count
        for($CurrentDisk = 1; $NumDisks -gt $CurrentDisk; $CurrentDisk++)
        {
            out-file c:\diskpartscript.txt -Encoding ASCII -InputObject "select disk $CurrentDisk`r`n online disk noerr`r`n attributes disk clear readonly`r`n clean`r`n create partition primary`r`n format fs=ntfs quick`r`n assign letter=($datahash[$currentdisk])[1]"
            diskpart /s c:\diskpartscript.txt
        }
   "@

Produced the following error:

PowerCLI C:\> Invoke-VMScript -ScriptText $script -vm $displayname -GuestCredential $localadmincreds -ScriptType Powershell

ScriptOutput

-------------------------------------------------------------------------------

At line:2 char:32

|  +             for( = 1;  -gt ; ++)

|  +                                ~

|  Missing expression after unary operator '++'.

|      + CategoryInfo          : ParserError: (:) [],

ParentContainsErrorRecordEx

|     ception

|      + FullyQualifiedErrorId : MissingExpressionAfterOperator

|

|

-------------------------------------------------------------------------------

0 Kudos
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

           The below code works, I had to hardcode the variable names in, if you have a better method please let me know!

            $i = 1

          

            do

            {

                $drive = $datahash.Keys | ? {$_ -eq $i} | %{$datahash[$_][1]}

                $script = @"

              

                    out-file c:\diskpartscript.txt -Encoding ASCII -InputObject "select disk $i`r`n online disk noerr`r`n attributes disk clear readonly`r`n clean`r`n create partition primary`r`n format fs=ntfs quick`r`n assign letter=$drive"

                    diskpart /s c:\diskpartscript.txt

                "@

                Invoke-VMScript -ScriptText $script -VM $displayname -GuestCredential $localadmincreds -scripttype powershell

                $i++

            }

            until($i -eq $datahash.count)

After some further editing, i got it down to:

foreach ( $name in $datahash.keys )

{

$script += '"select disk ' + $name + '`r`nonline disk noerr`r`nattributes disk clear readonly`r`nclean`r`ncreate partition primary`r`nformat fs=ntfs quick`r`nassign letter=' + $datahash[$name][1] + '"|diskpart;'

}

Invoke-VMScript -ScriptText $script -VM $displayname -GuestCredential $localadmincreds -scripttype powershell | out-null

0 Kudos
LucD
Leadership
Leadership
Jump to solution

There are but a few simple rules for variable substitution in here-strings.

As an example

$u = 2

$t1 = @"

Value $u

"@

$t2 = @'

Value $u

'@

$t3 = @"

Value `$u

"@

$t1

$t2

$t3

  • In $t1, a here-string with double quotes, the variable gets substituted
  • In $t2, a here-string with single quotes, no variable substitution will take place
  • In $t3, a here-string with double quotes, we avoid the substitution of $u by escaping (back-tick) the $-sign


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
aaronmiller85
Enthusiast
Enthusiast
Jump to solution

Very helpful post for the future, thanks!

0 Kudos