This commit is contained in:
Chris Kuech 2018-01-15 15:27:13 -08:00
Родитель 3e9c21c6b8
Коммит 25161f037d
6 изменённых файлов: 366 добавлений и 8 удалений

Двоичные данные
AzureBakery/AzureBakery.psd1

Двоичный файл не отображается.

Просмотреть файл

@ -2,6 +2,6 @@
Simple module for producing production-ready VM images. Standard Windows Server images require Windows Update to be run and often do not contain desired Windows Features fully installed--this can prolong scale outs and complcate initialization scripts. The `New-BakedImage` cmdlet will create a VHD in blob storage containing all the specified Windows Features fully installed (and rebooted if necessary), as well as installed with the latest Windows Updates.
`New-BakedImage` complements the existing Azure Resource Manager API. The returned VHD blob URL can be passed into a correctly configured ARM template to create a managed disk from the generalized VHD. `New-BakedImage` explicitly uses VHD blobs, as VHD blobs can be copied across regions (managed disks cannot), and can be turned into managed disks at their destination region within an ARM template or using PowerShell.
`New-BakedImage` complements the existing Azure Resource Manager API. The returned VHD blob URL can be passed into a correctly configured ARM template to create a managed disk from the generalized VHD. `New-BakedImage` explicitly uses VHD blobs (as opposed to Managed Images), as VHD blobs can be copied across regions (Managed Images cannot), and can be turned into Managed Images at their destination region within an ARM template or using PowerShell.
Install from PowerShell Gallery with `Install-Module AzureBakery`. Run `help New-BakedImage` for usage information.

Двоичные данные
Cluster.psd1

Двоичный файл не отображается.

Просмотреть файл

