Skip to content

Commit 3212272

Browse files
committed
vVol Core update
vVol Core update
1 parent c9b9b05 commit 3212272

3 files changed

Lines changed: 123 additions & 64 deletions

File tree

PureStorage.FlashArray.VMware.Configuration/PureStorage.FlashArray.VMware.Configuration.psm1

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1544,7 +1544,7 @@ function New-PfaRestOperation {
15441544
}
15451545
}
15461546
$apiendpoint = "https://$($url)/api/$($pfaRestVersion)/" + $resourceType + $queryFilter
1547-
Write-Debug $apiendpoint
1547+
Write-debug $apiendpoint
15481548
if ($PSVersionTable.PSEdition -eq "Core")
15491549
{
15501550
if ($jsonBody -ne "")

PureStorage.FlashArray.VMware.VVol/PureStorage.FlashArray.VMware.VVol.psd1

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
Created by: Cody Hosterman
55
Organization: Pure Storage, Inc.
66
Filename: PureStorage.FlashArray.VMware.vVol.psd1
7-
Version: 1.4.0.2
7+
Version: 2.0.0.0
88
Copyright: 2020 Pure Storage, Inc.
99
-------------------------------------------------------------------------
1010
Module Name: PureStorageFlashArrayVMwarevVolPowerShell
@@ -29,7 +29,7 @@
2929
RootModule = 'PureStorage.FlashArray.VMware.vVol.psm1'
3030

3131
# Version number of this module; major.minor[.build[.revision]]
32-
ModuleVersion = '1.4.0.2'
32+
ModuleVersion = '2.0.0.0'
3333

3434
# ID used to uniquely identify this module
3535
GUID = '105e97db-98b4-41be-be35-17ba25a1ede5'
@@ -47,7 +47,7 @@
4747
Description = 'Pure Storage FlashArray VMware PowerShell vVol management.'
4848

4949
# Minimum version of the Windows PowerShell engine required by this module
50-
PowerShellVersion = '5.0'
50+
PowerShellVersion = '5.1'
5151

5252
# Name of the Windows PowerShell host required by this module
5353
PowerShellHostName = ''
@@ -82,7 +82,7 @@
8282
NestedModules = @()
8383

8484
# Functions to export from this module
85-
FunctionsToExport = 'Update-PfaVvolVmVolumeGroup','Get-VvolUuidFromVmdk','Get-PfaVolumeNameFromVvolUuid','Get-PfaSnapshotFromVvolVmdk','Copy-PfaVvolVmdkToNewVvolVmdk','Copy-PfaSnapshotToExistingVvolVmdk','Copy-PfaSnapshotToNewVvolVmdk','Copy-PfaVvolVmdkToExistingVvolVmdk','New-PfaSnapshotOfVvolVmdk','Get-VmdkFromWindowsDisk','New-PfaVasaProvider','Get-PfaVasaProvider','Remove-PfaVasaProvider','Mount-PfaVvolDatastore','Initialize-PfaVVols'
85+
FunctionsToExport = 'Get-PfaVvolVol','Update-PfaVvolVmVolumeGroup','Get-VvolUuidFromVmdk','Get-PfaVolumeNameFromVvolUuid','Get-PfaSnapshotFromVvolVmdk','Copy-PfaVvolVmdkToNewVvolVmdk','Copy-PfaSnapshotToExistingVvolVmdk','Copy-PfaSnapshotToNewVvolVmdk','Copy-PfaVvolVmdkToExistingVvolVmdk','New-PfaSnapshotOfVvolVmdk','Get-VmdkFromWindowsDisk','New-PfaVasaProvider','Get-PfaVasaProvider','Remove-PfaVasaProvider','Mount-PfaVvolDatastore','Initialize-PfaVVols'
8686

8787
# Cmdlets to export from this module
8888
CmdletsToExport = '*'

PureStorage.FlashArray.VMware.VVol/PureStorage.FlashArray.VMware.VVol.psm1

Lines changed: 118 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,10 @@ function Update-PfaVvolVmVolumeGroup {
6161
[VMware.VimAutomation.ViCore.Types.V1.DatastoreManagement.Datastore]$datastore,
6262

6363
[Parameter(Position=2,ValueFromPipeline=$True)]
64-
[PurePowerShell.PureArray[]]$flasharray
64+
[PurePowerShell.PureArray[]]$flasharray,
65+
66+
[Parameter(ParameterSetName='VM',Position=3)]
67+
[String]$volumeGroupName
6568
)
6669
$volumeFinalNames = @()
6770
if ($null -ne $datastore)
@@ -81,23 +84,6 @@ function Update-PfaVvolVmVolumeGroup {
8184
}
8285
foreach ($vm in $vms)
8386
{
84-
$configUUID = $vm.ExtensionData.Config.VmStorageObjectId
85-
if ($null -eq $configUUID)
86-
{
87-
write-warning -message "The input VM $($vm.name) is not a vVol-based virtual machine. Skipping"
88-
continue
89-
}
90-
add-type @"
91-
using System.Net;
92-
using System.Security.Cryptography.X509Certificates;
93-
public class TrustAllCertsPolicy : ICertificatePolicy {
94-
public bool CheckValidationResult(
95-
ServicePoint srvPoint, X509Certificate certificate,
96-
WebRequest request, int certificateProblem) {
97-
return true;
98-
}
99-
}
100-
"@
10187
$vmDatastores = $vm |Get-Datastore
10288
foreach ($vmDatastore in $vmDatastores)
10389
{
@@ -115,62 +101,135 @@ public class TrustAllCertsPolicy : ICertificatePolicy {
115101
{
116102
$fa = get-PfaConnectionOfDatastore -datastore $vmDatastore -flasharrays $flasharray -ErrorAction Stop
117103
}
118-
$faSession = new-PfaRestSession -flasharray $fa
119-
[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
120-
[System.Net.ServicePointManager]::CertificatePolicy = New-Object TrustAllCertsPolicy
121-
$volumeConfig = Invoke-RestMethod -Method Get -Uri "https://$($fa.Endpoint)/api/$($fa.apiversion)/volume?tags=true&filter=value='${configUUID}'" -WebSession $faSession -ErrorAction Stop
122-
$configVVolName = ($volumeConfig |where-object {$_.key -eq "PURE_VVOL_ID"}).name
123-
if ($null -eq $configVVolName)
104+
$vmId = $vm.ExtensionData.Config.InstanceUuid
105+
$customVgroupName = $false
106+
if ([string]::IsNullOrEmpty($volumeGroupName))
124107
{
125-
write-warning -message "The VM $($vm.name) was not found on this FlashArray. Skipping."
126-
continue
108+
$volumeGroupName = $vm.Name
109+
}
110+
else {
111+
$customVgroupName = $true
127112
}
128-
if ($vm.Name -match "^[a-zA-Z0-9\-]+$")
113+
if ($volumeGroupName -notmatch "^[a-zA-Z0-9\-]+$")
129114
{
130-
$vmName = $vm.Name
115+
$volumeGroupName = $volumeGroupName -replace "[^\w\-]", ""
116+
$volumeGroupName = $volumeGroupName -replace "[_]", ""
117+
$volumeGroupName = $volumeGroupName -replace " ", ""
131118
}
132-
else
119+
if ($customVgroupName -eq $false)
133120
{
134-
$vmName = $vm.Name -replace "[^\w\-]", ""
135-
$vmName = $vmName -replace "[_]", ""
136-
$vmName = $vmName -replace " ", ""
121+
$vGroupRand = '{0:X}' -f (get-random -Minimum 286331153 -max 4294967295)
122+
$volumeGroupName = "vvol-$($volumeGroupName)-$($vGroupRand)-vg"
137123
}
138-
$vGroupRand = '{0:X}' -f (get-random -Minimum 286331153 -max 4294967295)
139-
$newName = "vvol-$($vmName)-$($vGroupRand)-vg"
140-
if ([Regex]::Matches($configVVolName, "/").Count -eq 0)
124+
$vVolInfos = $null
125+
$vVolInfos = Get-PfaVvolVol -vm $vm[0] -flasharray $fa
126+
if (($vVolInfos.VolumeGroup |Select-Object -Unique).count -gt 1)
141127
{
142-
$vGroup = New-PfaVolumeGroup -Array $fa -Name $newName
128+
$vgroupsUnique = $vvolInfos.VolumeGroup |Select-Object -Unique
129+
Write-Warning -Message "Skipping the VM $($VM.name) as it is spread across more than one volume group: `r`n $($vgroupsUnique) "
130+
continue
143131
}
144-
else {
145-
$vGroup = $configVVolName.split('/')[0]
146-
$vGroup = Invoke-RestMethod -Method Put -Uri "https://$($fa.Endpoint)/api/$($fa.apiversion)/vgroup/${vGroup}?name=${newName}" -WebSession $faSession -ErrorAction Stop
132+
elseif (($vVolInfos.VolumeGroup |Select-Object -Unique).count -eq 0)
133+
{
134+
New-PfaRestOperation -resourceType "vgroup/$($volumeGroupName)" -restOperationType POST -flasharray $fa -SkipCertificateCheck -ErrorAction stop |Out-Null
147135
}
148-
$vmId = $vm.ExtensionData.Config.InstanceUuid
149-
$volumesVmId = Invoke-RestMethod -Method Get -Uri "https://$($fa.Endpoint)/api/$($fa.apiversion)/volume?tags=true&filter=value='${vmId}'" -WebSession $faSession -ErrorAction Stop
150-
$volumeNames = $volumesVmId |where-object {$_.key -eq "VMW_VmID"}
151-
foreach ($volumeName in $volumeNames)
136+
elseif (($vVolInfos.VolumeGroup |Select-Object -Unique).count -eq 1)
152137
{
153-
if ([Regex]::Matches($volumeName.name, "/").Count -eq 1)
154-
{
155-
if ($newName -ne $volumeName.name.split('/')[0])
156-
{
157-
$volName= $volumeName.name.split('/')[1]
158-
Add-PfaVolumeToContainer -Array $fa -Container $newName -Name $volName |Out-Null
159-
}
160-
}
161-
else {
162-
$volName= $volumeName.name
163-
Add-PfaVolumeToContainer -Array $fa -Container $newName -Name $volName |Out-Null
164-
}
138+
if ($volumeGroupName -ne ($vVolInfos.VolumeGroup |Select-Object -Unique))
139+
{
140+
$vGroup = $vVolInfos.VolumeGroup |Select-Object -Unique
141+
New-PfaRestOperation -resourceType "vgroup/$($vGroup)" -restOperationType PUT -jsonBody "{`"name`":`"$($volumeGroupName)`"}" -flasharray $fa -SkipCertificateCheck |Out-Null
142+
}
143+
}
144+
$vVolInfos = $null
145+
$vVolInfos = Get-PfaVvolVol -vm $vm[0] -flasharray $fa
146+
foreach ($vVolInfo in $vVolInfos)
147+
{
148+
if (($vVolInfo.VolumeGroup -ne $volumeGroupName) -and ($null -ne $vVolInfo.VolumeGroup))
149+
{
150+
New-PfaRestOperation -resourceType "volume/$($vVolInfo.VolumeGroup)/$($vVolInfo.Volume)" -restOperationType PUT -flasharray $fa -SkipCertificateCheck -jsonBody "{`"container`":`"$($volumeGroupName)`"}" |Out-Null
151+
}
152+
elseif ($null -eq $vVolInfo.VolumeGroup)
153+
{
154+
New-PfaRestOperation -resourceType "volume/$($vVolInfo.Volume)" -restOperationType PUT -flasharray $fa -SkipCertificateCheck -jsonBody "{`"container`":`"$($volumeGroupName)`"}" |Out-Null
155+
}
156+
}
157+
$volumesAfterMove = (New-PfaRestOperation -resourceType "volume" -restOperationType GET -queryFilter "?tags=true&filter=value=`'$($vmId)`'" -flasharray $fa -SkipCertificateCheck).Name |Select-Object -Unique
158+
foreach ($volumeAfterMove in $volumesAfterMove) {
159+
$volumeFinalNames += $volumeAfterMove
165160
}
166-
$volumesVmId = Invoke-RestMethod -Method Get -Uri "https://$($fa.Endpoint)/api/$($fa.apiversion)/volume?tags=true&filter=value='${vmId}'" -WebSession $faSession -ErrorAction Stop
167-
$volumeFinalNames += $volumesVmId |where-object {$_.key -eq "VMW_VmID"}
168-
remove-PfaRestSession -flasharray $fa -faSession $faSession |Out-Null
169161
}
170162
}
171163
}
172-
return $volumeFinalNames.name
164+
return $volumeFinalNames
173165
}
166+
function Get-PfaVvolVol{
167+
<#
168+
.SYNOPSIS
169+
Gets the vVol volumes of entered VM
170+
.DESCRIPTION
171+
Takes in a virtual machine
172+
.INPUTS
173+
Virtual machine (get-vm)
174+
.OUTPUTS
175+
Returns the FA volume and volume group name(s)
176+
.NOTES
177+
Version: 2.0
178+
Author: Cody Hosterman https://codyhosterman.com
179+
Creation Date: 05/26/2019
180+
Purpose/Change: Updated for new connection mgmt
181+
.EXAMPLE
182+
PS C:\ New-PfaConnection -endpoint flasharray-m20-2 -credentials (get-credential) -defaultArray
183+
PS C:\ get-vm myVM | get-harddisk | Get-VvolUuidFromVmdk
184+
185+
Pass in one or more vVol hard disks and return the corresponding vVol UUIDs
186+
187+
*******Disclaimer:******************************************************
188+
This scripts are offered "as is" with no warranty. While this
189+
scripts is tested and working in my environment, it is recommended that you test
190+
this script in a test lab before using in a production environment. Everyone can
191+
use the scripts/commands provided here without any written permission but I
192+
will not be liable for any damage or loss to the system.
193+
************************************************************************
194+
#>
195+
196+
[CmdletBinding()]
197+
Param(
198+
[Parameter(Position=0,ValueFromPipeline=$True,mandatory=$true)]
199+
[VMware.VimAutomation.ViCore.Types.V1.Inventory.VirtualMachine]$vm,
200+
201+
[Parameter(Position=1,ValueFromPipeline=$True,mandatory=$true)]
202+
[PurePowerShell.PureArray]$flasharray
203+
)
204+
$arraySerial = (New-PfaRestOperation -resourceType array -restOperationType GET -flasharray $flasharray -SkipCertificateCheck).id
205+
$datastore = $vm |Get-Datastore |Where-Object {$_.Type -eq 'VVOL'} |Where-Object {$_.ExtensionData.Info.VvolDS.StorageArray[0].uuid.Substring(16) -eq $arraySerial}
206+
if ($null -eq $datastore)
207+
{
208+
throw "There are no volumes on this FlashArray $($flasharray.EndPoint) for entered VM $($vm.name)"
209+
}
210+
else
211+
{
212+
$vmId = $vm.ExtensionData.Config.InstanceUuid
213+
$vVolVolumes = (New-PfaRestOperation -resourceType "volume" -restOperationType GET -queryFilter "?tags=true&filter=value=`'$($vmId)`'" -flasharray $flasharray -SkipCertificateCheck).Name |Select-Object -Unique
214+
$vVolInfos = @()
215+
foreach ($vVolVolume in $vVolVolumes)
216+
{
217+
$vVolInfo = New-Object -TypeName psobject
218+
if (($vVolVolume.split("/")).count -gt 1)
219+
{
220+
$vVolInfo | Add-Member -MemberType NoteProperty -Name VolumeGroup -Value ($vVolVolume.split("/"))[0]
221+
$vVolInfo | Add-Member -MemberType NoteProperty -Name Volume -Value ($vVolVolume.split("/"))[1]
222+
}
223+
else {
224+
$vVolInfo | Add-Member -MemberType NoteProperty -Name VolumeGroup -Value $null
225+
$vVolInfo | Add-Member -MemberType NoteProperty -Name Volume -Value $vVolVolume
226+
}
227+
$vVolInfos += $vVolInfo
228+
}
229+
}
230+
return $vVolInfos
231+
}
232+
174233
function Get-VvolUuidFromVmdk {
175234
<#
176235
.SYNOPSIS

0 commit comments

Comments
 (0)