Перенос больших двоичных объектов между различными учетными записями хранения с помощью AzCopy в ОС Windows
В этом примере показано, как скопировать все большие двоичные объекты из исходной учетной записи хранения, предоставленной пользователем, в целевую.
Для этого используется команда Get-AzStorageContainer
, которая перечисляет все контейнеры в учетной записи хранения. Затем, как показано в примере, AzCopy выдает команды для копирования каждого контейнера из исходной учетной записи хранения источника в целевую. В случае сбоя выполняется повторная попытка столько раз, сколько указано в свойстве $retryTimes (по умолчанию — 3 раза, что можно изменить в параметре -RetryTimes
). Если при каждой повторной попытке возникают ошибки, то пользователь может перезапустить сценарий, указав в примере последний успешно скопированный контейнер с помощью параметра -LastSuccessContainerName
. Затем с этого места будет продолжена операция копирования.
Для работы с этим примером требуется модуль хранилища Azure PowerShell 0.7 или более поздней версии. С помощью команды Get-Module -ListAvailable Az.storage
можно проверить, какая версия установлена. Если вам необходимо выполнить установку или обновление, см. статью об установке модуля Azure PowerShell.
Если у вас еще нет подписки Azure, создайте бесплатную учетную запись Azure, прежде чем начать работу.
Для этого примера также необходима последняя версия AzCopy для ОС Windows. Каталог установки по умолчанию — C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\
В этом примере используются имя и ключ исходной и целевой учетной записи хранения, а также полный путь к файлу AzCopy.exe (если он не установлен в каталоге по умолчанию).
Ниже приведены примеры входных данных:
Если AzCopy установлен в каталог по умолчанию:
srcStorageAccountName: ExampleSourceStorageAccountName
srcStorageAccountKey: ExampleSourceStorageAccountKey
DestStorageAccountName: ExampleTargetStorageAccountName
DestStorageAccountKey: ExampleTargetStorageAccountKey
Если AzCopy не установлен в каталоге по умолчанию:
srcStorageAccountName: ExampleSourceStorageAccountName
srcStorageAccountKey: ExampleSourceStorageAccountKey
DestStorageAccountName: ExampleTargetStorageAccountName
DestStorageAccountKey: ExampleTargetStorageAccountKey
AzCopyPath: C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe
Если произошел сбой и пример необходимо снова запустить из определенного контейнера:
.\copyScript.ps1 -LastSuccessContainerName myContainerName
Пример скрипта
# Run the script in a new open Powershell window, which has not run other cmdlets, or AzCopy performance could suffer .
# Need install Azure PowerShell before runing the script: https://github.com/Azure/azure-powershell/releases
# Need install AzCopy before runing the script: https://docs.microsoft.com/Az.Storage/common/storage-use-azcopy
# Do not modify the Source or Destination accounts while the copy is running
param (
[Parameter(Mandatory = $true,
HelpMessage= "Source Storage account name.")]
[ValidatePattern("^[a-z0-9`]{3,24}$")]
[String]$srcStorageAccountName,
[Parameter(Mandatory = $true,
HelpMessage= "Source Storage account key.")]
[String]$srcStorageAccountKey,
[Parameter(Mandatory = $true,
HelpMessage= "Destination Storage account name.")]
[ValidatePattern("^[a-z0-9`]{3,24}$")]
[String]$DestStorageAccountName,
[Parameter(Mandatory = $true,
HelpMessage= "Destination Storage account key.")]
[String]$DestStorageAccountKey,
[Parameter(Mandatory = $false,
HelpMessage= "Input the full filePath of the AzCopy.exe, e.g.: C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe")]
[String]$AzCopyPath = "C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe",
[Parameter(Mandatory = $false,
HelpMessage='Sets the number of retries in an event of failure. Set to 0 for no retry, set -1 for infinite retry.')]
[Int32]$RetryTimes = 3,
[Parameter(Mandatory = $false,
ValueFromPipeline = $true,
HelpMessage='Used for resume operation. When provided, the script will copy containers that are alphabetically after $LastSuccessContainerName')]
[String]$LastSuccessContainerName = $nullz
)
if( (Get-Item $AzCopyPath).Exists)
{
$FileItemVersion = (Get-Item $AzCopyPath).VersionInfo
$FilePath = ("{0}.{1}.{2}.{3}" -f $FileItemVersion.FileMajorPart, $FileItemVersion.FileMinorPart, $FileItemVersion.FileBuildPart, $FileItemVersion.FilePrivatePart)
# only netcore version AzCopy.exe has version 0.0.0.0, and all netcore version AzCopy works in this script
if(([version] $FilePath -lt "7.0.0.2") -and ([version] $FilePath -ne "0.0.0.0"))
{
$AzCopyPath = Read-Host "Version of AzCopy found at default install directory is of a lower, unsupported version. Please input the full filePath of the AzCopy.exe that is version 7.0.0.2 or higher, e.g.: C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe"
}
}
elseIf( (Get-Item $AzCopyPath).Exists -eq $false)
{
$AzCopyPath = Read-Host "Input the full filePath of the AzCopy.exe, e.g.: C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe"
}
# Create and check Storage context
$Error.Clear()
$srcCtx = New-AzStorageContext -StorageAccountName $srcStorageAccountName -StorageAccountKey $srcStorageAccountKey
if ($srcCtx -eq $null)
{
Write-Error "Script could not create source Storage Context, possibly due to invalid StorageAccountName or StorageAccount Key terminating: $Error[0]";
return;
}
$destCtx = New-AzStorageContext -StorageAccountName $destStorageAccountName -StorageAccountKey $destStorageAccountKey
if ($destCtx -eq $null)
{
Write-Error "Script could not create destination storage context, possibly due to invalid StorageAccountName or StorageAccount Key terminating: $Error[0]";
return;
}
#Check Source and Destination Storage account Connection
$Error.Clear()
$Containers = Get-AzStorageContainer -MaxCount 1 -Context $srcCtx
if ($Error.Count -gt 0)
{
Write-Error "Script failed to connect to source Storage account, terminating: $Error[0]";
return;
}
$Containers = Get-AzStorageContainer -MaxCount 1 -Context $destCtx
if ($Error.Count -gt 0)
{
Write-Error "Script failed to connect to destination Storage account, terminating: $Error[0]";
return;
}
#Check AzCopy Path
if((Test-Path $AzCopyPath) -eq $false)
{
Write-Error "Script is terminating since the provided AzCopyPath does not exist: $AzCopyPath ";
return;
}
elseif((Get-Item $AzCopyPath).BaseName -ne "AzCopy" )
{
Write-Error "Script is terminating since the provided AzCopyPath does not refer to the AzCopy exe: $AzCopyPath ";
return;
}
elseif((Get-Item $AzCopyPath).BaseName -eq "AzCopy")
{
$FileItemVersion = (Get-Item $AzCopyPath).VersionInfo
$FilePath = ("{0}.{1}.{2}.{3}" -f $FileItemVersion.FileMajorPart, $FileItemVersion.FileMinorPart, $FileItemVersion.FileBuildPart, $FileItemVersion.FilePrivatePart)
if([version] $FilePath -lt "7.0.0.2")
{
$AzCopyPath = Read-Host "Version of AzCopy found at provided path is of a lower, unsupported version. Please input the full filePath of the AzCopy.exe that is version 7.0.0.2 or higher, e.g.: C:\Program Files (x86)\Microsoft SDKs\Azure\AzCopy\AzCopy.exe"
}
}
$OutputLastSuccessContainer = $LastSuccessContainerName;
$HasReachedLastSuccessContainer = $false;
if ($LastSuccessContainerName -eq $null -or $LastSuccessContainerName -eq "")
{
$HasReachedLastSuccessContainer = $true;
}
# For list container
$MaxReturn = 250
$Token = $Null
do{
# List source containers
$retry = 1
$Error.Clear()
$srcContainers = Get-AzStorageContainer -MaxCount $MaxReturn -ContinuationToken $Token -Context $srcCtx
# If list container fail, retry it
while(($Error.Count -gt 0) -and ($RetryTimes -eq -1 -or $retry -le $retryTimes))
{
Write-Host "Retry List containers $retry"
$Error.Clear()
$srcContainers = Get-AzStorageContainer -MaxCount $MaxReturn -ContinuationToken $Token -Context $srcCtx
$retry++
}
# If list container fail after retry, break script
if ($Error.Count -gt 0){
Write-Error "Terminating the script since listing source containers failed: $Error[0]";
$CopyContainerFail = $true
break;
}
$Token = $srcContainers[$srcContainers.Count -1].ContinuationToken;
# Transfer containers one by one
$CopyContainerFail = $false
foreach ($container in $srcContainers)
{
if (!$HasReachedLastSuccessContainer)
{
if ($container.Name -eq $LastSuccessContainerName)
{
$HasReachedLastSuccessContainer = $true;
}
Write-Host "Skipping container copy: $($container.Name)"
Continue;
}
Write-Host "Start copying container: $($container.Name)"
$retry = 1
# Get AzCopy command for transfer one container
$destContainer = $destCtx.StorageAccount.CreateCloudBlobClient().GetContainerReference($container.Name)
$azCopyCmd = [string]::Format("""{0}"" /source:{1} /dest:{2} /sourcekey:""{3}"" /destkey:""{4}"" /snapshot /y /s /synccopy",$AzCopyPath, $container.CloudBlobContainer.Uri.AbsoluteUri, $destContainer.Uri.AbsoluteUri, $srcStorageAccountKey, $DestStorageAccountKey)
# Execute the AzCopy command first time
Write-Host "$azCopyCmd"
$result = cmd /c $azCopyCmd
foreach($s in $result)
{
Write-Host $s
}
# If transfer failed, retry it
while(($LASTEXITCODE -ne 0) -and ($RetryTimes -eq -1 -or $retry -le $retryTimes))
{
Write-Host "Retry $retry : $azCopyCmd"
$result = cmd /c $azCopyCmd
foreach($s in $result)
{
Write-Host $s
}
$retry++
}
# If tranfer failed after retry, print error
if ($LASTEXITCODE -ne 0){
Write-Error "Container copy failed: $($container.Name)";
$CopyContainerFail = $true
break;
}
else
{
Write-Host "Finished copying container: $($container.Name)"
Write-Host ""
$OutputLastSuccessContainer = $container.Name
}
}
if($CopyContainerFail)
{
break;
}
}
While ($Token -ne $Null)
# Summary the copy result
if ($CopyContainerFail)
{
if(($OutputLastSuccessContainer -ne $null) -and ($OutputLastSuccessContainer -ne ""))
{
Write-Warning "To resume, rerun the script and append the parameter: ""-LastSuccessContainer $OutputLastSuccessContainer"""
return $OutputLastSuccessContainer
}
else
{
Write-Warning "To resume, rerun the script."
return $null
}
}
else
{
Write-Host "All Containers copied successfully."
return ""
}
Описание скрипта
В этом сценарии для копирования данных между учетными записями хранения используются следующие команды: Для каждого элемента в таблице приведены ссылки на документацию по команде.
Get-Help | Примечания |
---|---|
Get-AzStorageContainer | Возвращает контейнеры, связанные с этой учетной записью хранения. |
New-AzStorageContext | Создает контекст службы хранилища Azure. |
Дальнейшие действия
Дополнительные сведения о модуле Azure PowerShell см. в документации по Azure PowerShell.
Дополнительные примеры скриптов PowerShell хранилища см. в статье Примеры скриптов Azure PowerShell для хранилища BLOB-объектов Azure.