Framework/Models/SVT/PSCloudService.ps1

#
# CloudService.ps1
#
Set-StrictMode -Version Latest 
class PSCloudService
{
    [PSObject] $CloudServiceName
    [PSObject] $CloudServiceRGName    
    [DeploymentSlot[]] $DeploymentSlots    
    [PSObject] $VirtualIps
    [PSObject] $UpgradeType
    [PSObject] $UpgradeDomainCount
    [Extension[]] $Extensions
    [string] $CloudServiceResourceType = "Microsoft.ClassicCompute/domainNames"
    [string] $CloudServiceAPIVersion = "2016-04-01"

    PSCloudService([string] $cloudServiceName, [string] $cloudServiceRGName)
    {
        $this.CloudServiceName = $cloudServiceName;
        $this.CloudServiceRGName = $cloudServiceRGName;
    }

    [void] LoadCloudConfiguration()
    {
        $cloudServiceSlots = Get-AzResource -ResourceGroupName $this.CloudServiceRGName `
                                -Name $this.CloudServiceName `
                                -ResourceType "$($this.CloudServiceResourceType)/slots" `
                                -ApiVersion $this.CloudServiceAPIVersion

        if(($cloudServiceSlots | Measure-Object).Count -gt 0)
        {
            $this.DeploymentSlots = @();            
            $cloudServiceSlots | ForEach-Object {
                $cloudSlot = $_;
                $DeploymentSlot    = [DeploymentSlot]::new();
                $DeploymentSlot.SlotName = $cloudSlot.Name;
                if(([Helpers]::CheckMember($cloudSlot,"Properties")) -and ([Helpers]::CheckMember($cloudSlot.Properties,"configuration")))
                {
                    $DeploymentSlot.CloudCSCFG = [xml]$cloudSlot.Properties.configuration

                    if($null -ne $DeploymentSlot.CloudCSCFG.ServiceConfiguration)                        
                    {
                        $DeploymentSlot.IsOSAutoUpdateTurnedOn = $false;
                        if($null -ne $DeploymentSlot.CloudCSCFG.ServiceConfiguration.Attributes["osVersion"] -and $DeploymentSlot.CloudCSCFG.ServiceConfiguration.Attributes["osVersion"].value -eq "*")
                        {
                            $DeploymentSlot.IsOSAutoUpdateTurnedOn = $true;
                        }                        
                    }
                }
                
                if(([Helpers]::CheckMember($cloudSlot,"Properties")) -and ([Helpers]::CheckMember($cloudSlot.Properties,"slotType")))
                {
                    $DeploymentSlot.SlotType = $cloudSlot.Properties.slotType
                }

                #get roles
                $cloudServiceRoles = Get-AzResource -ResourceGroupName $this.CloudServiceRGName `
                                        -Name "$($this.CloudServiceName)/$($DeploymentSlot.SlotName)" `
                                        -ResourceType "$($this.CloudServiceResourceType)/slots/roles" `
                                        -ApiVersion $this.CloudServiceAPIVersion
    
                if(($cloudServiceRoles | Measure-Object).Count -gt 0)
                {
                    $DeploymentSlot.Roles = @();
                    $cloudServiceRoles | ForEach-Object{
                        $cloudRole = $_;
                        $Role = [Role]::new();
                        $Role.RoleName = $cloudRole.Name
                        if([Helpers]::CheckMember($cloudRole,"Properties"))
                        {
                            $Role.OSVersion = $cloudRole.Properties.osVersion    
                            $cloudRoleProps = $cloudRole.Properties;
                            if([Helpers]::CheckMember($cloudRoleProps,"inputEndpoints") -and ($cloudRoleProps.inputEndpoints | Measure-Object).Count -gt 0)
                            {
                                $Role.InputEndpoints = @();                                
                                $cloudRole.Properties.inputEndpoints | ForEach-Object{
                                    $roleInputEP = $_
                                    $InputEndPoint = [InputEndpoint]::new();
                                    if([Helpers]::CheckMember($roleInputEP,"publicIpAddress"))
                                    {
                                        $InputEndPoint.PublicIPAddress = $roleInputEP.publicIpAddress;
                                    }
                                    $InputEndPoint.Protocol = $roleInputEP.protocol;
                                    $InputEndPoint.PrivatePort = $roleInputEP.privatePort;
                                    $InputEndPoint.PublicPort = $roleInputEP.publicPort;
                                    if([Helpers]::CheckMember($roleInputEP,"virtualIpName"))
                                    {
                                        $InputEndPoint.VirtualIPName = $roleInputEP.virtualIpName;
                                    }
                                    $Role.InputEndpoints += $InputEndPoint;
                                }
                            }                            
                        }
                        $Role.IsRemoteAccessEnabled = $false;
                        $Role.IsRemoteForwarderEnabled = $false;
                        if($null-ne $DeploymentSlot.CloudCSCFG `
                            -and $null -ne $DeploymentSlot.CloudCSCFG.ServiceConfiguration `
                            -and $null -ne $DeploymentSlot.CloudCSCFG.ServiceConfiguration.Role)
                        {
                            foreach($configRole in $DeploymentSlot.CloudCSCFG.ServiceConfiguration.Role)
                            {
                                if($configRole.name -eq $Role.RoleName)
                                {
                                    if([Helpers]::CheckMember($configRole,"ConfigurationSettings") -and $null -ne $configRole.ConfigurationSettings `
                                        -and [Helpers]::CheckMember($configRole.ConfigurationSettings,"Setting") `
                                        -and $null -ne $configRole.ConfigurationSettings.Setting)
                                        {
                                            foreach ($setting in $configRole.ConfigurationSettings.Setting)
                                            {
                                                if($setting.name -eq "Microsoft.WindowsAzure.Plugins.RemoteAccess.Enabled" -and $setting.value -eq "true")
                                                {
                                                    $Role.IsRemoteAccessEnabled = $true;
                                                }
                                                elseif($setting.name -eq "Microsoft.WindowsAzure.Plugins.RemoteForwarder.Enabled" -and $setting.value -eq "true")
                                                {
                                                    $Role.IsRemoteForwarderEnabled = $true;
                                                }
                                            }
                                        }
                                }
                            }
                        }
                        $DeploymentSlot.Roles += $Role;

                    }
                }        
                
                $this.DeploymentSlots += $DeploymentSlot;
            }
        }        
    }

    hidden [void] LoadCloudConfigurationFromClassicConfig([xml] $CloudServiceResponse)
    {                
        # Get the results from the API as XML
        
        if($null -ne $CloudServiceResponse.hostedservice)
        {        
            if([Helpers]::CheckMember($CloudServiceResponse.hostedservice, "Deployments")){
                if([Helpers]::CheckMember($CloudServiceResponse.hostedservice.Deployments , "Deployment")){
                foreach($svc in $CloudServiceResponse.hostedservice.Deployments.Deployment)
                {
                    $DeploymentSlot = $this.DeploymentSlots | Where-Object { $_.SlotName -eq $svc.DeploymentSlot}
                    
                    if($null -ne $svc.RoleInstanceList)
                    {
                        foreach($instance in $svc.RoleInstanceList.RoleInstance)
                        {
                            [RoleInstance] $roleInstance = [RoleInstance]::new()
                            $roleInstance.RoleName = $instance.RoleName
                            $roleInstance.InstanceName = $instance.InstanceName
                            $roleInstance.PowerState = $instance.PowerState
                            if([Helpers]::CheckMember($instance, "IpAddress"))
                            {
                                $roleInstance.IPAddress = $instance.IpAddress
                            }
                            
                            if([Helpers]::CheckMember($instance, "InstanceEndpoints") -and $null -ne $instance.InstanceEndpoints -and $null -ne $instance.InstanceEndpoints.InstanceEndpoint)
                            {
                                $roleInstance.InstanceEndpoints = [array]($instance.InstanceEndpoints.InstanceEndpoint | Select-Object Name, Vip, PublicPort, LocalPort, Protocol)
                            }

                            $Role = $DeploymentSlot.Roles | Where-Object { $_.RoleName -eq $roleInstance.RoleName}
                            if($null -eq $Role.RoleInstances)
                            {
                                $Role.RoleInstances = @()
                            }

                            if([Helpers]::CheckMember($svc, "RoleList"))
                            {
                                $roleFromClassicObj = $svc.RoleList.Role | Where-Object { $_.RoleName -eq $roleInstance.RoleName }
                            
                                if($null -ne $roleFromClassicObj)
                                {
                                    if([Helpers]::CheckMember($roleFromClassicObj, "RoleType"))
                                    {
                                        $Role.RoleType = $roleFromClassicObj.RoleType
                                    }
                                }
                            }
                            
                            $Role.RoleInstances += $roleInstance                
                            
                            if([Helpers]::CheckMember($svc, "VirtualIPs") -and [Helpers]::CheckMember($svc.VirtualIPs, "VirtualIP"))
                            {
                                $Role.VirtualIPs = [array]($svc.VirtualIPs.VirtualIP | Select-Object Address, IsDnsProgrammed)
                            }

                            if([Helpers]::CheckMember($svc, "UpgradeDomainCount"))
                            {
                                $Role.UpgradeDomainCount = $svc.UpgradeDomainCount
                            }

                            # Write-Host `nRole Extensions: -ForegroundColor DarkYellow
                            # Write-Host ------------------

                            $Role.Extensions = @()
                            if(([Helpers]::CheckMember($svc ,"ExtensionConfiguration")) -and ([Helpers]::CheckMember($svc.ExtensionConfiguration,"NamedRoles") ))
                            {
                                foreach($instanceRole in $svc.ExtensionConfiguration.NamedRoles.Role)
                                {
                                    if($instanceRole.RoleName -eq $instance.RoleName)
                                    {
                                        [Extension] $extension = [Extension]::new()
                                        $extension.RoleName = $instanceRole.RoleName            
                                        if($null -ne $instanceRole.Extensions.Extension)
                                        {
                                            $extension.ExtensionId =  ($instanceRole.Extensions.Extension | Select-Object Id ) 
                                        }
                                        $Role.Extensions += $extension
                                    }
                                }
                            }
                        }
                    }

                    
                  }
                }
            }
        }
    }    

}

