他人のAzure BLOB(public)から自分のAzure StorageにBLOBをコピーする


publicとしてアクセスできるもののStorage Keyを知らないAzure BLOBから、自分の(Storage Keyを知っている)Azure StorageにBLOBをコピーする場合、azcopyコマンドやAzure PowerShellのStart-AzureStorageBlobCopy、azure-cliのazure storage blob copy startで実現することはできないようです。

そこで、これをPowerShellで実現するスクリプトを書いてみました。
PowerShellからAzure Storage Services REST APIを直接叩いています。
※スクリプト実行前に、コピー先のコンテナを作成してください。

$srcUri = "{コピー元URI}"
  # 例) http://SRCACCOUNT.blob.core.windows.net/SRCCONTAINER/SRCBLOB.EXT
$destAccount = "{コピー先ストレージアカウント名}"
$destKey = "{コピー先ストレージキー}"
$destContainer = "{コピー先コンテナ}"
$destBlob = "{コピー先BLOB名}"

$method = "PUT"
$headers = @{}
$headers.Add("x-ms-copy-source", $srcUri)
$signatureString = "x-ms-copy-source:$srcUri`n"
$date = (Get-Date -Format "R").ToString()
$headers.Add("x-ms-date", $date)
$signatureString += "x-ms-date:$date`n"
$storageAPIVersion = "2014-02-14"
$headers.Add("x-ms-version", $storageAPIVersion)
$signatureString += "x-ms-version:$storageAPIVersion`n"
$destBlobUri = "https://$destAccount.blob.core.windows.net/$destContainer/$destBlob"
$stringToSign = "$method`n`n`n0`n`n`n`n`n`n`n`n`n" `
              + $signatureString `
              + "/$destAccount/$destContainer/$destBlob"
$stringToMac = [System.Text.Encoding]::UTF8.GetBytes($stringToSign)
$accountKeyBytes = [System.Convert]::FromBase64String($destKey)
$hmac = New-Object System.Security.Cryptography.HMACSHA256((, $accountKeyBytes))
$signature = [System.Convert]::ToBase64String($hmac.ComputeHash($stringToMac))
$headers.Add("Authorization", "SharedKey ${destAccount}:$signature")
Invoke-RestMethod -Uri $destBlobUri -Method $method -Headers $headers

これでpublicな他人のAzure BLOBから、BLOB to BLOBで自分のAzure Storageにコピーすることができます。


タグ: , , ,


コメントをどうぞ