From dc0213773d60620a23885d61430f409896d33804 Mon Sep 17 00:00:00 2001 From: NamedJason Date: Wed, 31 May 2017 07:27:38 -0700 Subject: [PATCH 1/5] Improved performance and user feedback I changed the structure of the functions to improve performance when working with large numbers of datastores and hosts. I also added more verbose progress bars so that the user would be more aware of what the scripts were doing at any given time. --- .../DatastoreFunctions.psm1 | 339 +++++++++++------- 1 file changed, 200 insertions(+), 139 deletions(-) diff --git a/Modules/DatastoreFunctions/DatastoreFunctions.psm1 b/Modules/DatastoreFunctions/DatastoreFunctions.psm1 index e417112..b908a40 100644 --- a/Modules/DatastoreFunctions/DatastoreFunctions.psm1 +++ b/Modules/DatastoreFunctions/DatastoreFunctions.psm1 @@ -1,50 +1,112 @@ -#Created by Alan Renouf, published at https://communities.vmware.com/docs/DOC-18008 +<# +.SYNOPSIS Datastore Functions +.DESCRIPTION A collection of functions to manipulate datastore Mount + Attach status +.EXAMPLE Get-Datastore | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize +.EXAMPLE Get-Datastore IX2ISCSI01 | Unmount-Datastore +.EXAMPLE Get-Datastore IX2ISCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize +.EXAMPLE Get-Datastore IX2iSCSI01 | Mount-Datastore +.EXAMPLE Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize +.EXAMPLE Get-Datastore IX2iSCSI01 | Detach-Datastore +.EXAMPLE Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize +.EXAMPLE Get-Datastore IX2iSCSI01 | Attach-datastore +.EXAMPLE Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize +.NOTES Written by Alan Renouf, originally published at https://blogs.vmware.com/vsphere/2012/01/automating-datastore-storage-device-detachment-in-vsphere-5.html +.NOTES May 2017: Modified by Jason Coleman (virtuallyjason.blogspot.com), to improve performance when dealing with a large number of hosts and datastores +#> +Function Get-HostViews { + [CmdletBinding()] + Param ( + $Datastore + ) + Begin{ + $allDatastores = @() + } + Process { + $allDatastores += $Datastore + } + End { + #Build the array of Datastore Objects + if (-not $Datastore) { + $allDatastores = Get-Datastore + } + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" + } + $allHosts = @() + $DShostsKeys = $allDatastores.extensiondata.host.key.value | sort | get-unique -asstring + $DShosts = foreach ($thisKey in $DShostsKeys) {($allDatastores.extensiondata.host | ? {$_.key.value -eq $thisKey})[0]} + $i = 1 + foreach ($DSHost in $DSHosts){ + write-progress -activity "Collecting ESXi Host Views" -status "Querying $($dshost.key)..." -percentComplete ($i++/$DSHosts.count*100) + $hostObj = "" | select keyValue,hostView,storageSys + $hostObj.hostView = get-view $DSHost.key + $hostObj.keyValue = $DSHost.key.value + $hostObj.storageSys = Get-View $hostObj.hostView.ConfigManager.StorageSystem + $allHosts += $hostObj + } + write-progress -activity "Collecting ESXi Host Views" -completed + $allHosts + } +} + Function Get-DatastoreMountInfo { [CmdletBinding()] Param ( [Parameter(ValueFromPipeline=$true)] $Datastore ) + #Roll back up an unrolled array from a pipeline + Begin{ + $allDatastores = @() + } Process { + $allDatastores += $Datastore + } + End { $AllInfo = @() + #Build the array of Datastore Objects if (-not $Datastore) { - $Datastore = Get-Datastore + $allDatastores = Get-Datastore } - Foreach ($ds in $Datastore) { - if ($ds.ExtensionData.info.Vmfs) { - $hostviewDSDiskName = $ds.ExtensionData.Info.vmfs.extent[0].diskname - if ($ds.ExtensionData.Host) { - $attachedHosts = $ds.ExtensionData.Host - Foreach ($VMHost in $attachedHosts) { - $hostview = Get-View $VMHost.Key - $hostviewDSState = $VMHost.MountInfo.Mounted - $StorageSys = Get-View $HostView.ConfigManager.StorageSystem - $devices = $StorageSys.StorageDeviceInfo.ScsiLun - Foreach ($device in $devices) { - $Info = "" | Select Datastore, VMHost, Lun, Mounted, State - if ($device.canonicalName -eq $hostviewDSDiskName) { - $hostviewDSAttachState = "" - if ($device.operationalState[0] -eq "ok") { - $hostviewDSAttachState = "Attached" - } elseif ($device.operationalState[0] -eq "off") { - $hostviewDSAttachState = "Detached" - } else { - $hostviewDSAttachState = $device.operationalstate[0] - } - $Info.Datastore = $ds.Name - $Info.Lun = $hostviewDSDiskName - $Info.VMHost = $hostview.Name - $Info.Mounted = $HostViewDSState - $Info.State = $hostviewDSAttachState - $AllInfo += $Info - } - } - + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" + } + $allDatastoreNAAs = foreach ($ds in $allDatastores) {$ds.ExtensionData.Info.vmfs.extent[0].diskname} + + #Build the array of custom Host Objects + $allHosts = Get-HostViews -datastore $allDatastores + $output = @() + $i = 1 + foreach ($dsHost in $allHosts){ + write-progress -activity "Checking Datastore access" -status "Checking $($dshost.hostview.name)..." -percentComplete ($i++ / $allHosts.count * 100) + #Get all devices on the host that match the list of $allDatastoreNAAs + $devices = $dsHost.storagesys.StorageDeviceInfo.ScsiLun + foreach ($device in $devices){ + if ($allDatastoreNAAs -contains $device.canonicalName){ + #Record information about this device/host combo + $thisDatastore = $alldatastores | ? {$_.ExtensionData.Info.vmfs.extent[0].diskname -eq $device.canonicalName} + $hostviewDSAttachState = "" + if ($device.operationalState[0] -eq "ok") { + $hostviewDSAttachState = "Attached" + } elseif ($device.operationalState[0] -eq "off") { + $hostviewDSAttachState = "Detached" + } else { + $hostviewDSAttachState = $device.operationalstate[0] } + $Info = "" | Select Datastore, VMHost, Lun, Mounted, State + $Info.VMHost = $dsHost.hostview.name + $Info.Datastore = $thisDatastore.name + $Info.Lun = $device.canonicalName + $Info.mounted = ($thisDatastore.extensiondata.host | ? {$_.key.value -eq $dshost.keyvalue}).mountinfo.mounted + $Info.state = $hostviewDSAttachState + $output += $info } } } - $AllInfo + write-progress -activity "Checking Datastore access" -completed + $output } } @@ -54,81 +116,32 @@ Function Detach-Datastore { [Parameter(ValueFromPipeline=$true)] $Datastore ) - Process { - if (-not $Datastore) { - Write-Host "No Datastore defined as input" - Exit - } - Foreach ($ds in $Datastore) { - $hostviewDSDiskName = $ds.ExtensionData.Info.vmfs.extent[0].Diskname - if ($ds.ExtensionData.Host) { - $attachedHosts = $ds.ExtensionData.Host - Foreach ($VMHost in $attachedHosts) { - $hostview = Get-View $VMHost.Key - $StorageSys = Get-View $HostView.ConfigManager.StorageSystem - $devices = $StorageSys.StorageDeviceInfo.ScsiLun - Foreach ($device in $devices) { - if ($device.canonicalName -eq $hostviewDSDiskName) { - $LunUUID = $Device.Uuid - Write-Host "Detaching LUN $($Device.CanonicalName) from host $($hostview.Name)..." - $StorageSys.DetachScsiLun($LunUUID); - } - } - } - } - } + Begin{ + $allDatastores = @() } -} - -Function Unmount-Datastore { - [CmdletBinding()] - Param ( - [Parameter(ValueFromPipeline=$true)] - $Datastore - ) Process { - if (-not $Datastore) { - Write-Host "No Datastore defined as input" - Exit - } - Foreach ($ds in $Datastore) { - $hostviewDSDiskName = $ds.ExtensionData.Info.vmfs.extent[0].Diskname - if ($ds.ExtensionData.Host) { - $attachedHosts = $ds.ExtensionData.Host - Foreach ($VMHost in $attachedHosts) { - $hostview = Get-View $VMHost.Key - $StorageSys = Get-View $HostView.ConfigManager.StorageSystem - Write-Host "Unmounting VMFS Datastore $($DS.Name) from host $($hostview.Name)..." - $StorageSys.UnmountVmfsVolume($DS.ExtensionData.Info.vmfs.uuid); - } - } - } + $allDatastores += $Datastore } -} - -Function Mount-Datastore { - [CmdletBinding()] - Param ( - [Parameter(ValueFromPipeline=$true)] - $Datastore - ) - Process { - if (-not $Datastore) { - Write-Host "No Datastore defined as input" - Exit + End { + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" } - Foreach ($ds in $Datastore) { - $hostviewDSDiskName = $ds.ExtensionData.Info.vmfs.extent[0].Diskname - if ($ds.ExtensionData.Host) { - $attachedHosts = $ds.ExtensionData.Host - Foreach ($VMHost in $attachedHosts) { - $hostview = Get-View $VMHost.Key - $StorageSys = Get-View $HostView.ConfigManager.StorageSystem - Write-Host "Mounting VMFS Datastore $($DS.Name) on host $($hostview.Name)..." - $StorageSys.MountVmfsVolume($DS.ExtensionData.Info.vmfs.uuid); - } + $allDatastoreNAAs = foreach ($ds in $allDatastores) {$ds.ExtensionData.Info.vmfs.extent[0].diskname} + $allHosts = Get-HostViews -datastore $allDatastores + $j = 1 + foreach ($dsHost in $allHosts){ + #Get all devices on the host that match the list of $allDatastoreNAAs + write-progress -id 1 -activity "Detaching Datastores" -status "Removing device(s) from $($dsHost.hostview.name)" -percentComplete ($j++ / $allHosts.count * 100) + $devices = $dsHost.storagesys.StorageDeviceInfo.ScsiLun | ? {$allDatastoreNAAs -contains $_.canonicalName} + $i = 1 + foreach ($device in $devices){ + write-progress -parentid 1 -activity "Detaching Datastores" -status "Removing device: $(($allDatastores | ? {$_.ExtensionData.Info.vmfs.extent[0].diskname -eq $device.canonicalName}).name)" -percentComplete ($i++ / $allDatastoreNAAs.count * 100) + $LunUUID = $Device.Uuid + $dsHost.storageSys.DetachScsiLun($LunUUID); } } + write-progress -activity "Detaching Datastores" -completed } } @@ -138,47 +151,95 @@ Function Attach-Datastore { [Parameter(ValueFromPipeline=$true)] $Datastore ) + Begin{ + $allDatastores = @() + } Process { - if (-not $Datastore) { - Write-Host "No Datastore defined as input" - Exit + $allDatastores += $Datastore + } + End { + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" } - Foreach ($ds in $Datastore) { - $hostviewDSDiskName = $ds.ExtensionData.Info.vmfs.extent[0].Diskname - if ($ds.ExtensionData.Host) { - $attachedHosts = $ds.ExtensionData.Host - Foreach ($VMHost in $attachedHosts) { - $hostview = Get-View $VMHost.Key - $StorageSys = Get-View $HostView.ConfigManager.StorageSystem - $devices = $StorageSys.StorageDeviceInfo.ScsiLun - Foreach ($device in $devices) { - if ($device.canonicalName -eq $hostviewDSDiskName) { - $LunUUID = $Device.Uuid - Write-Host "Attaching LUN $($Device.CanonicalName) to host $($hostview.Name)..." - $StorageSys.AttachScsiLun($LunUUID); - } - } + $allDatastoreNAAs = foreach ($ds in $allDatastores) {$ds.ExtensionData.Info.vmfs.extent[0].diskname} + $allHosts = Get-HostViews -datastore $allDatastores + $j = 1 + foreach ($dsHost in $allHosts){ + #Get all devices on the host that match the list of $allDatastoreNAAs + write-progress -id 1 -activity "Attaching Datastores" -status "Attaching devices to $($dsHost.hostview.name)" -percentComplete ($j++ / $allHosts.count * 100) + $devices = $dsHost.storagesys.StorageDeviceInfo.ScsiLun + $i = 1 + foreach ($device in $devices){ + write-progress -parentid 1 -activity "Attaching Datastores" -status "Attaching device: $($Device.Uuid)" -percentComplete ($i++ / $devices.count * 100) + if ($allDatastoreNAAs -contains $device.canonicalName){ + $LunUUID = $Device.Uuid + $dsHost.storageSys.AttachScsiLun($LunUUID); } } } + write-progress -activity "Attaching Datastores" -completed + } +} + +Function Unmount-Datastore { + [CmdletBinding()] + Param ( + [Parameter(ValueFromPipeline=$true)] + $Datastore + ) + Begin{ + $allDatastores = @() + } + Process { + $allDatastores += $Datastore + } + End { + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" + } + $allHosts = Get-HostViews -datastore $allDatastores + $j = 1 + foreach ($dsHost in $allHosts){ + write-progress -id 1 -activity "Unmounting Datastores" -status "Unmounting devices from $($dsHost.hostview.name)" -percentComplete ($j++ / $allHosts.count * 100) + $i = 1 + foreach ($ds in $allDatastores){ + write-progress -parentid 1 -activity "Unmounting Datastores" -status "Unmounting device: $($ds.name)" -percentComplete ($i++ / $allDatastores.count * 100) + $dsHost.storageSys.UnmountVmfsVolume($DS.ExtensionData.Info.vmfs.uuid); + } + } + write-progress -activity "Unmounting Datastores" -completed + } +} + +Function Mount-Datastore { + [CmdletBinding()] + Param ( + [Parameter(ValueFromPipeline=$true)] + $Datastore + ) + Begin{ + $allDatastores = @() + } + Process { + $allDatastores += $Datastore + } + End { + $allDatastores = $allDatastores | ? {$_.pstypenames -contains "VMware.VimAutomation.ViCore.Impl.V1.DatastoreManagement.DatastoreImpl"} + if (-not $allDatastores){ + Throw "No Datastores found.`nIs ""$Datastore"" a Datastore Object?" + } + $allHosts = Get-HostViews -datastore $allDatastores + $j = 0 + foreach ($dsHost in $allHosts){ + write-progress -activity "Mounting Datastores" -status "Mounting devices to $($dsHost.hostview.name)" -percentComplete ($j++ / $allHosts.count * 100) + $i = 1 + foreach ($ds in $allDatastores){ + write-progress -activity "Mounting Datastores" -status "Mounting device: $($DS.ExtensionData.Info.vmfs.uuid)" -percentComplete ($i++ / $allDatastores.count * 100) + $dsHost.storageSys.MountVmfsVolume($DS.ExtensionData.Info.vmfs.uuid); + } + } + write-progress -activity "Mounting Datastores" -completed } } -# -#Get-Datastore | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize -# -#Get-Datastore IX2ISCSI01 | Unmount-Datastore -# -#Get-Datastore IX2ISCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize -# -#Get-Datastore IX2iSCSI01 | Mount-Datastore -# -#Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize -# -#Get-Datastore IX2iSCSI01 | Detach-Datastore -# -#Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize -# -#Get-Datastore IX2iSCSI01 | Attach-datastore -# -#Get-Datastore IX2iSCSI01 | Get-DatastoreMountInfo | Sort Datastore, VMHost | FT -AutoSize -# From e1bc6912fa3c6397ac5b4b63459894f9ddc80dd5 Mon Sep 17 00:00:00 2001 From: mycloudrevolution Date: Tue, 13 Jun 2017 22:51:12 +0200 Subject: [PATCH 2/5] VMware-vCD-Module Create new Org, OrgUser, OrgVDC --- Modules/VMware-vCD-Module/README.md | 23 ++ .../VMware-vCD-Module/VMware-vCD-Module.psd1 | 126 +++++++++ .../examples/OnBoarding.json | 24 ++ .../functions/Invoke-MyOnBoarding.psm1 | 172 ++++++++++++ .../functions/New-MyOrg.psm1 | 107 ++++++++ .../functions/New-MyOrgAdmin.psm1 | 91 +++++++ .../functions/New-MyOrgVdc.psm1 | 252 ++++++++++++++++++ .../media/Invoke-MyOnBoarding.png | Bin 0 -> 40988 bytes .../media/VSCode-Pester-Tests.png | Bin 0 -> 80733 bytes .../tests/VMware-vCD-Module.Tests.ps1 | 35 +++ 10 files changed, 830 insertions(+) create mode 100644 Modules/VMware-vCD-Module/README.md create mode 100644 Modules/VMware-vCD-Module/VMware-vCD-Module.psd1 create mode 100644 Modules/VMware-vCD-Module/examples/OnBoarding.json create mode 100644 Modules/VMware-vCD-Module/functions/Invoke-MyOnBoarding.psm1 create mode 100644 Modules/VMware-vCD-Module/functions/New-MyOrg.psm1 create mode 100644 Modules/VMware-vCD-Module/functions/New-MyOrgAdmin.psm1 create mode 100644 Modules/VMware-vCD-Module/functions/New-MyOrgVdc.psm1 create mode 100644 Modules/VMware-vCD-Module/media/Invoke-MyOnBoarding.png create mode 100644 Modules/VMware-vCD-Module/media/VSCode-Pester-Tests.png create mode 100644 Modules/VMware-vCD-Module/tests/VMware-vCD-Module.Tests.ps1 diff --git a/Modules/VMware-vCD-Module/README.md b/Modules/VMware-vCD-Module/README.md new file mode 100644 index 0000000..a691421 --- /dev/null +++ b/Modules/VMware-vCD-Module/README.md @@ -0,0 +1,23 @@ +VMware-vCD-Module PowerShell Module +=================================== + +![Invoke-MyOnBoarding](/media/Invoke-MyOnBoarding.png) + +# About + +## Project Owner: + +Markus Kraus [@vMarkus_K](https://twitter.com/vMarkus_K) + +## Project WebSite: +[mycloudrevolution.com](http://mycloudrevolution.com/) + +## Project Documentation: + +[Read the Docs](http://vmware-vcd-module.readthedocs.io/) + +## Project Description: + +The 'VMware-vCD-Module' PowerShell Module is focused on the initial craation of VMware vCloud Director Objects like Org, Org User, Org VDC. + + diff --git a/Modules/VMware-vCD-Module/VMware-vCD-Module.psd1 b/Modules/VMware-vCD-Module/VMware-vCD-Module.psd1 new file mode 100644 index 0000000..59a02de --- /dev/null +++ b/Modules/VMware-vCD-Module/VMware-vCD-Module.psd1 @@ -0,0 +1,126 @@ +# +# Modulmanifest für das Modul "PSGet_VMware-vCD-Module" +# +# Generiert von: Markus +# +# Generiert am: 6/11/2017 +# + +@{ + +# Die diesem Manifest zugeordnete Skript- oder Binärmoduldatei. +# RootModule = '' + +# Die Versionsnummer dieses Moduls +ModuleVersion = '0.2.0' + +# ID zur eindeutigen Kennzeichnung dieses Moduls +GUID = '1ef8a2de-ca22-4c88-8cdb-e00f35007d2a' + +# Autor dieses Moduls +Author = 'Markus' + +# Unternehmen oder Hersteller dieses Moduls +CompanyName = 'Unbekannt' + +# Urheberrechtserklärung für dieses Modul +Copyright = '(c) 2017 Markus. Alle Rechte vorbehalten.' + +# Beschreibung der von diesem Modul bereitgestellten Funktionen +# Description = '' + +# Die für dieses Modul mindestens erforderliche Version des Windows PowerShell-Moduls +# PowerShellVersion = '' + +# Der Name des für dieses Modul erforderlichen Windows PowerShell-Hosts +# PowerShellHostName = '' + +# Die für dieses Modul mindestens erforderliche Version des Windows PowerShell-Hosts +# PowerShellHostVersion = '' + +# Die für dieses Modul mindestens erforderliche Microsoft .NET Framework-Version +# DotNetFrameworkVersion = '' + +# Die für dieses Modul mindestens erforderliche Version der CLR (Common Language Runtime) +# CLRVersion = '' + +# Die für dieses Modul erforderliche Prozessorarchitektur ("Keine", "X86", "Amd64"). +# ProcessorArchitecture = '' + +# Die Module, die vor dem Importieren dieses Moduls in die globale Umgebung geladen werden müssen +# RequiredModules = @() + +# Die Assemblys, die vor dem Importieren dieses Moduls geladen werden müssen +# RequiredAssemblies = @() + +# Die Skriptdateien (PS1-Dateien), die vor dem Importieren dieses Moduls in der Umgebung des Aufrufers ausgeführt werden. +# ScriptsToProcess = @() + +# Die Typdateien (.ps1xml), die beim Importieren dieses Moduls geladen werden sollen +# TypesToProcess = @() + +# Die Formatdateien (.ps1xml), die beim Importieren dieses Moduls geladen werden sollen +# FormatsToProcess = @() + +# Die Module, die als geschachtelte Module des in "RootModule/ModuleToProcess" angegebenen Moduls importiert werden sollen. +NestedModules = @('functions\Invoke-MyOnBoarding.psm1', + 'functions\New-MyOrg.psm1', + 'functions\New-MyOrgAdmin.psm1', + 'functions\New-MyOrgVdc.psm1') + +# Aus diesem Modul zu exportierende Funktionen +FunctionsToExport = 'Invoke-MyOnBoarding', 'New-MyOrg', 'New-MyOrgAdmin', 'New-MyOrgVdc' + +# Aus diesem Modul zu exportierende Cmdlets +CmdletsToExport = '*' + +# Die aus diesem Modul zu exportierenden Variablen +VariablesToExport = '*' + +# Aus diesem Modul zu exportierende Aliase +AliasesToExport = '*' + +# Aus diesem Modul zu exportierende DSC-Ressourcen +# DscResourcesToExport = @() + +# Liste aller Module in diesem Modulpaket +# ModuleList = @() + +# Liste aller Dateien in diesem Modulpaket +# FileList = @() + +# Die privaten Daten, die an das in "RootModule/ModuleToProcess" angegebene Modul übergeben werden sollen. Diese können auch eine PSData-Hashtabelle mit zusätzlichen von PowerShell verwendeten Modulmetadaten enthalten. +PrivateData = @{ + + PSData = @{ + + # Tags applied to this module. These help with module discovery in online galleries. + # Tags = @() + + # A URL to the license for this module. + # LicenseUri = '' + + # A URL to the main website for this project. + # ProjectUri = '' + + # A URL to an icon representing this module. + # IconUri = '' + + # ReleaseNotes of this module + # ReleaseNotes = '' + + # External dependent modules of this module + # ExternalModuleDependencies = '' + + } # End of PSData hashtable + +} # End of PrivateData hashtable + +# HelpInfo-URI dieses Moduls +# HelpInfoURI = '' + +# Standardpräfix für Befehle, die aus diesem Modul exportiert werden. Das Standardpräfix kann mit "Import-Module -Prefix" überschrieben werden. +# DefaultCommandPrefix = '' + +} + diff --git a/Modules/VMware-vCD-Module/examples/OnBoarding.json b/Modules/VMware-vCD-Module/examples/OnBoarding.json new file mode 100644 index 0000000..ecd1f88 --- /dev/null +++ b/Modules/VMware-vCD-Module/examples/OnBoarding.json @@ -0,0 +1,24 @@ +{ +"Org": { + "Name":"TestOrg", + "FullName": "Test Org", + "Description":"Automation Test Org" + }, +"OrgAdmin": { + "Name":"TestOrgAdmin", + "Pasword": "myPassword1!", + "FullName":"Test OrgAdmin", + "EmailAddress":"test@admin.org" + }, +"OrgVdc": { + "Name":"TestOrgVdc", + "FixedSize": "M", + "CPULimit": "1000", + "MEMLimit":"1024", + "StorageLimit":"1024", + "StorageProfile":"Standard-DC01", + "ProviderVDC":"Provider-VDC-DC01", + "NetworkPool":"Provider-VDC-DC01-NetPool", + "ExternalNetwork": "External-OrgVdcNet" + } +} \ No newline at end of file diff --git a/Modules/VMware-vCD-Module/functions/Invoke-MyOnBoarding.psm1 b/Modules/VMware-vCD-Module/functions/Invoke-MyOnBoarding.psm1 new file mode 100644 index 0000000..4b5e209 --- /dev/null +++ b/Modules/VMware-vCD-Module/functions/Invoke-MyOnBoarding.psm1 @@ -0,0 +1,172 @@ +#Requires -Version 4 +#Requires -Modules VMware.VimAutomation.Cloud, @{ModuleName="VMware.VimAutomation.Cloud";ModuleVersion="6.3.0.0"} +Function Invoke-MyOnBoarding { +<# +.SYNOPSIS + Creates all vCD Objecst for a new IAAS Customer + +.DESCRIPTION + Creates all vCD Objects for a new IAAS Customer + + All Objects are: + * Org + * Default Org Admin + * Org VDC + ** Private Catalog + ** Optional Bridged Network + + JSON Config Example: + + { + "Org": { + "Name":"TestOrg", + "FullName": "Test Org", + "Description":"Automation Test Org" + }, + "OrgAdmin": { + "Name":"TestOrgAdmin", + "Pasword": "myPassword1!", + "FullName":"Test OrgAdmin", + "EmailAddress":"test@admin.org" + }, + "OrgVdc": { + "Name":"TestOrgVdc", + "FixedSize": "M", + "CPULimit": "1000", + "MEMLimit":"1000", + "StorageLimit":"1000", + "StorageProfile":"Standard-DC01", + "ProviderVDC":"Provider-VDC-DC01", + "NetworkPool":"Provider-VDC-DC01-NetPool", + "ExternalNetwork": "External_OrgVdcNet" + } + } + +.NOTES + File Name : Invoke-MyOnBoarding.ps1 + Author : Markus Kraus + Version : 1.2 + State : Ready + +.LINK + https://mycloudrevolution.com/ + +.EXAMPLE + Invoke-MyOnBoarding -ConfigFile ".\OnBoarding.json" -Enabled:$true + +.EXAMPLE + Invoke-MyOnBoarding -ConfigFile ".\OnBoarding.json" -Enabled:$false + +.PARAMETER ConfigFile + Full Path to the JSON Config File + +.PARAMETER Enabled + Should the Customer be enabled after creation + + Default: $False + +#> + Param ( + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Full Path to the JSON Config File")] + [ValidateNotNullorEmpty()] + [String] $ConfigFile, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Should the Customer be enabled after creation")] + [ValidateNotNullorEmpty()] + [Switch]$Enabled + ) + Process { + + $Valid = $true + + Write-Verbose "## Import JSON Config" + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Importing JSON Config...`n" + $Configs = Get-Content -Raw -Path $ConfigFile -ErrorAction Continue | ConvertFrom-Json -ErrorAction Continue + + if (!($Configs)) { + $Valid = $false + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Importing JSON Config Failed" -ForegroundColor Red + } + else { + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Importing JSON Config OK" -ForegroundColor Green + } + + if ($Valid) { + try{ + Write-Verbose "## Create Org" + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new Org...`n" -ForegroundColor Yellow + $Trash = New-MyOrg -Name $Configs.Org.Name -FullName $Configs.Org.Fullname -Description $Configs.Org.Description -Enabled:$Enabled + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new Org OK" -ForegroundColor Green + Get-Org -Name $Configs.Org.Name | Select-Object Name, FullName, Enabled | Format-Table -AutoSize + } + catch { + $Valid = $false + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new Org Failed" -ForegroundColor Red + } + } + + if ($Valid) { + try{ + Write-Verbose "## Create OrgAdmin" + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgAdmin...`n" -ForegroundColor Yellow + $Trash = New-MyOrgAdmin -Name $Configs.OrgAdmin.Name -Pasword $Configs.OrgAdmin.Pasword -FullName $Configs.OrgAdmin.FullName -EmailAddress $Configs.OrgAdmin.EmailAddress -Org $Configs.Org.Name -Enabled:$Enabled + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgAdmin OK" -ForegroundColor Green + Get-CIUser -Org $Configs.Org.Name -Name $Configs.OrgAdmin.Name | Select-Object Name, FullName, Email | Format-Table -AutoSize + } + catch { + $Valid = $false + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgAdmin Failed" -ForegroundColor Red + } + } + if ($Valid) { + try{ + Write-Verbose "## Create OrgVdc" + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgVdc...`n" -ForegroundColor Yellow + + if ($Configs.OrgVdc.FixedSize){ + + Write-Host "Fixed Size (T-Shirt Size) '$($Configs.OrgVdc.FixedSize)' Org VDC Requested!" + + switch ($Configs.OrgVdc.FixedSize) { + M { + [String]$CPULimit = 36000 + [String]$MEMLimit = 122880 + [String]$StorageLimit = 1048576 + } + L { + [String]$CPULimit = 36000 + [String]$MEMLimit = 245760 + [String]$StorageLimit = 1048576 + } + default {throw "Invalid T-Shirt Size!"} + } + + } + else{ + Write-Host "Custom Org VDC Size Requested!" + + $CPULimit = $Configs.OrgVdc.CPULimit + $MEMLimit = $Configs.OrgVdc.MEMLimit + $StorageLimit = $Configs.OrgVdc.StorageLimit + + } + + if ($Configs.OrgVdc.ExternalNetwork){ + $Trash = New-MyOrgVdc -Name $Configs.OrgVdc.Name -CPULimit $CPULimit -MEMLimit $MEMLimit -StorageLimit $StorageLimit -Networkpool $Configs.OrgVdc.NetworkPool -StorageProfile $Configs.OrgVdc.StorageProfile -ProviderVDC $Configs.OrgVdc.ProviderVDC -ExternalNetwork $Configs.OrgVdc.ExternalNetwork -Org $Configs.Org.Name -Enabled:$Enabled + } + else { + $Trash = New-MyOrgVdc -Name $Configs.OrgVdc.Name -CPULimit $CPULimit -MEMLimit $MEMLimit -StorageLimit $StorageLimit -Networkpool $Configs.OrgVdc.NetworkPool -StorageProfile $Configs.OrgVdc.StorageProfile -ProviderVDC $Configs.OrgVdc.ProviderVDC -Org $Configs.Org.Name -Enabled:$Enabled + } + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgVdc OK" -ForegroundColor Green + Get-OrgVdc -Org $Configs.Org.Name -Name $Configs.OrgVdc.Name | Select-Object Name, Enabled, CpuAllocationGhz, MemoryLimitGB, StorageLimitGB, AllocationModel, ThinProvisioned, UseFastProvisioning, ` + @{N="StorageProfile";E={$_.ExtensionData.VdcStorageProfiles.VdcStorageProfile.Name}}, ` + @{N='VCpuInMhz';E={$_.ExtensionData.VCpuInMhz}} | Format-Table -AutoSize + } + catch { + $Valid = $false + Write-Host "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss") Creating new OrgVdc Failed" -ForegroundColor Red + } + } + + Write-Output "Overall Execution was Valid: $Valid" + } +} diff --git a/Modules/VMware-vCD-Module/functions/New-MyOrg.psm1 b/Modules/VMware-vCD-Module/functions/New-MyOrg.psm1 new file mode 100644 index 0000000..69565bb --- /dev/null +++ b/Modules/VMware-vCD-Module/functions/New-MyOrg.psm1 @@ -0,0 +1,107 @@ +#Requires -Version 4 +#Requires -Modules VMware.VimAutomation.Cloud, @{ModuleName="VMware.VimAutomation.Cloud";ModuleVersion="6.3.0.0"} +Function New-MyOrg { +<# +.SYNOPSIS + Creates a new vCD Org with Default Parameters + +.DESCRIPTION + Creates a new vCD Org with Default Parameters. + + Default Parameters are: + * Catalog Publishing + * Catalog Subscription + * VM Quota + * Stored VM Quota + * VM Lease Time + * Stored VM Lease Time + * Password Policy Settings + +.NOTES + File Name : New-MyOrg.ps1 + Author : Markus Kraus + Version : 1.1 + State : Ready + +.LINK + https://mycloudrevolution.com/ + +.EXAMPLE + New-MyOrg -Name "TestOrg" -FullName "Test Org" -Description "PowerCLI Test Org" + +.PARAMETER Name + Name of the New Org as String + +.PARAMETER FullName + Full Name of the New Org as String + +.PARAMETER Description + Description of the New Org as String + +.PARAMETER Enabled + Should the New Org be enabled after creation + + Default:$false + +#> + Param ( + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Name of the New Org as string")] + [ValidateNotNullorEmpty()] + [String] $Name, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Full Name of the New Org as string")] + [ValidateNotNullorEmpty()] + [String] $FullName, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Description of the New Org as string")] + [ValidateNotNullorEmpty()] + [String] $Description, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Should the New Org be enabled after creation")] + [ValidateNotNullorEmpty()] + [Switch]$Enabled + ) + Process { + $vcloud = $DefaultCIServers[0].ExtensionData + + ## Create Objects + $AdminOrg = New-Object VMware.VimAutomation.Cloud.Views.AdminOrg + $orgGeneralSettings = New-Object VMware.VimAutomation.Cloud.Views.OrgGeneralSettings + $orgOrgLeaseSettings = New-Object VMware.VimAutomation.Cloud.Views.OrgLeaseSettings + $orgOrgVAppTemplateLeaseSettings = New-Object VMware.VimAutomation.Cloud.Views.OrgVAppTemplateLeaseSettings + $orgOrgPasswordPolicySettings = New-Object VMware.VimAutomation.Cloud.Views.OrgPasswordPolicySettings + $orgSettings = New-Object VMware.VimAutomation.Cloud.Views.OrgSettings + + ## Admin Settings + $adminOrg.Name = $name + $adminOrg.FullName = $FullName + $adminOrg.Description = $description + $adminOrg.IsEnabled = $Enabled + + ## Org Setting + ### General Org Settings + $orgGeneralSettings.CanPublishCatalogs = $False + $orgGeneralSettings.CanPublishExternally = $False + $orgGeneralSettings.CanSubscribe = $True + $orgGeneralSettings.DeployedVMQuota = 0 + $orgGeneralSettings.StoredVmQuota = 0 + $orgSettings.OrgGeneralSettings = $orgGeneralSettings + ### vApp Org Setting + $orgOrgLeaseSettings.DeleteOnStorageLeaseExpiration = $false + $orgOrgLeaseSettings.DeploymentLeaseSeconds = 0 + $orgOrgLeaseSettings.StorageLeaseSeconds = 0 + $orgSettings.VAppLeaseSettings = $orgOrgLeaseSettings + ### vApp Template Org Setting + $orgOrgVAppTemplateLeaseSettings.DeleteOnStorageLeaseExpiration = $false + $orgOrgVAppTemplateLeaseSettings.StorageLeaseSeconds = 0 + $orgSettings.VAppTemplateLeaseSettings = $orgOrgVAppTemplateLeaseSettings + ### PasswordPolicySettings Org Setting + $orgOrgPasswordPolicySettings.AccountLockoutEnabled = $True + $orgOrgPasswordPolicySettings.InvalidLoginsBeforeLockout = 5 + $orgOrgPasswordPolicySettings.AccountLockoutIntervalMinutes = 30 + $orgSettings.OrgPasswordPolicySettings = $orgOrgPasswordPolicySettings + + $adminOrg.Settings = $orgSettings + + $CreateOrg = $vcloud.CreateOrg($adminOrg) + + Get-Org -Name $name | Format-Table -AutoSize + } +} diff --git a/Modules/VMware-vCD-Module/functions/New-MyOrgAdmin.psm1 b/Modules/VMware-vCD-Module/functions/New-MyOrgAdmin.psm1 new file mode 100644 index 0000000..26087c0 --- /dev/null +++ b/Modules/VMware-vCD-Module/functions/New-MyOrgAdmin.psm1 @@ -0,0 +1,91 @@ +#Requires -Version 4 +#Requires -Modules VMware.VimAutomation.Cloud, @{ModuleName="VMware.VimAutomation.Cloud";ModuleVersion="6.3.0.0"} +Function New-MyOrgAdmin { +<# +.SYNOPSIS + Creates a new vCD Org Admin with Default Parameters + +.DESCRIPTION + Creates a new vCD Org Admin with Default Parameters + + Default Parameters are: + * User Role + +.NOTES + File Name : New-MyOrgAdmin.ps1 + Author : Markus Kraus + Version : 1.1 + State : Ready + +.LINK + https://mycloudrevolution.com/ + +.EXAMPLE + New-MyOrgAdmin -Name "OrgAdmin" -Pasword "Anfang!!" -FullName "Org Admin" -EmailAddress "OrgAdmin@TestOrg.local" -Org "TestOrg" + +.PARAMETER Name + Name of the New Org Admin as String + +.PARAMETER FullName + Full Name of the New Org Admin as String + +.PARAMETER Password + Password of the New Org Admin as String + +.PARAMETER EmailAddress + EmailAddress of the New Org Admin as String + +.PARAMETER Enabled + Should the New Org be enabled after creation + + Default:$false + +.PARAMETER Org + Org where the new Org Admin should be created as string + +#> + Param ( + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Name of the New Org Admin as String")] + [ValidateNotNullorEmpty()] + [String] $Name, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Password of the New Org Admin as String")] + [ValidateNotNullorEmpty()] + [String] $Pasword, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Full Name of the New Org Admin as String")] + [ValidateNotNullorEmpty()] + [String] $FullName, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="EmailAddress of the New Org Admin as String")] + [ValidateNotNullorEmpty()] + [String] $EmailAddress, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Org where the new Org Admin should be created as string")] + [ValidateNotNullorEmpty()] + [String] $Org, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Should the New Org be enabled after creation")] + [ValidateNotNullorEmpty()] + [Switch]$Enabled + ) + Process { + + ## Create Objects + $OrgED = (Get-Org $Org).ExtensionData + $orgAdminUser = New-Object VMware.VimAutomation.Cloud.Views.User + + ## Settings + $orgAdminUser.Name = $Name + $orgAdminUser.FullName = $FullName + $orgAdminUser.EmailAddress = $EmailAddress + $orgAdminUser.Password = $Pasword + $orgAdminUser.IsEnabled = $Enabled + + $vcloud = $DefaultCIServers[0].ExtensionData + + ## Find Role + $orgAdminRole = $vcloud.RoleReferences.RoleReference | Where-Object {$_.Name -eq "Organization Administrator"} + $orgAdminUser.Role = $orgAdminRole + + ## Create User + $user = $orgED.CreateUser($orgAdminUser) + + Get-CIUser -Org $Org -Name $Name | Format-Table -AutoSize + } +} diff --git a/Modules/VMware-vCD-Module/functions/New-MyOrgVdc.psm1 b/Modules/VMware-vCD-Module/functions/New-MyOrgVdc.psm1 new file mode 100644 index 0000000..783ad5e --- /dev/null +++ b/Modules/VMware-vCD-Module/functions/New-MyOrgVdc.psm1 @@ -0,0 +1,252 @@ +#Requires -Version 4 +#Requires -Modules VMware.VimAutomation.Cloud, @{ModuleName="VMware.VimAutomation.Cloud";ModuleVersion="6.3.0.0"} +Function New-MyOrgVdc { +<# +.SYNOPSIS + Creates a new vCD Org VDC with Default Parameters + +.DESCRIPTION + Creates a new vCD Org VDC with Default Parameters + + Default Parameters are: + * Allocation Model + * Network Quota + * VM Quota + * 'vCpu In Mhz' + * Fast Provisioning + * Thin Provisioning + * private Catalog + +.NOTES + File Name : New-MyOrgVdc.ps1 + Author : Markus Kraus + Version : 1.2 + State : Ready + +.LINK + https://mycloudrevolution.com/ + +.EXAMPLE + New-MyOrgVdc -Name "TestVdc" -CPULimit 1000 -MEMLimit 1000 -StorageLimit 1000 -StorageProfile "Standard-DC01" -NetworkPool "NetworkPool-DC01" -ProviderVDC "Provider-VDC-DC01" -Org "TestOrg" -ExternalNetwork "External_OrgVdcNet" + +.EXAMPLE + New-MyOrgVdc -Name "TestVdc" -CPULimit 1000 -MEMLimit 1000 -StorageLimit 1000 -StorageProfile "Standard-DC01" -NetworkPool "NetworkPool-DC01" -ProviderVDC "Provider-VDC-DC01" -Org "TestOrg" + +.PARAMETER Name + Name of the New Org VDC as String + +.PARAMETER CPULimit + CPU Limit (MHz) of the New Org VDC as String + +.PARAMETER MEMLimit + Memory Limit (MB) of the New Org VDC as String + +.PARAMETER StorageLimit + Storage Limit (MB) of the New Org VDC as String + +.PARAMETER StorageProfile + Storage Profile of the New Org VDC as String + +.PARAMETER NetworkPool + Network Pool of the New Org VDC as String + +.PARAMETER ExternalNetwork + Optional External Network of the New Org VDC as String + +.PARAMETER Enabled + Should the New Org VDC be enabled after creation + + Default:$false + + Note: If an External Network is requested the Org VDC will be enabled during External Network Configuration + +.PARAMETER ProviderVDC + ProviderVDC where the new Org VDC should be created as string + +.PARAMETER Org + Org where the new Org VDC should be created as string + +.PARAMETER Timeout + Timeout for teh Org VDC to get Ready + + Default: 120s + +#> + Param ( + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Name of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [String] $Name, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="CPU Limit (MHz) of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [int] $CPULimit, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Memory Limit (MB) of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [int] $MEMLimit, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Storage Limit (MB) of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [int] $StorageLimit, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Storage Profile of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [String] $StorageProfile, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Network Pool of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [String] $NetworkPool, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Optional External Network of the New Org VDC as String")] + [ValidateNotNullorEmpty()] + [String] $ExternalNetwork, + [Parameter(Mandatory=$False, ValueFromPipeline=$False, HelpMessage="Should the New Org VDC be enabled after creation")] + [ValidateNotNullorEmpty()] + [Switch]$Enabled, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="ProviderVDC where the new Org VDC should be created as string")] + [ValidateNotNullorEmpty()] + [String] $ProviderVDC, + [Parameter(Mandatory=$True, ValueFromPipeline=$False, HelpMessage="Org where the new Org VDC should be created as string")] + [ValidateNotNullorEmpty()] + [String] $Org, + [Parameter(Mandatory=$False, ValueFromPipeline=$False,HelpMessage="Timeout for teh Org VDC to get Ready")] + [ValidateNotNullorEmpty()] + [int] $Timeout = 120 + ) + Process { + ## Create Objects and all Settings + Write-Verbose "Create Objects and all Settings" + $adminVdc = New-Object VMware.VimAutomation.Cloud.Views.AdminVdc + $adminVdc.Name = $name + $adminVdc.IsEnabled = $Enabled + $OrgVdcproviderVdc = Get-ProviderVdc $ProviderVDC + $providerVdcRef = New-Object VMware.VimAutomation.Cloud.Views.Reference + $providerVdcRef.Href = $OrgVdcproviderVdc.Href + $adminVdc.ProviderVdcReference = $providerVdcRef + $adminVdc.AllocationModel = "AllocationPool" + $adminVdc.ComputeCapacity = New-Object VMware.VimAutomation.Cloud.Views.ComputeCapacity + $adminVdc.ComputeCapacity.Cpu = New-Object VMware.VimAutomation.Cloud.Views.CapacityWithUsage + $adminVdc.ComputeCapacity.Cpu.Units = "MHz" + $adminVdc.ComputeCapacity.Cpu.Limit = $CPULimit + $adminVdc.ComputeCapacity.Cpu.Allocated = $CPULimit + $adminVdc.ComputeCapacity.Memory = New-Object VMware.VimAutomation.Cloud.Views.CapacityWithUsage + $adminVdc.ComputeCapacity.Memory.Units = "MB" + $adminVdc.ComputeCapacity.Memory.Limit = $MEMLimit + $adminVdc.ComputeCapacity.Memory.Allocated = $MEMLimit + $adminVdc.StorageCapacity = New-Object VMware.VimAutomation.Cloud.Views.CapacityWithUsage + $adminVdc.StorageCapacity.Units = "MB" + $adminVdc.StorageCapacity.Limit = $StorageLimit + $adminVdc.NetworkQuota = 10 + $adminVdc.VmQuota = 0 + $adminVdc.VCpuInMhz = 1000 + $adminVdc.VCpuInMhz2 = 1000 + $adminVdc.UsesFastProvisioning = $false + $adminVdc.IsThinProvision = $true + + ## Create Org vDC + Write-Verbose "Create Org vDC" + $OrgED = (Get-Org $Org).ExtensionData + $orgVdc = $orgED.CreateVdc($adminVdc) + + ## Wait for getting Ready + Write-Verbose "Wait for getting Ready" + $i = 0 + while(($orgVdc = Get-OrgVdc -Name $Name).Status -eq "NotReady"){ + $i++ + Start-Sleep 2 + if($i -gt $Timeout) { Write-Error "Creating Org Failed."; break} + Write-Progress -Activity "Creating Org" -Status "Wait for Org to become Ready..." + } + Write-Progress -Activity "Creating Org" -Completed + Start-Sleep 2 + + ## Search given Storage Profile + Write-Verbose "Search given Storage Profile" + $ProVdcStorageProfile = search-cloud -QueryType ProviderVdcStorageProfile -Name $StorageProfile | Get-CIView + + ## Create Storage Profile Object with Settings + Write-Verbose "Create Storage Profile Object with Settings" + $spParams = new-object VMware.VimAutomation.Cloud.Views.VdcStorageProfileParams + $spParams.Limit = $StorageLimit + $spParams.Units = "MB" + $spParams.ProviderVdcStorageProfile = $ProVdcStorageProfile.href + $spParams.Enabled = $true + $spParams.Default = $true + $UpdateParams = new-object VMware.VimAutomation.Cloud.Views.UpdateVdcStorageProfiles + $UpdateParams.AddStorageProfile = $spParams + + ## Update Org vDC + $orgVdc = Get-OrgVdc -Name $name + $orgVdc.ExtensionData.CreateVdcStorageProfile($UpdateParams) + + ## Wait for getting Ready + Write-Verbose "Wait for getting Ready" + while(($orgVdc = Get-OrgVdc -Name $name).Status -eq "NotReady"){ + $i++ + Start-Sleep 1 + if($i -gt $Timeout) { Write-Error "Update Org Failed."; break} + Write-Progress -Activity "Updating Org" -Status "Wait for Org to become Ready..." + } + Write-Progress -Activity "Updating Org" -Completed + Start-Sleep 1 + + ## Search Any-StorageProfile + Write-Verbose "Search Any-StorageProfile" + $orgvDCAnyProfile = search-cloud -querytype AdminOrgVdcStorageProfile | Where-Object {($_.Name -match '\*') -and ($_.VdcName -eq $orgVdc.Name)} | Get-CIView + + ## Disable Any-StorageProfile + Write-Verbose "Disable Any-StorageProfile" + $orgvDCAnyProfile.Enabled = $False + $return = $orgvDCAnyProfile.UpdateServerData() + + ## Remove Any-StorageProfile + Write-Verbose "Remove Any-StorageProfile" + $ProfileUpdateParams = new-object VMware.VimAutomation.Cloud.Views.UpdateVdcStorageProfiles + $ProfileUpdateParams.RemoveStorageProfile = $orgvDCAnyProfile.href + $remove = $orgvdc.extensiondata.CreatevDCStorageProfile($ProfileUpdateParams) + + ## Wait for getting Ready + Write-Verbose "Wait for getting Ready" + while(($orgVdc = Get-OrgVdc -Name $name).Status -eq "NotReady"){ + $i++ + Start-Sleep 1 + if($i -gt $Timeout) { Write-Error "Update Org Failed."; break} + Write-Progress -Activity "Updating Org" -Status "Wait for Org to become Ready..." + } + Write-Progress -Activity "Updating Org" -Completed + Start-Sleep 1 + + ## Set NetworkPool for correct location + Write-Verbose "Set NetworkPool for correct location" + $orgVdc = Get-OrgVdc -Name $name + $ProVdcNetworkPool = Get-NetworkPool -ProviderVdc $ProviderVDC -Name $NetworkPool + $set = Set-OrgVdc -OrgVdc $orgVdc -NetworkPool $ProVdcNetworkPool -NetworkMaxCount "10" + + ## Create private Catalog + Write-Verbose "Create private Catalog Object" + $OrgCatalog = New-Object VMware.VimAutomation.Cloud.Views.AdminCatalog + $OrgCatalog.name = "$Org Private Catalog" + if (!(Get-Org $org | Get-Catalog -Name $OrgCatalog.name -ErrorAction SilentlyContinue)) { + Write-Verbose "Create private Catalog" + $CreateCatalog = (Get-Org $org | Get-CIView).CreateCatalog($OrgCatalog) + $AccessControlRule = New-CIAccessControlRule -Entity $CreateCatalog.name -EveryoneInOrg -AccessLevel ReadWrite -Confirm:$False + } + else { + Write-Output "Catalog '$($OrgCatalog.name)' aleady exists!" + } + + ## Create a direct connect network + if ($ExternalNetwork) { + Write-Verbose "Create a direct connect network" + Write-Output "Org VDC '$Name' needs to be enabled to add an external Network!" + $EnableOrgVdc = Set-OrgVdc -OrgVdc $Name -Enabled:$True + $orgVdcView = Get-OrgVdc $Name | Get-CIView + $extNetwork = $_.externalnetwork + $extNetwork = Get-ExternalNetwork | Get-CIView | Where-Object {$_.name -eq $ExternalNetwork} + $orgNetwork = new-object vmware.vimautomation.cloud.views.orgvdcnetwork + $orgNetwork.name = $ExternalNetwork + $orgNetwork.Configuration = New-Object VMware.VimAutomation.Cloud.Views.NetworkConfiguration + $orgNetwork.Configuration.FenceMode = 'bridged' + $orgNetwork.configuration.ParentNetwork = New-Object vmware.vimautomation.cloud.views.reference + $orgNetwork.configuration.ParentNetwork.href = $extNetwork.href + + $result = $orgVdcView.CreateNetwork($orgNetwork) + } + + Get-OrgVdc -Name $name | Format-Table -AutoSize + } +} diff --git a/Modules/VMware-vCD-Module/media/Invoke-MyOnBoarding.png b/Modules/VMware-vCD-Module/media/Invoke-MyOnBoarding.png new file mode 100644 index 0000000000000000000000000000000000000000..9f60a93508c54e47418fa493ab0b730f8b003a3f GIT binary patch literal 40988 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 %IBM`Y0F&%$%@Mz>h~Xp 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 Y0@TidQEK`NO#t%qyOtiTT*EfvACt(Yp#T5? literal 0 HcmV?d00001 diff --git a/Modules/VMware-vCD-Module/media/VSCode-Pester-Tests.png b/Modules/VMware-vCD-Module/media/VSCode-Pester-Tests.png new file mode 100644 index 0000000000000000000000000000000000000000..2669d07b371a24bdfc72894208ab301fa52d75a6 GIT binary patch literal 80733 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�~x1eXgp4{f}++ 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 XP`J?L89Dp>J>Y{dMVh>XyT$zvC#L89 literal 0 HcmV?d00001 diff --git a/Modules/VMware-vCD-Module/tests/VMware-vCD-Module.Tests.ps1 b/Modules/VMware-vCD-Module/tests/VMware-vCD-Module.Tests.ps1 new file mode 100644 index 0000000..ada710e --- /dev/null +++ b/Modules/VMware-vCD-Module/tests/VMware-vCD-Module.Tests.ps1 @@ -0,0 +1,35 @@ +$moduleRoot = Resolve-Path "$PSScriptRoot\.." +$moduleName = "VMware-vCD-Module" +$ConfigFile = "$moduleRoot\examples\OnBoarding.json" + +Describe "General project validation: $moduleName" { + + $scripts = Get-ChildItem $moduleRoot -Include *.ps1, *.psm1, *.psd1 -Recurse + + # TestCases are splatted to the script so we need hashtables + $testCase = $scripts | Foreach-Object {@{file = $_}} + It "Script should be valid powershell" -TestCases $testCase { + param($file) + + $file.fullname | Should Exist + + $contents = Get-Content -Path $file.fullname -ErrorAction Stop + $errors = $null + $null = [System.Management.Automation.PSParser]::Tokenize($contents, [ref]$errors) + $errors.Count | Should Be 0 + } + + It "Module '$moduleName' prerequirements are met" { + {Import-Module VMware.VimAutomation.Cloud -Force} | Should Not Throw + } + + It "Module '$moduleName' can import cleanly" { + {Import-Module (Join-Path $moduleRoot "$moduleName.psd1") -force } | Should Not Throw + } + + It "Module '$moduleName' JSON example is valid" { + {Get-Content -Raw -Path $ConfigFile | ConvertFrom-Json} | Should Not Throw + } + + +} From 704251045ddafdf2336730b65e8b08c92c2fbd6b Mon Sep 17 00:00:00 2001 From: Matt Frey Date: Tue, 13 Jun 2017 23:13:15 -0500 Subject: [PATCH 3/5] Add Get-HVGlobalSettings and Set-HVGlobalSettings 2 new functions to Get and Set VMware.Hv.GlobalSettingsInfo --- .../Set-HVGlobalSettings.json | 22 + .../VMware.Hv.Helper/VMware.HV.Helper.psm1 | 391 +++++++++++++++++- 2 files changed, 412 insertions(+), 1 deletion(-) create mode 100644 Modules/VMware.Hv.Helper/Set-HVGlobalSettings/Set-HVGlobalSettings.json diff --git a/Modules/VMware.Hv.Helper/Set-HVGlobalSettings/Set-HVGlobalSettings.json b/Modules/VMware.Hv.Helper/Set-HVGlobalSettings/Set-HVGlobalSettings.json new file mode 100644 index 0000000..269d034 --- /dev/null +++ b/Modules/VMware.Hv.Helper/Set-HVGlobalSettings/Set-HVGlobalSettings.json @@ -0,0 +1,22 @@ +{ + "generalData.clientMaxSessionTimePolicy": "TIMEOUT_AFTER", + "generalData.clientMaxSessionTimeMinutes": 600, + "generalData.clientIdleSessionTimeoutPolicy": "NEVER", + "generalData.clientIdleSessionTimeoutMinutes": null, + "generalData.clientSessionTimeoutMinutes": 1200, + "generalData.desktopSSOTimeoutPolicy": "DISABLE_AFTER", + "generalData.desktopSSOTimeoutMinutes": 15, + "generalData.applicationSSOTimeoutPolicy": "ALWAYS_ENABLED", + "generalData.applicationSSOTimeoutMinutes": null, + "generalData.viewAPISessionTimeoutMinutes": 10, + "generalData.preLoginMessage": null, + "generalData.displayWarningBeforeForcedLogoff": true, + "generalData.forcedLogoffTimeoutMinutes": 5, + "generalData.forcedLogoffMessage": "Your desktop is scheduled for an important update and will shut down in 5 minutes. Please save any unsaved work now", + "generalData.enableServerInSingleUserMode": false, + "generalData.storeCALOnBroker": false, + "generalData.storeCALOnClient": false, + "securityData.reauthSecureTunnelAfterInterruption": true, + "securityData.messageSecurityMode": "ENHANCED", + "securityData.enableIPSecForSecurityServerPairing": true +} \ No newline at end of file diff --git a/Modules/VMware.Hv.Helper/VMware.HV.Helper.psm1 b/Modules/VMware.Hv.Helper/VMware.HV.Helper.psm1 index aa7697f..e335ce2 100644 --- a/Modules/VMware.Hv.Helper/VMware.HV.Helper.psm1 +++ b/Modules/VMware.Hv.Helper/VMware.HV.Helper.psm1 @@ -8982,4 +8982,393 @@ Function Remove-HVApplicationIcon { } } -Export-ModuleMember Add-HVDesktop,Add-HVRDSServer,Connect-HVEvent,Disconnect-HVEvent,Get-HVPoolSpec,Get-HVInternalName, Get-HVEvent,Get-HVFarm,Get-HVFarmSummary,Get-HVPool,Get-HVPoolSummary,Get-HVMachine,Get-HVMachineSummary,Get-HVQueryResult,Get-HVQueryFilter,New-HVFarm,New-HVPool,Remove-HVFarm,Remove-HVPool,Set-HVFarm,Set-HVPool,Start-HVFarm,Start-HVPool,New-HVEntitlement,Get-HVEntitlement,Remove-HVEntitlement, Set-HVMachine, New-HVGlobalEntitlement, Remove-HVGlobalEntitlement, Get-HVGlobalEntitlement, Get-HVPodSession, Set-HVApplicationIcon, Remove-HVApplicationIcon +function Get-HVGlobalSettings { +<# +.Synopsis + Gets a list of Global Settings + +.DESCRIPTION + Queries and returns the Global Settings for the pod of the specified HVServer. + +.PARAMETER HvServer + Reference to Horizon View Server to query the virtual machines from. If the value is not passed or null then + first element from global:DefaultHVServers would be considered inplace of hvServer + +.EXAMPLE + Get-HVGlobalSettings + +.OUTPUTS + Returns list of object type VMware.Hv.GlobalSettingsInfo + +.NOTES + Author : Matt Frey. + Author email : mfrey@vmware.com + Version : 1.0 + + ===Tested Against Environment==== + Horizon View Server Version : 7.1 + PowerCLI Version : PowerCLI 6.5.1 + PowerShell Version : 5.0 +#> + + [CmdletBinding( + SupportsShouldProcess = $true, + ConfirmImpact = 'High' + )] + + param( + [Parameter(Mandatory = $false)] + $HvServer = $null + ) + + begin { + $services = Get-ViewAPIService -hvServer $hvServer + + if ($null -eq $services) { + Write-Error "Could not retrieve ViewApi services from connection object" + break + } + } + + process { + + $globalSettings = $services.GlobalSettings.GlobalSettings_Get() + + } + + end { + + Return $globalSettings + + } +} + +function Set-HVGlobalSettings { +<# +.SYNOPSIS + Sets the Global Settings of the Connection Server Pod + +.DESCRIPTION + This cmdlet allows user to set Global Settings by passing key/value pair or by passing specific parameters. Optionally, user can pass a JSON spec file. + +.PARAMETER Key + Property names path separated by . (dot) from the root of global settings spec. + +.PARAMETER Value + Property value corresponds to above key name. + +.PARAMETER HvServer + View API service object of Connect-HVServer cmdlet. + +.PARAMETER Spec + Path of the JSON specification file containing key/value pair. + +.PARAMETER clientMaxSessionTimePolicy + Client max session lifetime policy. + "TIMEOUT_AFTER" Indicates that the client session times out after a configurable session length (in minutes) + "NEVER" Indicates no absolute client session length (sessions only end due to inactivity) + +.PARAMETER clientMaxSessionTimeMinutes + Determines how long a user can keep a session open after logging in to View Connection Server. The value is set in minutes. When a session times out, the session is terminated and the View client is disconnected from the resource. + Default value is 600. + Minimum value is 5. + Maximum value is 600. + This property is required if clientMaxSessionTimePolicy is set to "TIMEOUT_AFTER" + +.PARAMETER clientIdleSessionTimeoutPolicy + Specifies the policy for the maximum time that a that a user can be idle before the broker takes measure to protect the session. + "TIMEOUT_AFTER" Indicates that the user session can be idle for a configurable max time (in minutes) before the broker takes measure to protect the session. + "NEVER" Indicates that the client session is never locked. + +.PARAMETER clientIdleSessionTimeoutMinutes + Determines how long a that a user can be idle before the broker takes measure to protect the session. The value is set in minutes. + Default value is 15 + This property is required if -clientIdleSessionTimeoutPolicy is set to "TIMEOUT_AFTER" + +.PARAMETER clientSessionTimeoutMinutes + Determines the maximum length of time that a Broker session will be kept active if there is no traffic between a client and the Broker. The value is set in minutes. + Default value is 1200 + Minimum value is 5 + +.PARAMETER desktopSSOTimeoutPolicy + The single sign on setting for when a user connects to View Connection Server. + "DISABLE_AFTER" SSO is disabled the specified number of minutes after a user connects to View Connection Server. + "DISABLED" Single sign on is always disabled. + "ALWAYS_ENABLED" Single sign on is always enabled. + +.PARAMETER desktopSSOTimeoutMinutes + SSO is disabled the specified number of minutes after a user connects to View Connection Server. + Minimum value is 1 + Maximum value is 999 + +.PARAMETER applicationSSOTimeoutPolicy + The single sign on timeout policy for application sessions. + "DISABLE_AFTER" SSO is disabled the specified number of minutes after a user connects to View Connection Server. + "DISABLED" Single sign on is always disabled. + "ALWAYS_ENABLED" Single sign on is always enabled. + +.PARAMETER applicationSSOTimeoutMinutes + SSO is disabled the specified number of minutes after a user connects to View Connection Server. + Minimum value is 1 + Maximum value is 999 + +.PARAMETER viewAPISessionTimeoutMinutes + Determines how long (in minutes) an idle View API session continues before the session times out. Setting the View API session timeout to a high number of minutes increases the risk of unauthorized use of View API. Use caution when you allow an idle session to persist a long time. + Default value is 10 + Minimum value is 1 + Maximum value is 4320 + +.PARAMETER preLoginMessage + Displays a disclaimer or another message to View Client users when they log in. No message will be displayed if this is null. + +.PARAMETER displayWarningBeforeForcedLogoff + Displays a warning message when users are forced to log off because a scheduled or immediate update such as a machine-refresh operation is about to start. + $TRUE or $FALSE + +.PARAMETER forcedLogoffMinutes + The number of minutes to wait after the warning is displayed and before logging off the user. + Default value is 5 + Minimum value is 1 + Maximum value is 999999 + This property is required if displayWarningBeforeForcedLogoff is $true + +.PARAMETER forcedLogoffMessage + The warning to be displayed before logging off the user. + +.PARAMETER enableServerInSingleUserMode + Permits certain RDSServer operating systems to be used for non-RDS Desktops. + +.PARAMETER storeCALOnBroker + Used for configuring whether or not to store the RDS Per Device CAL on Broker. + $TRUE or $FALSE + +.PARAMETER storeCALOnClient + Used for configuring whether or not to store the RDS Per Device CAL on client devices. This value can be true only if the storeCALOnBroker is true. + $TRUE or $FALSE + +.PARAMETER reauthSecureTunnelAfterInterruption + Reauthenticate secure tunnel connections after network interruption Determines if user credentials must be reauthenticated after a network interruption when View clients use secure tunnel connections to View resources. When you select this setting, if a secure tunnel connection ends during a session, View Client requires the user to reauthenticate before reconnecting. This setting offers increased security. For example, if a laptop is stolen and moved to a different network, the user cannot automatically gain access to the remote resource because the network connection was temporarily interrupted. When this setting is not selected, the client reconnects to the resource without requiring the user to reauthenticate. This setting has no effect when you use direct connection. + +.PARAMETER messageSecurityMode + Determines if signing and verification of the JMS messages passed between View Manager components takes place. + "DISABLED" Message security mode is disabled. + "MIXED" Message security mode is enabled but not enforced. You can use this mode to detect components in your View environment that predate View Manager 3.0. The log files generated by View Connection Server contain references to these components. + "ENABLED" Message security mode is enabled. Unsigned messages are rejected by View components. Message security mode is enabled by default. Note: View components that predate View Manager 3.0 are not allowed to communicate with other View components. + "ENHANCED" Message Security mode is Enhanced. Message signing and validation is performed based on the current Security Level and desktop Message Security mode. + +.PARAMETER enableIPSecForSecurityServerPairing + Determines whether to use Internet Protocol Security (IPSec) for connections between security servers and View Connection Server instances. By default, secure connections (using IPSec) for security server connections is enabled. + $TRUE or $FALSE + +.EXAMPLE + Set-HVGlobalSettings 'ManualPool' -Spec 'C:\Set-HVGlobalSettings\Set-GlobalSettings.json' + +.EXAMPLE + Set-HVGlobalSettings -Key 'generalData.clientMaxSessionTimePolicy' -Value 'NEVER' + +.EXAMPLE + Set-HVGlobalSettings -clientMaxSessionTimePolicy "TIMEOUT_AFTER" -clientMaxSessionTimeMinutes 1200 + +.OUTPUTS + None + +.NOTES + Author : Matt Frey. + Author email : mfrey@vmware.com + Version : 1.0 + + ===Tested Against Environment==== + Horizon View Server Version : 7.1 + PowerCLI Version : PowerCLI 6.5.1 + PowerShell Version : 5.0 +#> + + [CmdletBinding( + SupportsShouldProcess = $true, + ConfirmImpact = 'High' + )] + + param( + [Parameter(Mandatory = $false)] + [string]$Key, + + [Parameter(Mandatory = $false)] + $Value, + + [Parameter(Mandatory = $false)] + [string]$Spec, + + [Parameter(Mandatory = $false)] + [ValidateSet('TIMEOUT_AFTER','NEVER')] + [string]$clientMaxSessionTimePolicy, + + [Parameter(Mandatory = $false)] + [ValidateRange(5,600)] + [Int]$clientMaxSessionTimeMinutes, + + [Parameter(Mandatory = $false)] + [ValidateSet('TIMEOUT_AFTER','NEVER')] + [string]$clientIdleSessionTimeoutPolicy, + + [Parameter(Mandatory = $false)] + [Int]$clientIdleSessionTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [Int]$clientSessionTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [ValidateSet('DISABLE_AFTER','DISABLED','ALWAYS_ENABLED')] + [string]$desktopSSOTimeoutPolicy, + + [Parameter(Mandatory = $false)] + [ValidateRange(1,999)] + [Int]$desktopSSOTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [ValidateSet('DISABLE_AFTER','DISABLED','ALWAYS_ENABLED')] + [string]$applicationSSOTimeoutPolicy, + + [Parameter(Mandatory = $false)] + [ValidateRange(1,999)] + [Int]$applicationSSOTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [ValidateRange(1,4320)] + [Int]$viewAPISessionTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [string]$preLoginMessage, + + [Parameter(Mandatory = $false)] + [boolean]$displayWarningBeforeForcedLogoff, + + [Parameter(Mandatory = $false)] + [ValidateRange(1,999999)] + [Int]$forcedLogoffTimeoutMinutes, + + [Parameter(Mandatory = $false)] + [string]$forcedLogoffMessage, + + [Parameter(Mandatory = $false)] + [boolean]$enableServerInSingleUserMode, + + [Parameter(Mandatory = $false)] + [boolean]$storeCALOnBroker, + + [Parameter(Mandatory = $false)] + [boolean]$storeCALOnClient, + + [Parameter(Mandatory = $false)] + [boolean]$reauthSecureTunnelAfterInterruption, + + [Parameter(Mandatory = $false)] + [ValidateSet('DISABLED','MIXED','ENABLED','ENHANCED')] + [string]$messageSecurityMode, + + [Parameter(Mandatory = $false)] + [boolean]$enableIPSecForSecurityServerPairing, + + [Parameter(Mandatory = $false)] + $HvServer = $null + ) + + begin { + $services = Get-ViewAPIService -hvServer $hvServer + if ($null -eq $services) { + Write-Error "Could not retrieve ViewApi services from connection object" + break + } + } + + process { + + $updates = @() + if ($key -and $value) { + $updates += Get-MapEntry -key $key -value $value + } elseif ($key -or $value) { + Write-Error "Both key:[$key] and value:[$value] needs to be specified" + } + if ($spec) { + try { + $specObject = Get-JsonObject -specFile $spec + } catch { + Write-Error "Json file exception, $_" + return + } + foreach ($member in ($specObject.PSObject.Members | Where-Object { $_.MemberType -eq 'NoteProperty' })) { + $updates += Get-MapEntry -key $member.name -value $member.value + } + } + if ($clientMaxSessionTimePolicy) { + $updates += Get-MapEntry -key 'generalData.clientMaxSessionTimePolicy' -Value $clientMaxSessionTimePolicy + } + if ($clientMaxSessionTimeMinutes) { + $updates += Get-MapEntry -key 'generalData.clientMaxSessionTimeMinutes' -Value $clientMaxSessionTimeMinutes + } + if ($clientIdleSessionTimeoutPolicy) { + $updates += Get-MapEntry -key 'generalData.clientIdleSessionTimeoutPolicy' -Value $clientIdleSessionTimeoutPolicy + } + if ($clientIdleSessionTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.clientIdleSessionTimeoutMinutes' -Value $clientIdleSessionTimeoutMinutes + } + if ($clientSessionTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.clientSessionTimeoutMinutes' -Value $clientSessionTimeoutMinutes + } + if ($desktopSSOTimeoutPolicy) { + $updates += Get-MapEntry -key 'generalData.desktopSSOTimeoutPolicy' -Value $desktopSSOTimeoutPolicy + } + if ($desktopSSOTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.desktopSSOTimeoutMinutes' -Value $desktopSSOTimeoutMinutes + } + if ($applicationSSOTimeoutPolicy) { + $updates += Get-MapEntry -key 'generalData.applicationSSOTimeoutPolicy' -Value $applicationSSOTimeoutPolicy + } + if ($applicationSSOTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.applicationSSOTimeoutMinutes' -Value $applicationSSOTimeoutMinutes + } + if ($viewAPISessionTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.viewAPISessionTimeoutMinutes' -Value $viewAPISessionTimeoutMinutes + } + if ($preLoginMessage) { + $updates += Get-MapEntry -key 'generalData.preLoginMessage' -Value $preLoginMessage + } + if ($displayWarningBeforeForcedLogoff) { + $updates += Get-MapEntry -key 'generalData.displayWarningBeforeForcedLogoff' -Value $displayWarningBeforeForcedLogoff + } + if ($forcedLogoffTimeoutMinutes) { + $updates += Get-MapEntry -key 'generalData.forcedLogoffTimeoutMinutes' -Value $forcedLogoffTimeoutMinutes + } + if ($forcedLogoffMessage) { + $updates += Get-MapEntry -key 'generalData.forcedLogoffMessage' -Value $forcedLogoffMessage + } + if ($enableServerInSingleUserMode) { + $updates += Get-MapEntry -key 'generalData.enableServerInSingleUserMode' -Value $enableServerInSingleUserMode + } + if ($storeCALOnBroker) { + $updates += Get-MapEntry -key 'generalData.storeCALOnBroker' -Value $storeCALOnBroker + } + if ($storeCALOnClient) { + $updates += Get-MapEntry -key 'generalData.storeCALOnClient' -Value $storeCALOnClient + } + if ($reauthSecureTunnelAfterInterruption) { + $updates += Get-MapEntry -key 'securityData.reauthSecureTunnelAfterInterruption' -Value $reauthSecureTunnelAfterInterruption + } + if ($messageSecurityMode) { + $updates += Get-MapEntry -key 'securityData.messageSecurityMode' -Value $messageSecurityMode + } + if ($enableIPSecForSecurityServerPairing) { + $updates += Get-MapEntry -key 'securityData.enableIPSecForSecurityServerPairing' -Value $enableIPSecForSecurityServerPairing + } + + $global_settings_helper = New-Object VMware.Hv.GlobalSettingsService + + $global_settings_helper.GlobalSettings_Update($services,$updates) + + } + + end { + [System.gc]::collect() + } +} + +Export-ModuleMember Add-HVDesktop,Add-HVRDSServer,Connect-HVEvent,Disconnect-HVEvent,Get-HVPoolSpec,Get-HVInternalName, Get-HVEvent,Get-HVFarm,Get-HVFarmSummary,Get-HVPool,Get-HVPoolSummary,Get-HVMachine,Get-HVMachineSummary,Get-HVQueryResult,Get-HVQueryFilter,New-HVFarm,New-HVPool,Remove-HVFarm,Remove-HVPool,Set-HVFarm,Set-HVPool,Start-HVFarm,Start-HVPool,New-HVEntitlement,Get-HVEntitlement,Remove-HVEntitlement, Set-HVMachine, New-HVGlobalEntitlement, Remove-HVGlobalEntitlement, Get-HVGlobalEntitlement, Get-HVPodSession, Set-HVApplicationIcon, Remove-HVApplicationIcon, Get-HVGlobalSettings, Set-HVGlobalSettings From 6ca366e8c4f46d5e412ed17024e12e9bb7e59a69 Mon Sep 17 00:00:00 2001 From: Ryan Bolger Date: Sat, 24 Jun 2017 23:55:58 -0700 Subject: [PATCH 4/5] bugfixes for issues #96 and #97 --- Modules/Backup-VCSA/Backup-VCSA.psm1 | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Modules/Backup-VCSA/Backup-VCSA.psm1 b/Modules/Backup-VCSA/Backup-VCSA.psm1 index 271a7ff..f5731c0 100644 --- a/Modules/Backup-VCSA/Backup-VCSA.psm1 +++ b/Modules/Backup-VCSA/Backup-VCSA.psm1 @@ -72,7 +72,7 @@ $BackupJob = $BackupAPI.create($CreateSpec) } catch { - Write-Error $Error[0].exception.Message + throw $_.Exception.Message } @@ -84,6 +84,7 @@ start-sleep -seconds 5 } until ($BackupAPI.get("$($BackupJob.ID)").progress -eq 100 -or $BackupAPI.get("$($BackupJob.ID)").state -ne "INPROGRESS") + Write-Progress -Activity "Backing up VCSA" -Completed $BackupAPI.get("$($BackupJob.ID)") | select id, progress, state } Else { From 0beda7c30dc3a53a04d6dc3d7614f3b6f4c8109e Mon Sep 17 00:00:00 2001 From: William Lam Date: Wed, 5 Jul 2017 05:31:22 -0700 Subject: [PATCH 5/5] Adding Module for vSphere Content Library --- Modules/ContentLibrary/ContentLibrary.psm1 | 197 +++++++++++++++++++++ 1 file changed, 197 insertions(+) create mode 100644 Modules/ContentLibrary/ContentLibrary.psm1 diff --git a/Modules/ContentLibrary/ContentLibrary.psm1 b/Modules/ContentLibrary/ContentLibrary.psm1 new file mode 100644 index 0000000..824cb16 --- /dev/null +++ b/Modules/ContentLibrary/ContentLibrary.psm1 @@ -0,0 +1,197 @@ +Function Get-ContentLibrary { +<# + .NOTES + =========================================================================== + Created by: William Lam + Organization: VMware + Blog: www.virtuallyghetto.com + Twitter: @lamw + =========================================================================== + .DESCRIPTION + This function lists all available vSphere Content Libaries + .PARAMETER LibraryName + The name of a vSphere Content Library + .EXAMPLE + Get-ContentLibrary + .EXAMPLE + Get-ContentLibrary -LibraryName Test +#> + param( + [Parameter(Mandatory=$false)][String]$LibraryName + ) + + $contentLibaryService = Get-CisService com.vmware.content.library + $libaryIDs = $contentLibaryService.list() + + $results = @() + foreach($libraryID in $libaryIDs) { + $library = $contentLibaryService.get($libraryId) + + # Use vCenter REST API to retrieve name of Datastore that is backing the Content Library + $datastoreService = Get-CisService com.vmware.vcenter.datastore + $datastore = $datastoreService.get($library.storage_backings.datastore_id) + + if(!$LibraryName) { + $libraryResult = [pscustomobject] @{ + Id = $library.Id; + Name = $library.Name; + Type = $library.Type; + Description = $library.Description; + Datastore = $datastore.name; + CreationTime = $library.Creation_Time; + } + $results+=$libraryResult + } else { + if($LibraryName -eq $library.name) { + $libraryResult = [pscustomobject] @{ + Name = $library.Name; + Id = $library.Id; + Type = $library.Type; + Description = $library.Description; + Datastore = $datastore.name; + CreationTime = $library.Creation_Time; + } + $results+=$libraryResult + } + } + } + $results +} + +Function Get-ContentLibraryItems { +<# + .NOTES + =========================================================================== + Created by: William Lam + Organization: VMware + Blog: www.virtuallyghetto.com + Twitter: @lamw + =========================================================================== + .DESCRIPTION + This function lists all items within a given vSphere Content Library + .PARAMETER LibraryName + The name of a vSphere Content Library + .PARAMETER LibraryItemName + The name of a vSphere Content Library Item + .EXAMPLE + Get-ContentLibraryItems -LibraryName Test + .EXAMPLE + Get-ContentLibraryItems -LibraryName Test -LibraryItemName TinyPhotonVM +#> + param( + [Parameter(Mandatory=$true)][String]$LibraryName, + [Parameter(Mandatory=$false)][String]$LibraryItemName + ) + + $contentLibaryService = Get-CisService com.vmware.content.library + $libaryIDs = $contentLibaryService.list() + + $results = @() + foreach($libraryID in $libaryIDs) { + $library = $contentLibaryService.get($libraryId) + if($library.name -eq $LibraryName) { + $contentLibaryItemService = Get-CisService com.vmware.content.library.item + $itemIds = $contentLibaryItemService.list($libraryID) + + foreach($itemId in $itemIds) { + $item = $contentLibaryItemService.get($itemId) + + if(!$LibraryItemName) { + $itemResult = [pscustomobject] @{ + Name = $item.name; + Id = $item.id; + Description = $item.description; + Size = $item.size + Type = $item.type; + Version = $item.version; + MetadataVersion = $item.metadata_version; + ContentVersion = $item.content_version; + } + $results+=$itemResult + } else { + if($LibraryItemName -eq $item.name) { + $itemResult = [pscustomobject] @{ + Name = $item.name; + Id = $item.id; + Description = $item.description; + Size = $item.size + Type = $item.type; + Version = $item.version; + MetadataVersion = $item.metadata_version; + ContentVersion = $item.content_version; + } + $results+=$itemResult + } + } + } + } + } + $results +} + +Function Get-ContentLibraryItemFiles { +<# + .NOTES + =========================================================================== + Created by: William Lam + Organization: VMware + Blog: www.virtuallyghetto.com + Twitter: @lamw + =========================================================================== + .DESCRIPTION + This function lists all item files within a given vSphere Content Library + .PARAMETER LibraryName + The name of a vSphere Content Library + .PARAMETER LibraryItemName + The name of a vSphere Content Library Item + .EXAMPLE + Get-ContentLibraryItemFiles -LibraryName Test + .EXAMPLE + Get-ContentLibraryItemFiles -LibraryName Test -LibraryItemName TinyPhotonVM +#> + param( + [Parameter(Mandatory=$true)][String]$LibraryName, + [Parameter(Mandatory=$false)][String]$LibraryItemName + ) + + $contentLibaryService = Get-CisService com.vmware.content.library + $libaryIDs = $contentLibaryService.list() + + $results = @() + foreach($libraryID in $libaryIDs) { + $library = $contentLibaryService.get($libraryId) + if($library.name -eq $LibraryName) { + $contentLibaryItemService = Get-CisService com.vmware.content.library.item + $itemIds = $contentLibaryItemService.list($libraryID) + + foreach($itemId in $itemIds) { + $itemName = ($contentLibaryItemService.get($itemId)).name + $contenLibraryItemFileSerice = Get-CisService com.vmware.content.library.item.file + $files = $contenLibraryItemFileSerice.list($itemId) + + foreach($file in $files) { + if(!$LibraryItemName) { + $fileResult = [pscustomobject] @{ + Name = $file.name; + Version = $file.version; + Size = $file.size; + Stored = $file.cached; + } + $results+=$fileResult + } else { + if($itemName -eq $LibraryItemName) { + $fileResult = [pscustomobject] @{ + Name = $file.name; + Version = $file.version; + Size = $file.size; + Stored = $file.cached; + } + $results+=$fileResult + } + } + } + } + } + } + $results +} \ No newline at end of file