DSCResources/ArcGIS_DataStoreBackup/ArcGIS_DataStoreBackup.psm1
function Get-TargetResource { [CmdletBinding()] [OutputType([System.Collections.Hashtable])] param ( [parameter(Mandatory = $True)] [ValidateSet("Relational","TileCache","SpatioTemporal")] [System.String] $DataStoreType, [parameter(Mandatory = $True)] [ValidateSet("fs","s3","azure")] [System.String] $BackupType, [parameter(Mandatory = $True)] [System.String] $BackupName, [parameter(Mandatory = $True)] [System.String] $BackupLocation, [parameter(Mandatory = $False)] [System.Management.Automation.PSCredential] $CloudBackupCredential, [parameter(Mandatory = $False)] [System.Boolean] $IsDefault = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceDefaultRelationalBackupUpdate = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceCloudCredentialsUpdate = $False ) Import-Module $PSScriptRoot\..\..\ArcGISUtility.psm1 -Verbose:$false $null } function Set-TargetResource { [CmdletBinding()] param ( [parameter(Mandatory = $True)] [ValidateSet("Relational","TileCache","SpatioTemporal")] [System.String] $DataStoreType, [parameter(Mandatory = $True)] [ValidateSet("fs","s3","azure")] [System.String] $BackupType, [parameter(Mandatory = $True)] [System.String] $BackupName, [parameter(Mandatory = $True)] [System.String] $BackupLocation, [parameter(Mandatory = $False)] [System.Management.Automation.PSCredential] $CloudBackupCredential, [parameter(Mandatory = $False)] [System.Boolean] $IsDefault = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceDefaultRelationalBackupUpdate = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceCloudCredentialsUpdate = $False ) Import-Module $PSScriptRoot\..\..\ArcGISUtility.psm1 -Verbose:$false [System.Reflection.Assembly]::LoadWithPartialName("System.Web") | Out-Null $ServiceName = 'ArcGIS Data Store' $RegKey = Get-EsriRegistryKeyForService -ServiceName $ServiceName $RegKeyObject = (Get-ItemProperty -Path $RegKey -ErrorAction Ignore) $DataStoreInstallDirectory = $RegKeyObject.InstallDir.TrimEnd('\') $RealVersion = $RegKeyObject.RealVersion Write-Verbose "Version of DataStore is $RealVersion" $VersionArray = $RealVersion.Split('.') if($VersionArray[1] -lt 6){ throw "ArcGIS_DataStoreBackup resource doesn't support ArcGIS DataStore 10.5.1 and below" } $UseDescribeDataStore = (($VersionArray[1] -lt 8) -and ($DataStoreType -eq "TileCache")) -or (($RealVersion -ieq "10.6") -and ($DataStoreType -eq "Relational")) $AllExistingBackupLocations = Get-DataStoreBackupLocation -DataStoreType $DataStoreType -DataStoreInstallDirectory $DataStoreInstallDirectory ` -UseDescibeDatastore:$UseDescribeDataStore $Flag = $False if($DataStoreType -eq "Relational"){ if(($VersionArray[1] -eq 6) -and ($VersionArray[2] -eq 0)){ if($BackupName -ne "DEFAULT"){ throw "Backup for Relational DataStore cannot have a backup name other than 'DEFAULT' at $RealVersion" } if($BackupType -ne "fs"){ throw "Backup for Relational DataStore can only be a local path or shared file location at $RealVersion" } if($AllExistingBackupLocations[0].Location -ine $BackupLocation){ Write-Verbose "Updating default backup location to '$BackupLocation' for $DataStoreType Datastore" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $BackupLocation ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "change" -Verbose } }else{ if($IsDefault){ if($BackupType -ne "fs"){ throw "Default back up for Relational DataStore can only be a local path or shared file location at $RealVersion" } $ExistingBackup = ($AllExistingBackupLocations | Where-Object { $_.IsDefault -ieq $true } | Select-Object -First 1 ) if($ExistingBackup.Location -ine $BackupLocation){ Write-Verbose "Updating default backup location to '$BackupLocation' for $DataStoreType Datastore" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $BackupLocation ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "change" ` -Verbose -ForceUpdate:$ForceDefaultRelationalBackupUpdate } if($ExistingBackup.Name -ne $BackupName){ Write-Verbose "Updating default backup name to '$BackupName' for $DataStoreType Datastore" $ExpectedBackupLocationString = "type=fs;name=$($BackupName);location=$($BackupLocation)" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $ExpectedBackupLocationString ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "change" -Verbose } }else{ $Flag = $true } } }elseif($DataStoreType -eq "TileCache"){ if($VersionArray[1] -lt 8){ if($BackupName -ne "DEFAULT"){ throw "Backup for Tile Cache DataStore cannot have a backup name other than 'DEFAULT' at $RealVersion" } if($BackupType -ne "fs"){ throw "Backup of Tile Cache DataStore to a Cloud Store isn't supported at $RealVersion" } if($AllExistingBackupLocations[0].Location -ine $BackupLocation){ Write-Verbose "Updating default backup location to '$BackupLocation' for $DataStoreType Datastore" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $BackupLocation ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "change" -Verbose } }else{ $Flag = $true } }elseif($DataStoreType -eq "SpatioTemporal"){ $Flag = $true } if($Flag){ $ExpectedBackupLocationString = "type=$($BackupType);name=$($BackupName);location=$($BackupLocation)" if($BackupType -ne "fs"){ $EndpointSuffix = $null $CloudCredentialUserName = $CloudBackupCredential.UserName if($BackupType -ieq "azure"){ $Pos = $CloudBackupCredential.UserName.IndexOf('.blob.') if($Pos -gt -1) { $EndpointSuffix = $CloudCredentialUserName.Substring($Pos + 6) if(($VersionArray[1] -ge 7) -or (($VersionArray[1] -le 6) -and ($EndpointSuffix -ieq "core.windows.net"))){ $CloudCredentialUserName = $CloudCredentialUserName.Substring(0, $Pos) }else{ throw "Error - Backups to Azure Cloud Storage with endpoint suffix $EndpointSuffix is not supported for ArcGIS Enterprise 10.6.1 and below" } } else { throw "Error - Invalid Backup Azure Blob Storage Account" } } $ExpectedBackupLocationString += ";username=$($CloudCredentialUserName);password=$($CloudBackupCredential.GetNetworkCredential().Password)" if($BackupType -ieq "azure" -and ($null -ne $EndpointSuffix) -and ($VersionArray[1] -ge 7)){ $ExpectedBackupLocationString += ";endpointsuffix=$EndpointSuffix" } } $ExistingBackup = ($AllExistingBackupLocations | Where-Object { $_.Location -ieq $BackupLocation } | Select-Object -First 1 ) if($null -ne $ExistingBackup){ Write-Verbose "Backup with location '$BackupLocation' found for $DataStoreType Datastore" $UpdateBackupLocation = $False if(($BackupType -ne "fs") -and $ForceCloudCredentialsUpdate){ Write-Verbose "Forcing Credentials update for backup with location '$BackupLocation' for $DataStoreType Datastore" $UpdateBackupLocation = $true } if($ExistingBackup.Name -ne $BackupName){ Write-Verbose "Forcing backup location name update for backup with location '$BackupLocation' for $DataStoreType Datastore" $UpdateBackupLocation = $true } if($UpdateBackupLocation){ Write-Verbose "Updating Backup with location '$BackupLocation' found for $DataStoreType Datastore" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $ExpectedBackupLocationString ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "change" -Verbose } }else{ Write-Verbose "Registering Backup of type '$BackupType', location '$BackupLocation' and name '$BackupName' for $DataStoreType Datastore " Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString $ExpectedBackupLocationString ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "register" -Verbose } if(($DataStoreType -ne "Relational") -and $IsDefault -and (($null -eq $ExistingBackup) -or (($null -ne $ExistingBackup) -and -not($ExistingBackup.IsDefault)))){ Write-Verbose "Setting backup with location '$BackupLocation' and name '$BackupName' for $DataStoreType Datastore to default" Invoke-DataStoreConfigureBackupLocationTool -BackupLocationString "name=$($BackupName)" ` -DataStoreInstallDirectory $DataStoreInstallDirectory ` -DataStoreType $DataStoreType -OperationType "setdefault" -Verbose } } } function Test-TargetResource { [CmdletBinding()] [OutputType([System.Boolean])] param ( [parameter(Mandatory = $True)] [ValidateSet("Relational","TileCache","SpatioTemporal")] [System.String] $DataStoreType, [parameter(Mandatory = $True)] [ValidateSet("fs","s3","azure")] [System.String] $BackupType, [parameter(Mandatory = $True)] [System.String] $BackupName, [parameter(Mandatory = $True)] [System.String] $BackupLocation, [parameter(Mandatory = $False)] [System.Management.Automation.PSCredential] $CloudBackupCredential, [parameter(Mandatory = $False)] [System.Boolean] $IsDefault = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceDefaultRelationalBackupUpdate = $False, [parameter(Mandatory = $False)] [System.Boolean] $ForceCloudCredentialsUpdate = $False ) Import-Module $PSScriptRoot\..\..\ArcGISUtility.psm1 -Verbose:$false [System.Reflection.Assembly]::LoadWithPartialName("System.Web") | Out-Null $result = $true $ServiceName = 'ArcGIS Data Store' $RegKey = Get-EsriRegistryKeyForService -ServiceName $ServiceName $RegKeyObject = (Get-ItemProperty -Path $RegKey -ErrorAction Ignore) $DataStoreInstallDirectory = $RegKeyObject.InstallDir.TrimEnd('\') $RealVersion = $RegKeyObject.RealVersion Write-Verbose "Version of DataStore is $RealVersion" $VersionArray = $RealVersion.Split('.') if($VersionArray[1] -lt 6){ throw "ArcGIS_DataStoreBackup resource doesn't support ArcGIS DataStore 10.5.1 and below" } $UseDescribeDataStore = (($VersionArray[1] -lt 8) -and ($DataStoreType -eq "TileCache")) -or ($RealVersion -ieq "10.6" -and ($DataStoreType -eq "Relational")) $AllExistingBackupLocations = Get-DataStoreBackupLocation -DataStoreType $DataStoreType -DataStoreInstallDirectory $DataStoreInstallDirectory ` -UseDescibeDatastore:$UseDescribeDataStore if($DataStoreType -eq "Relational"){ if(($VersionArray[1] -eq 6) -and ($VersionArray[2] -eq 0)){ if($BackupName -ne "DEFAULT"){ throw "Backup for Relational DataStore cannot have a backup name other than 'DEFAULT' at $RealVersion" } if($BackupType -ne "fs"){ throw "Backup for Relational DataStore can only be a local path or shared file location at $RealVersion" } if($AllExistingBackupLocations[0].Location -ine $BackupLocation){ Write-Verbose "Current Default backup location $($ExistingBackup.Location) doesn't match '$BackupLocation' for $DataStoreType Datastore" $result = $False } }else{ if($IsDefault){ if($BackupType -ne "fs"){ throw "Default back up for Relational DataStore can only be a local path or shared file location at $RealVersion" } $ExistingBackup = ($AllExistingBackupLocations | Where-Object { $_.IsDefault -ieq $true } | Select-Object -First 1 ) if($ExistingBackup.Location -ine $BackupLocation){ Write-Verbose "Current Default backup location $($ExistingBackup.Location) doesn't match '$BackupLocation' for $DataStoreType Datastore" $result = $False } if($result -and $ExistingBackup.Name -ne $BackupName){ Write-Verbose "Current Default backup name $($ExistingBackup.Name) doesn't match '$BackupName' for $DataStoreType Datastore" $result = $False } }else{ $Flag = $true } } }elseif($DataStoreType -eq "TileCache"){ if($VersionArray[1] -lt 8){ if($BackupName -ne "DEFAULT"){ throw "Backup for Tile Cache DataStore cannot have a backup name other than 'DEFAULT' at $RealVersion" } if($BackupType -ne "fs"){ throw "Backup of Tile Cache DataStore to a Cloud Store isn't supported at $RealVersion" } if($AllExistingBackupLocations[0].Location -ine $BackupLocation){ Write-Verbose "Current Default backup location $($ExistingBackup.Location) doesn't match '$BackupLocation' for $DataStoreType Datastore" $result = $False } }else{ $Flag = $true } }elseif($DataStoreType -eq "SpatioTemporal"){ $Flag = $true } if($result -and $Flag){ $ExistingBackup = ($AllExistingBackupLocations | Where-Object { $_.Location -ieq $BackupLocation } | Select-Object -First 1 ) if($null -ne $ExistingBackup){ Write-Verbose "Backup with location '$BackupLocation' found for $DataStoreType Datastore" if($BackupType -ne "fs"){ $EndpointSuffix = $null $CloudCredentialUserName = $CloudBackupCredential.UserName if($BackupType -ieq "azure"){ Write-Verbose "Validating Azure Cloud Storage account Name" $Pos = $CloudBackupCredential.UserName.IndexOf('.blob.') if($Pos -gt -1) { $EndpointSuffix = $CloudCredentialUserName.Substring($Pos + 6) if(-not(($VersionArray[1] -ge 7) -or (($VersionArray[1] -le 6) -and ($EndpointSuffix -eq "core.windows.net")))){ throw "Error - Backups to Azure Cloud Storage with endpoint suffix $EndpointSuffix is not supported for ArcGIS Enterprise 10.6.1 and below" } } else { throw "Error - Invalid Backup Azure Blob Storage Account" } } if($ForceCloudCredentialsUpdate){ Write-Verbose "Backup cloud credential with location '$BackupLocation' and name '$BackupName' don't match for $DataStoreType Datastore" $result = $False } } if( $result -and $ExistingBackup.Name -ne $BackupName){ Write-Verbose "Current backup location $($ExistingBackup.Name) doesn't match '$BackupName' for $DataStoreType Datastore" $result = $False } }else{ Write-Verbose "No Backup of type '$BackupType', location '$BackupLocation' and name '$BackupName' found for $DataStoreType Datastore" $result = $False } if($result -and ($DataStoreType -ne "Relational") -and $IsDefault -and (($null -eq $ExistingBackup) -or (($null -ne $ExistingBackup) -and -not($ExistingBackup.IsDefault)))){ Write-Verbose "Backup of type '$BackupType', location '$BackupLocation' and name '$BackupName' isn't default backup for $DataStoreType Datastore" $result = $False } } $result } Export-ModuleMember -Function *-TargetResource |