class RoleInstance
{    
    [PSObject] $RoleName
    [PSObject] $InstanceName
    [PSObject] $PowerState
    [PSObject] $IPAddress
    [PSObject] $InstanceEndpoints
}

class Role
{
    [string] $RoleName
    [string] $OSVersion
    [string] $RoleType
    [InputEndpoint[]] $InputEndpoints
    [RoleInstance[]] $RoleInstances
    [bool] $IsRemoteForwarderEnabled
    [bool] $IsRemoteAccessEnabled
    [PSObject] $VirtualIPs
    [PSObject] $UpgradeDomainCount
    [Extension[]] $Extensions
}

class InputEndpoint
{
    [string] $PublicIPAddress
    [string] $PrivatePort
    [string] $PublicPort
    [string] $Protocol
    [string] $VirtualIPName
}

class Extension
{
    [PSObject] $RoleName
    [PSObject] $ExtensionId
}

class DeploymentSlot
{
    [string] $SlotName
    [PSObject] $CloudCSCFG 
    [Role[]] $Roles
    [bool] $IsOSAutoUpdateTurnedOn
    [string] $SlotType
}
# SIG # Begin signature block
# MIIjjAYJKoZIhvcNAQcCoIIjfTCCI3kCAQExDzANBglghkgBZQMEAgEFADB5Bgor
# BgEEAYI3AgEEoGswaTA0BgorBgEEAYI3AgEeMCYCAwEAAAQQH8w7YFlLCE63JNLG
# KX7zUQIBAAIBAAIBAAIBAAIBADAxMA0GCWCGSAFlAwQCAQUABCDGDsKLJewq7G4t
# V7BCq9xyftmoNV/Q3HwYsxZGy61qGaCCDYUwggYDMIID66ADAgECAhMzAAAB4HFz
# JMpcmPgZAAAAAAHgMA0GCSqGSIb3DQEBCwUAMH4xCzAJBgNVBAYTAlVTMRMwEQYD
# VQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNy
# b3NvZnQgQ29ycG9yYXRpb24xKDAmBgNVBAMTH01pY3Jvc29mdCBDb2RlIFNpZ25p
# bmcgUENBIDIwMTEwHhcNMjAxMjE1MjEzMTQ2WhcNMjExMjAyMjEzMTQ2WjB0MQsw
# CQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9u
# ZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMR4wHAYDVQQDExVNaWNy
# b3NvZnQgQ29ycG9yYXRpb24wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB
# AQDRXpc9eiGRI/2BlmU7OMiQPTKpNlluodjT2rltPO/Gk47bH4gBShPMD4BX/4sg
# NvvBun6ZOG2dxUW30myWoUJJ0iRbTAv2JFzjSpVQvPE+D5vtmdu6WlOR2ahF4leF
# 5Vvk4lPg2ZFrqg5LNwT9gjwuYgmih+G2KwT8NMWusBhO649F4Ku6B6QgA+vZld5S
# G2XWIdvS0pmpmn/HFrV4eYTsl9HYgjn/bPsAlfWolLlEXYTaCljK7q7bQHDBrzlR
# ukyyryFpPOR9Wx1cxFJ6KBqg2jlJpzxjN3udNJPOqarnQIVgB8DUm3I5g2v5xTHK
# Ovz9ucN21467cYcIxjPC4UkDAgMBAAGjggGCMIIBfjAfBgNVHSUEGDAWBgorBgEE
# AYI3TAgBBggrBgEFBQcDAzAdBgNVHQ4EFgQUVBWIZHrG4UIX3uX4142l+8GsPXAw
# VAYDVR0RBE0wS6RJMEcxLTArBgNVBAsTJE1pY3Jvc29mdCBJcmVsYW5kIE9wZXJh
# dGlvbnMgTGltaXRlZDEWMBQGA1UEBRMNMjMwMDEyKzQ2MzAxMDAfBgNVHSMEGDAW
# gBRIbmTlUAXTgqoXNzcitW2oynUClTBUBgNVHR8ETTBLMEmgR6BFhkNodHRwOi8v
# d3d3Lm1pY3Jvc29mdC5jb20vcGtpb3BzL2NybC9NaWNDb2RTaWdQQ0EyMDExXzIw
# MTEtMDctMDguY3JsMGEGCCsGAQUFBwEBBFUwUzBRBggrBgEFBQcwAoZFaHR0cDov
# L3d3dy5taWNyb3NvZnQuY29tL3BraW9wcy9jZXJ0cy9NaWNDb2RTaWdQQ0EyMDEx
# XzIwMTEtMDctMDguY3J0MAwGA1UdEwEB/wQCMAAwDQYJKoZIhvcNAQELBQADggIB
# AE5msNzmYzYbNgpnhya6YsrM+CIC8CXDu10nwzZtkgQciPOOqAYmFcWJCwD5VZzs
# qFwad8XIOrfCylWf4hzn09mD87yuazpuCstLSqfDLNd3740+254vEZqdGxOglAGU
# ih2IiF8S0GDwucpLGzt/OLXPFr/d4MWxPuX0L+HB5lA3Y/CJE673dHGQW2DELdqt
# ohtkhp+oWFn1hNDDZ3LP++HEZvA7sI/o/981Sh4kaGayOp6oEiQuGeCXyfrIC9KX
# eew0UlYX/NHVDqr4ykKkqpHtzbUbuo7qovUHPbYKcRGWrrEtBS5SPLFPumqsRtzb
# LgU9HqfRAN36bMsd2qynGyWBVFOM7NMs2lTCGM85Z/Fdzv/8tnYT36Cmbue+IM+6
# kS86j6Ztmx0VIFWbOvNsASPT6yrmYiecJiP6H0TrYXQK5B3jE8s53l+t61ab0Eul
# 7DAxNWX3lAiUlzKs3qZYQEK1LFvgbdTXtBRnHgBdABALK3RPrieIYqPln9sAmg3/
# zJZi4C/c2cWGF6WwK/w1Nzw08pj7jaaZZVBpCeDe+y7oM26QIXxracot7zJ21/TL
# 70biK36YybSUDkjhQPP/uxT0yebLNBKk7g8V98Wna2MsHWwk0sgqpkjIp02TrkVz
# 26tcF2rml2THRSDrwpBa4x9c8rM8Qomiyeh2tEJnsx2LMIIHejCCBWKgAwIBAgIK
# YQ6Q0gAAAAAAAzANBgkqhkiG9w0BAQsFADCBiDELMAkGA1UEBhMCVVMxEzARBgNV
# BAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jv
# c29mdCBDb3Jwb3JhdGlvbjEyMDAGA1UEAxMpTWljcm9zb2Z0IFJvb3QgQ2VydGlm
# aWNhdGUgQXV0aG9yaXR5IDIwMTEwHhcNMTEwNzA4MjA1OTA5WhcNMjYwNzA4MjEw
# OTA5WjB+MQswCQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UE
# BxMHUmVkbW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSgwJgYD
# VQQDEx9NaWNyb3NvZnQgQ29kZSBTaWduaW5nIFBDQSAyMDExMIICIjANBgkqhkiG
# 9w0BAQEFAAOCAg8AMIICCgKCAgEAq/D6chAcLq3YbqqCEE00uvK2WCGfQhsqa+la
# UKq4BjgaBEm6f8MMHt03a8YS2AvwOMKZBrDIOdUBFDFC04kNeWSHfpRgJGyvnkmc
# 6Whe0t+bU7IKLMOv2akrrnoJr9eWWcpgGgXpZnboMlImEi/nqwhQz7NEt13YxC4D
# dato88tt8zpcoRb0RrrgOGSsbmQ1eKagYw8t00CT+OPeBw3VXHmlSSnnDb6gE3e+
# lD3v++MrWhAfTVYoonpy4BI6t0le2O3tQ5GD2Xuye4Yb2T6xjF3oiU+EGvKhL1nk
# kDstrjNYxbc+/jLTswM9sbKvkjh+0p2ALPVOVpEhNSXDOW5kf1O6nA+tGSOEy/S6
# A4aN91/w0FK/jJSHvMAhdCVfGCi2zCcoOCWYOUo2z3yxkq4cI6epZuxhH2rhKEmd
# X4jiJV3TIUs+UsS1Vz8kA/DRelsv1SPjcF0PUUZ3s/gA4bysAoJf28AVs70b1FVL
# 5zmhD+kjSbwYuER8ReTBw3J64HLnJN+/RpnF78IcV9uDjexNSTCnq47f7Fufr/zd
# sGbiwZeBe+3W7UvnSSmnEyimp31ngOaKYnhfsi+E11ecXL93KCjx7W3DKI8sj0A3
# T8HhhUSJxAlMxdSlQy90lfdu+HggWCwTXWCVmj5PM4TasIgX3p5O9JawvEagbJjS
# 4NaIjAsCAwEAAaOCAe0wggHpMBAGCSsGAQQBgjcVAQQDAgEAMB0GA1UdDgQWBBRI
# bmTlUAXTgqoXNzcitW2oynUClTAZBgkrBgEEAYI3FAIEDB4KAFMAdQBiAEMAQTAL
# BgNVHQ8EBAMCAYYwDwYDVR0TAQH/BAUwAwEB/zAfBgNVHSMEGDAWgBRyLToCMZBD
# uRQFTuHqp8cx0SOJNDBaBgNVHR8EUzBRME+gTaBLhklodHRwOi8vY3JsLm1pY3Jv
# c29mdC5jb20vcGtpL2NybC9wcm9kdWN0cy9NaWNSb29DZXJBdXQyMDExXzIwMTFf
# MDNfMjIuY3JsMF4GCCsGAQUFBwEBBFIwUDBOBggrBgEFBQcwAoZCaHR0cDovL3d3
# dy5taWNyb3NvZnQuY29tL3BraS9jZXJ0cy9NaWNSb29DZXJBdXQyMDExXzIwMTFf
# MDNfMjIuY3J0MIGfBgNVHSAEgZcwgZQwgZEGCSsGAQQBgjcuAzCBgzA/BggrBgEF
# BQcCARYzaHR0cDovL3d3dy5taWNyb3NvZnQuY29tL3BraW9wcy9kb2NzL3ByaW1h
# cnljcHMuaHRtMEAGCCsGAQUFBwICMDQeMiAdAEwAZQBnAGEAbABfAHAAbwBsAGkA
# YwB5AF8AcwB0AGEAdABlAG0AZQBuAHQALiAdMA0GCSqGSIb3DQEBCwUAA4ICAQBn
# 8oalmOBUeRou09h0ZyKbC5YR4WOSmUKWfdJ5DJDBZV8uLD74w3LRbYP+vj/oCso7
# v0epo/Np22O/IjWll11lhJB9i0ZQVdgMknzSGksc8zxCi1LQsP1r4z4HLimb5j0b
# pdS1HXeUOeLpZMlEPXh6I/MTfaaQdION9MsmAkYqwooQu6SpBQyb7Wj6aC6VoCo/
# KmtYSWMfCWluWpiW5IP0wI/zRive/DvQvTXvbiWu5a8n7dDd8w6vmSiXmE0OPQvy
# CInWH8MyGOLwxS3OW560STkKxgrCxq2u5bLZ2xWIUUVYODJxJxp/sfQn+N4sOiBp
# mLJZiWhub6e3dMNABQamASooPoI/E01mC8CzTfXhj38cbxV9Rad25UAqZaPDXVJi
# hsMdYzaXht/a8/jyFqGaJ+HNpZfQ7l1jQeNbB5yHPgZ3BtEGsXUfFL5hYbXw3MYb
# BL7fQccOKO7eZS/sl/ahXJbYANahRr1Z85elCUtIEJmAH9AAKcWxm6U/RXceNcbS
# oqKfenoi+kiVH6v7RyOA9Z74v2u3S5fi63V4GuzqN5l5GEv/1rMjaHXmr/r8i+sL
# gOppO6/8MO0ETI7f33VtY5E90Z1WTk+/gFcioXgRMiF670EKsT/7qMykXcGhiJtX
# cVZOSEXAQsmbdlsKgEhr/Xmfwb1tbWrJUnMTDXpQzTGCFV0wghVZAgEBMIGVMH4x
# CzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRt
# b25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xKDAmBgNVBAMTH01p
# Y3Jvc29mdCBDb2RlIFNpZ25pbmcgUENBIDIwMTECEzMAAAHgcXMkylyY+BkAAAAA
# AeAwDQYJYIZIAWUDBAIBBQCggbAwGQYJKoZIhvcNAQkDMQwGCisGAQQBgjcCAQQw
# HAYKKwYBBAGCNwIBCzEOMAwGCisGAQQBgjcCARUwLwYJKoZIhvcNAQkEMSIEIJXp
# Lmgbm5n58M6k6INRWn/98CV0H9NojX2hyDrqnVIbMEQGCisGAQQBgjcCAQwxNjA0
# oBSAEgBNAGkAYwByAG8AcwBvAGYAdKEcgBpodHRwczovL3d3dy5taWNyb3NvZnQu
# Y29tIDANBgkqhkiG9w0BAQEFAASCAQB+3usVDuAnfkAD9iGMjTyUoT/x6gEoec5D
# s7tbS5rrVpUMTGpx06/JubaDTQVM1924+YsGqq9Dr5uXPUN3Oy+d/ldMNMQ7ToCd
# bsjOkOT29vQgUrt95YAQwkPdDF8uHWdLoagj3XtkaK7svtlxUyZWRx17M/pCKk5F
# qMmra8Sx4lvIbhkFJdWk8GRa5IJCLw8Pm9UV0RrY2cdJeGMLJZ/oqU0pqknbSUi7
# Y+5uYS2iXNrzcglRl4juyfw8ht3y1VeyeU3/7Lgk/f3hJYZaLpYb0jhZwoUhIjia
# qLkAXZQjAGVJ1jiR02lgC23agMcFzyJC4iVxYL0WFqsWgif5+qoUoYIS5TCCEuEG
# CisGAQQBgjcDAwExghLRMIISzQYJKoZIhvcNAQcCoIISvjCCEroCAQMxDzANBglg
# hkgBZQMEAgEFADCCAVEGCyqGSIb3DQEJEAEEoIIBQASCATwwggE4AgEBBgorBgEE
# AYRZCgMBMDEwDQYJYIZIAWUDBAIBBQAEIC0c6Ryvz20/4ajtBwhWaHWTtj01UWft
# BgYWihxsJ8wqAgZg+Zx280QYEzIwMjEwODE2MDU1MzQzLjMxNFowBIACAfSggdCk
# gc0wgcoxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQH
# EwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xJTAjBgNV
# BAsTHE1pY3Jvc29mdCBBbWVyaWNhIE9wZXJhdGlvbnMxJjAkBgNVBAsTHVRoYWxl
# cyBUU1MgRVNOOjdCRjEtRTNFQS1CODA4MSUwIwYDVQQDExxNaWNyb3NvZnQgVGlt
# ZS1TdGFtcCBTZXJ2aWNloIIOPDCCBPEwggPZoAMCAQICEzMAAAFRw1DnWWyqxqcA
# AAAAAVEwDQYJKoZIhvcNAQELBQAwfDELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldh
# c2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBD
# b3Jwb3JhdGlvbjEmMCQGA1UEAxMdTWljcm9zb2Z0IFRpbWUtU3RhbXAgUENBIDIw
# MTAwHhcNMjAxMTEyMTgyNjA0WhcNMjIwMjExMTgyNjA0WjCByjELMAkGA1UEBhMC
# VVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNV
# BAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjElMCMGA1UECxMcTWljcm9zb2Z0IEFt
# ZXJpY2EgT3BlcmF0aW9uczEmMCQGA1UECxMdVGhhbGVzIFRTUyBFU046N0JGMS1F
# M0VBLUI4MDgxJTAjBgNVBAMTHE1pY3Jvc29mdCBUaW1lLVN0YW1wIFNlcnZpY2Uw
# ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCf0ofvqoSuO+84iSNZsem0
# yRgOOYb4kSbOC7Kv9XGNmBn+KDwyTjuOpIk/lHEf+wPKqFi7uM9I7zqyJmHy7sMF
# f0vwj4AH7x88+8Pi6gsoPbYGmgWXgHwXDkrtK6Ju9vEY3tp0vX/Nb6xZeVW+kOEQ
# 8goMgK8R02MZMuGS19+2N5+D2W6YExQEnYbj+Dhp3R0O9E2YqIxldd78uXhCD+g9
# LNcJQRihJKprkP7kxGKZV7n9hMuPSNWvyIXjlXSFPtUfw4k7hgiZydmGroPDUb7D
# oAJEZ48WY5apby0RnXdIyY6q4mtOTDLLzPI21W20kBft2IUttHRK8yVsllYrQod3
# AgMBAAGjggEbMIIBFzAdBgNVHQ4EFgQUxXf/42hQYpM0aDo4zITp83VE6m0wHwYD
# VR0jBBgwFoAU1WM6XIoxkPNDe3xGG8UzaFqFbVUwVgYDVR0fBE8wTTBLoEmgR4ZF
# aHR0cDovL2NybC5taWNyb3NvZnQuY29tL3BraS9jcmwvcHJvZHVjdHMvTWljVGlt
# U3RhUENBXzIwMTAtMDctMDEuY3JsMFoGCCsGAQUFBwEBBE4wTDBKBggrBgEFBQcw
# AoY+aHR0cDovL3d3dy5taWNyb3NvZnQuY29tL3BraS9jZXJ0cy9NaWNUaW1TdGFQ
# Q0FfMjAxMC0wNy0wMS5jcnQwDAYDVR0TAQH/BAIwADATBgNVHSUEDDAKBggrBgEF
# BQcDCDANBgkqhkiG9w0BAQsFAAOCAQEAK/31wBWDmfHRKqO8t9DOa6AyPlwn00Tr
# R25IfUunEdiKb0uzdR+Jh3u3Qm/ITD+tFMQodvOdXosUuVf76UckwYrNmce1N7Y4
# jpkcWc2IWG2DJa5gMmubspDKQ2LUbUtu5WJ70x6Gagr6EGJmeetx9lKcFKiSu87Z
# ARYcLXGdnnAzzZQSOmsVg6RyFT7pFygKOOYgUZ+BLM2PUwht/iVwnkWhXUyDoXAX
# jkKKM5cdVevOSKwxn2m4OkWOMRXpMBjog2AySEt6/8BWjDSwXwx9DO0kiUVh0USR
# nk0X8jLOgLZhv2LDhsIp0Gt0PcCzqa+gZI2MILqU53PoR6skrc2EWDCCBnEwggRZ
# oAMCAQICCmEJgSoAAAAAAAIwDQYJKoZIhvcNAQELBQAwgYgxCzAJBgNVBAYTAlVT
# MRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQK
# ExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xMjAwBgNVBAMTKU1pY3Jvc29mdCBSb290
# IENlcnRpZmljYXRlIEF1dGhvcml0eSAyMDEwMB4XDTEwMDcwMTIxMzY1NVoXDTI1
# MDcwMTIxNDY1NVowfDELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24x
# EDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlv
# bjEmMCQGA1UEAxMdTWljcm9zb2Z0IFRpbWUtU3RhbXAgUENBIDIwMTAwggEiMA0G
# CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCpHQ28dxGKOiDs/BOX9fp/aZRrdFQQ
# 1aUKAIKF++18aEssX8XD5WHCdrc+Zitb8BVTJwQxH0EbGpUdzgkTjnxhMFmxMEQP
# 8WCIhFRDDNdNuDgIs0Ldk6zWczBXJoKjRQ3Q6vVHgc2/JGAyWGBG8lhHhjKEHnRh
# Z5FfgVSxz5NMksHEpl3RYRNuKMYa+YaAu99h/EbBJx0kZxJyGiGKr0tkiVBisV39
# dx898Fd1rL2KQk1AUdEPnAY+Z3/1ZsADlkR+79BL/W7lmsqxqPJ6Kgox8NpOBpG2
# iAg16HgcsOmZzTznL0S6p/TcZL2kAcEgCZN4zfy8wMlEXV4WnAEFTyJNAgMBAAGj
# ggHmMIIB4jAQBgkrBgEEAYI3FQEEAwIBADAdBgNVHQ4EFgQU1WM6XIoxkPNDe3xG
# G8UzaFqFbVUwGQYJKwYBBAGCNxQCBAweCgBTAHUAYgBDAEEwCwYDVR0PBAQDAgGG
# MA8GA1UdEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAU1fZWy4/oolxiaNE9lJBb186a
# GMQwVgYDVR0fBE8wTTBLoEmgR4ZFaHR0cDovL2NybC5taWNyb3NvZnQuY29tL3Br
# aS9jcmwvcHJvZHVjdHMvTWljUm9vQ2VyQXV0XzIwMTAtMDYtMjMuY3JsMFoGCCsG
# AQUFBwEBBE4wTDBKBggrBgEFBQcwAoY+aHR0cDovL3d3dy5taWNyb3NvZnQuY29t
# L3BraS9jZXJ0cy9NaWNSb29DZXJBdXRfMjAxMC0wNi0yMy5jcnQwgaAGA1UdIAEB
# /wSBlTCBkjCBjwYJKwYBBAGCNy4DMIGBMD0GCCsGAQUFBwIBFjFodHRwOi8vd3d3
# Lm1pY3Jvc29mdC5jb20vUEtJL2RvY3MvQ1BTL2RlZmF1bHQuaHRtMEAGCCsGAQUF
# BwICMDQeMiAdAEwAZQBnAGEAbABfAFAAbwBsAGkAYwB5AF8AUwB0AGEAdABlAG0A
# ZQBuAHQALiAdMA0GCSqGSIb3DQEBCwUAA4ICAQAH5ohRDeLG4Jg/gXEDPZ2joSFv
# s+umzPUxvs8F4qn++ldtGTCzwsVmyWrf9efweL3HqJ4l4/m87WtUVwgrUYJEEvu5
# U4zM9GASinbMQEBBm9xcF/9c+V4XNZgkVkt070IQyK+/f8Z/8jd9Wj8c8pl5SpFS
# AK84Dxf1L3mBZdmptWvkx872ynoAb0swRCQiPM/tA6WWj1kpvLb9BOFwnzJKJ/1V
# ry/+tuWOM7tiX5rbV0Dp8c6ZZpCM/2pif93FSguRJuI57BlKcWOdeyFtw5yjojz6
# f32WapB4pm3S4Zz5Hfw42JT0xqUKloakvZ4argRCg7i1gJsiOCC1JeVk7Pf0v35j
# WSUPei45V3aicaoGig+JFrphpxHLmtgOR5qAxdDNp9DvfYPw4TtxCd9ddJgiCGHa
# sFAeb73x4QDf5zEHpJM692VHeOj4qEir995yfmFrb3epgcunCaw5u+zGy9iCtHLN
# HfS4hQEegPsbiSpUObJb2sgNVZl6h3M7COaYLeqN4DMuEin1wC9UJyH3yKxO2ii4
# sanblrKnQqLJzxlBTeCG+SqaoxFmMNO7dDJL32N79ZmKLxvHIa9Zta7cRDyXUHHX
# odLFVeNp3lfB0d4wwP3M5k37Db9dT+mdHhk4L7zPWAUu7w2gUDXa7wknHNWzfjUe
# CLraNtvTX4/edIhJEqGCAs4wggI3AgEBMIH4oYHQpIHNMIHKMQswCQYDVQQGEwJV
# UzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9uZDEeMBwGA1UE
# ChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSUwIwYDVQQLExxNaWNyb3NvZnQgQW1l
# cmljYSBPcGVyYXRpb25zMSYwJAYDVQQLEx1UaGFsZXMgVFNTIEVTTjo3QkYxLUUz
# RUEtQjgwODElMCMGA1UEAxMcTWljcm9zb2Z0IFRpbWUtU3RhbXAgU2VydmljZaIj
# CgEBMAcGBSsOAwIaAxUAoKKvc/E/pEILJUwlIBWgxXrXI16ggYMwgYCkfjB8MQsw
# CQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9u
# ZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSYwJAYDVQQDEx1NaWNy
# b3NvZnQgVGltZS1TdGFtcCBQQ0EgMjAxMDANBgkqhkiG9w0BAQUFAAIFAOTEZuww
# IhgPMjAyMTA4MTYxMjI0MTJaGA8yMDIxMDgxNzEyMjQxMlowdzA9BgorBgEEAYRZ
# CgQBMS8wLTAKAgUA5MRm7AIBADAKAgEAAgINjQIB/zAHAgEAAgIRRjAKAgUA5MW4
# bAIBADA2BgorBgEEAYRZCgQCMSgwJjAMBgorBgEEAYRZCgMCoAowCAIBAAIDB6Eg
# oQowCAIBAAIDAYagMA0GCSqGSIb3DQEBBQUAA4GBAAOcPMi7mb3pX28GdWJ+Hxo7
# Kw6endNsNGmF0aHSptGkgeUye+3Fzyf4hEdGFJkxs8VURBrL4anFyMsGTpY5VTd9
# jvNxe534Ca38TeLg6bwYO1joPPPDOrMoOHlQiSNl/BmURkpyOTpUiIAgF0byxZux
# F/wskD+S7cBkYtCn2dejMYIDDTCCAwkCAQEwgZMwfDELMAkGA1UEBhMCVVMxEzAR
# BgNVBAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1p
# Y3Jvc29mdCBDb3Jwb3JhdGlvbjEmMCQGA1UEAxMdTWljcm9zb2Z0IFRpbWUtU3Rh
# bXAgUENBIDIwMTACEzMAAAFRw1DnWWyqxqcAAAAAAVEwDQYJYIZIAWUDBAIBBQCg
# ggFKMBoGCSqGSIb3DQEJAzENBgsqhkiG9w0BCRABBDAvBgkqhkiG9w0BCQQxIgQg
# 0BES4tSmokfyEwuzufvIua2uP0FRjKRACl0LCwd23vYwgfoGCyqGSIb3DQEJEAIv
# MYHqMIHnMIHkMIG9BCAuzVyZiPjWwVkHAKYW+/1Jw/m265SHGy/+3QH1cXrlQTCB
# mDCBgKR+MHwxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYD
# VQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xJjAk
# BgNVBAMTHU1pY3Jvc29mdCBUaW1lLVN0YW1wIFBDQSAyMDEwAhMzAAABUcNQ51ls
# qsanAAAAAAFRMCIEILOMpy1baJ49SuxXwSBxdEBR+PCKEaPe5b7+7YkbjAlXMA0G
# CSqGSIb3DQEBCwUABIIBAEgTg1hlzqDVV+2v+UMdaG/yAuq/gcdEoiEEE1VnVQfD
# rQHP/F6mSaD1Vg+qPqETA8tjhA9/PUnYrbcQ0rwyFMq2GREdhiBOJmsQek+XiORO
# e8LgBlpVmCBWsdn5+g+W5rvNACEIx3UHg5U49JmOfxqK/gCcZSTRYZsxIansKqm4
# eBhRMM3bEJlnEbcux+kSper1klfP+i394AIKxzxcP0yURRryOtO3gOL2CiUgfS5a
# 72cVUW0duk3Euox+FTO5dgg5kH075cOQBjL4BDkbEX/SUEwoERS8Qeoh+N4BLgJD
# HUL5A5aXCMu/P56VnHkMPtF7591n7HuPOX1SaI3dYB4=
# SIG # End signature block