@ -10,7 +10,25 @@ $InformationPreference = "Continue"
# New cluster set
#>
function New-ClusterService {
<#
.SYNOPSIS
Creates a new Service in Azure and returns the associated ClusterService object
.DESCRIPTION
Creates a new Service in Azure and returns the associated ClusterService object
.PARAMETER Name
Name of the Service
.EXAMPLE
New-ClusterService -Name "MyService"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -25,6 +43,33 @@ function New-ClusterService {
function New-ClusterFlightingRing {
<#
.SYNOPSIS
Creates a new Flighting Ring in Azure and returns the associated ClusterFlightingRing object
.DESCRIPTION
Creates a new Flighting Ring in Azure and returns the associated ClusterFlightingRing object
.PARAMETER ServiceName
Name of the Service containg the Flighting Ring
.PARAMETER Service
ClusterService object of the Service containing the Flighting Ring
.PARAMETER Name
Name of the Flighting Ring
.EXAMPLE
# create "MyService-DEV" using names
New-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
# create "MyService-DEV" using management objects
$service = Get-ClusterService -Name "MyService"
New-ClusterFlightingRing -Service $service -Name "DEV"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -50,6 +95,36 @@ function New-ClusterFlightingRing {
function New-ClusterEnvironment {
<#
.SYNOPSIS
Creates a new Environment in Azure and returns the associated ClusterEnvironment object
.DESCRIPTION
Creates a new Environment in Azure and returns the associated ClusterEnvironment object
.PARAMETER ServiceName
Name of the Service containing the Environment
.PARAMETER FlightingRingName
Name of the Flighting Ring containing the Environment
.PARAMETER FlightingRing
ClusterFlightingRing object of the Flighting Ring containing the Environment
.PARAMETER Region
Name of the Region containing the Environment
.EXAMPLE
# create "MyService-DEV-EastUS" using names
New-ClusterEnvironment -ServiceName "MyService" -FlightingRingName "DEV" -RegionName "EastUS"
# create "MyService-DEV-EastUS" using management objects
$flightingRing = Get-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
New-ClusterEnvironment -FlightingRing $flightingRing -Region "EastUS"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -78,6 +153,42 @@ function New-ClusterEnvironment {
function New-Cluster {
<#
.SYNOPSIS
Creates a new Cluster in Azure and returns the associated Cluster object
.DESCRIPTION
Creates a new Cluster in Azure and returns the associated Cluster object
.PARAMETER ServiceName
Name of the Service containing the Cluster
.PARAMETER FlightingRingName
Name of the Flighting Ring containing the Cluster
.PARAMETER RegionName
Name of the Region containing the Cluster
.PARAMETER Environment
ClusterEnvironment object of the Flighting Ring containing the Cluster
.PARAMETER DefinitionsContainer
Path to the folder containing all the configuration definitions
.PARAMETER Expiry
Date when the configuration can no longer be read from Azure without redeploying
.EXAMPLE
# create cluster child of "MyService-DEV-EastUS" using names
New-Cluster -ServiceName "MyService" -FlightingRingName "DEV" -RegionName "EastUS"
# create "MyService-DEV-EastUS" using management objects
$environment = Get-ClusterEnvironment -ServiceName "MyService" -FlightingRingName "DEV" -RegionName "EastUS"
New-Cluster -Environment $environment -DefinitionsContainer ".\Definitions" -Expiry (Get-Date).AddDays(14)
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -113,6 +224,22 @@ function New-Cluster {
#>
function Get-ClusterService {
<#
.SYNOPSIS
Gets the ClusterService object
.DESCRIPTION
Gets the ClusterService object
.PARAMETER Name
Name of the Service
.EXAMPLE
$service = Get-ClusterService -Name "MyService"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[Alias('ServiceName')]
@ -124,6 +251,28 @@ function Get-ClusterService {
function Get-ClusterFlightingRing {
<#
.SYNOPSIS
Gets the ClusterFlightingRing object
.DESCRIPTION
Gets the ClusterFlightingRing object
.PARAMETER ServiceName
Name of the Service containing the Flighting Ring
.PARAMETER Service
ClusterService object of the Service containing the Flighting Ring
.PARAMETER Name
Name of the Flighting Ring
.EXAMPLE
$flightingRing = Get-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -146,6 +295,31 @@ function Get-ClusterFlightingRing {
function Get-ClusterEnvironment {
<#
.SYNOPSIS
Gets the ClusterEnvironment object
.DESCRIPTION
Gets the ClusterEnvironment object
.PARAMETER ServiceName
Name of the Service containing the Environment
.PARAMETER FlightingRingName
Name of the Flighting Ring containing the Environment
.PARAMETER FlightingRing
ClusterFlightingRing object of the Flighting Ring containing the Environment
.PARAMETER Region
Name of the Region containing the Environment
.EXAMPLE
$environment = Get-ClusterEnvironment -ServiceName "MyService" -FlightingRingName "DEV" -RegionName "EastUS"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -171,6 +345,34 @@ function Get-ClusterEnvironment {
function Get-Cluster {
<#
.SYNOPSIS
Gets the Cluster object
.DESCRIPTION
Gets the Cluster object
.PARAMETER ServiceName
Name of the Service containing the Cluster
.PARAMETER FlightingRingName
Name of the Flighting Ring containing the Cluster
.PARAMETER RegionName
Name of the Region containing the Cluster
.PARAMETER Environment
ClusterEnvironment object of the Flighting Ring containing the Cluster
.PARAMETER Index
Index of the Cluster within its Environment
.EXAMPLE
$cluster = Get-Cluster -ServiceName "MyService" -FlightingRingName "DEV" -RegionName "EastUS" -Index 0
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory, ParameterSetName = 'Components')]
[ValidatePattern("^[A-Z][A-z0-9]+$")]
@ -204,6 +406,26 @@ function Get-Cluster {
#>
function Publish-ClusterArtifact {
<#
.SYNOPSIS
Uploads an artifact to the specified ClusterSet
.DESCRIPTION
Uploads the artifact to the specified Cluster set and stores it as its name in the "artifacts" container
.PARAMETER ClusterSet
The Cluster management object representing the subtree of the service that will hold the secret
.PARAMETER Path
Local path to the artifact to be uploaded
.EXAMPLE
$flightingRing = Get-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
Publish-ClusterArtifact -ClusterSet $flightingRing -Path ".\DefinitionsContainer"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
@ -219,6 +441,34 @@ function Publish-ClusterArtifact {
function Publish-ClusterSecret {
<#
.SYNOPSIS
Creates a new secret
.DESCRIPTION
Creates a new Key Vault secret in the specified ClusterSet
.PARAMETER ClusterSet
The Cluster management object representing the subtree of the service that will hold the secret
.PARAMETER Name
Name of the secret
.PARAMETER Value
Value of the secret, represented as a Secure String
.PARAMETER ContentType
MIME type of the secret
.EXAMPLE
$flightingRing = Get-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
$secretName = "MySecret"
$secretValue = Read-Host "Enter value for '$secretName' in this secure prompt" -AsSecureString
Publish-ClusterSecret -ClusterSet $flightingRing -Name $secretName -Value $secretValue
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
@ -241,7 +491,27 @@ function Publish-ClusterSecret {
}
function New-ClusterImage {
function Publish-ClusterImage {
<#
.SYNOPSIS
Creates a new baked image
.DESCRIPTION
Captures a generalized VM image containing the latest Windows Updates and the specified Windows Features
.PARAMETER ClusterSet
The Cluster management object representing the subtree of the service that will hold the image
.PARAMETER WindowsFeature
List of Windows Features to be baked into the custom Windows Image
.EXAMPLE
$flightingRing = Get-ClusterFlightingRing -ServiceName "MyService" -FlightingRingName "DEV"
Publish-ClusterImage -ClusterSet $flightingRing -WindowsFeature "Web-Server", "Web-Asp-Net45", "Telnet-Client"
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
@ -255,6 +525,29 @@ function New-ClusterImage {
function Publish-ClusterConfiguration {
<#
.SYNOPSIS
Pushes a new Resource Manager Template configuration to the Cluster resource group
.DESCRIPTION
Creates a new Azure Resource Manager Template Deployment, which will ensure the Cluster reflects the template and trigger any Desired State Configuration extensions or Custom Script Extensions in the script.
.PARAMETER Cluster
The Cluster(s) that will be updated with their new Configurations
.PARAMETER DefinitionsContainer
Path to the folder containing all the configuration definitions
.PARAMETER Expiry
Date when the configuration can no longer be read from Azure without redeploying
.EXAMPLE
$clusters = Select-Cluster "MyService" "DEV" "EastUS"
Publish-ClusterConfiguration -Cluster $clusters -DefinitionsContainer ".\Definitions" -Expiry (Get-Date).AddDays(14)
.NOTES
Must be logged into Azure
#>
Param(
[Parameter(Mandatory)]
[ValidateNotNullOrEmpty()]
@ -275,6 +568,31 @@ function Publish-ClusterConfiguration {
#>
function Select-Cluster {
<#
.SYNOPSIS
Returns an array of Cluster objects matching the parameters
.DESCRIPTION
Queries the current Azure subscription for
.PARAMETER ServiceName
Name (or glob pattern) of the Service containing the Cluster
.PARAMETER FlightingRingName
Name (or glob pattern) of the Flighting Ring containing the Cluster
.PARAMETER RegionName
Name (or glob pattern) of the Region containing the Cluster
.PARAMETER Index
Index (or glob pattern) of the Cluster
.EXAMPLE
$clusters = Select-Cluster "MyService" "DEV" "EastUS"
.NOTES
Must be logged into Azure
#>
Param(
[Alias('Service')]
[string]$ServiceName = "*",

Просмотреть файл

@ -13,12 +13,12 @@ This module requires PowerShell 5+ and the AzureRM PowerShell module. This modu
### Finding Commands
`Get-Command "*-Cluster*"` will list all cmdlets from this module.
`(Get-Module "Cluster").ExportedCommands` will list all cmdlets from this module.
`Get-Help "<cmdlet>"` will get the help information for any cmdlets you discover through `Get-Command`. All cmdlets are described in this README as well.
`Get-Help "<cmdlet>"` will show the documentation for . All cmdlets are described in this README as well.
### Installation
This module is available in the PowerShell Gallery. PowerShell 5 is required. Install with
This module is available in the PowerShell Gallery. PowerShell 5 is required. Install with:
```PowerShell
Install-Module "Cluster"
```
@ -150,7 +150,7 @@ A cluster is a resource group that can independently serve some version of the S
#### Creation
The cmdlet will automatically generate a new unique index for the Cluster, create the standard Service Tree node resources, then publish a *[Configuration](#configurations)* to the Cluster.
`New-Cluster` follows the same parameter conventions as the other `New-Cluster*` modules with two additional parameters:
* *[DefinitionsContainer](#definitionscontainer)* (default is current location)
* *DefinitionsContainer*, the folder path containing your [Configurations](#configurations) (default is current location)
* *[Expiry](#expiry)* (default is never)
```PowerShell
@ -241,6 +241,40 @@ Azure Resource Manager Templates used by Cluster must include the following para
*Must be supported if and only if a `*.config.json` file is present*
## Lifespan of Configurations
Azure uses [SAS tokens](https://docs.microsoft.com/en-us/azure/storage/common/storage-dotnet-shared-access-signature-part-1) to authenticate access to storage blobs. Cluster uses read-only SAS tokens to bootstrap assets. By default, these SAS tokens will not expire; however, cmdlets leveraging SAS tokens support the `[[-Expiry] <datetime>]` parameter to specify when the token should expire.
Any resources redeploying/scaling using this SAS token after the expiry date will be unhealthy. To support autoscale, a Cluster must use the default infinite expiry or redeploy the configuration prior to the expiry date. VSTS can be configured to support timed deployments, circumventing this issue.
The script below can be used in a VSTS release task to deploy cluster-by-cluster to a given environment:
```PowerShell
Param(
$ServiceName = "MyService",
$FlightingRingName,
$RegionName
)
# throw terminating error if a deployment fails
$ErrorActionPreference = "Stop"
# run in hosted VSTS to download and install the modules without elevation
Install-Module "AzureRM", "Cluster" -Scope CurrentUser
Import-Module "Cluster"
# get the clusters within our target environment
$clusters = Select-Cluster $ServiceName $FlightingRingName $RegionName
# deploy each cluster
foreach ($cluster in $clusters) {
Publish-ClusterConfiguration `
-Cluster $cluster `
-DefinitionsContainer ".\Definitions" `
-Expiry (Get-Date).AddDays(14)
}
```
## Troubleshooting

Просмотреть файл

@ -129,6 +129,12 @@ class ClusterResourceGroup {
| % {[ClusterResourceGroup]::new($_)}
return @($children)
}
[ClusterResourceGroup[]] GetDescendants() {
$children = $this.GetChildren()
return $children + ($children | % {$_.GetDescendants()})
}
[IStorageContext]$_StorageContext
@ -144,7 +150,7 @@ class ClusterResourceGroup {
[void] NewImage([string[]] $WindowsFeature) {
New-BakedImage `
-Context $this.GetStorageContext() `
-StorageContext $this.GetStorageContext() `
-WindowsFeature $WindowsFeature `
-StorageContainer $script:ImageContainerName
}
@ -161,7 +167,7 @@ class ClusterResourceGroup {
[void] PropagateBlobs([string] $Container) {
$children = $this.GetChildren()
$children = $this.GetDescendants()
if (-not $children) {
return
}