/// <inheritdoc/> public async Task <CopyFromUriOperation> BlobCopyAsync(Uri sourceUri, Uri destinationUri) { _ = sourceUri ?? throw new ArgumentNullException(nameof(sourceUri)); _ = destinationUri ?? throw new ArgumentNullException(nameof(destinationUri)); var destinationBlobBaseClient = new BlobBaseClient(destinationUri, _tokenCredential); CopyFromUriOperation blobCopyInfo; try { // 1. Get SAS for Source string sasUri = await GetSasUrlAsync(sourceUri, _blobCopyTimeout).ConfigureAwait(false); // 2. Copy Async to Dest blobCopyInfo = await destinationBlobBaseClient.StartCopyFromUriAsync(new Uri(sasUri)).ConfigureAwait(false); } catch (RequestFailedException e) when(e.ErrorCode == "AuthorizationPermissionMismatch") { var msg = $"BlobBaseClient.StartCopyFromUriAsync requires the identity principal to have role 'Storage Blob Data Contributor' on resource (file, container, resource-group, or subscription). " + $"Could not copy blob from {sourceUri} to {destinationUri}."; _log.LogError(e, msg); throw new Exception(msg, e); } catch (Exception e) { var msg = $"Could not copy blob from {sourceUri} to {destinationUri}."; _log.LogError(e, msg); throw new Exception(msg, e); } return(blobCopyInfo); }
private async Task StartCopyFromUri(long taskId, IStorageBlobManagement destChannel, Uri srcUri, BlobBaseClient destBlob) { bool destExist = true; Track2Models.BlobType? destBlobType = Util.GetBlobType(destBlob); Track2Models.BlobProperties properties = null; try { properties = (await destBlob.GetPropertiesAsync(this.BlobRequestConditions, cancellationToken: this.CmdletCancellationToken).ConfigureAwait(false)).Value; destBlobType = properties.BlobType; } catch (global::Azure.RequestFailedException e) when(e.Status == 404) { destExist = false; } if (destBlobType != null) { ValidateBlobTier(Util.convertBlobType_Track2ToTrack1(destBlobType), pageBlobTier, standardBlobTier, rehydratePriority); } if (!destExist || this.ConfirmOverwrite(srcUri.AbsoluteUri.ToString(), destBlob.Uri.ToString())) { Track2Models.BlobCopyFromUriOptions options = new global::Azure.Storage.Blobs.Models.BlobCopyFromUriOptions(); // The Blob Type and Blob Tier must match, since already checked they are match at the begin of ExecuteCmdlet(). if (pageBlobTier != null) { options.AccessTier = Util.ConvertAccessTier_Track1ToTrack2(pageBlobTier); } else if (standardBlobTier != null || rehydratePriority != null) { options.AccessTier = Util.ConvertAccessTier_Track1ToTrack2(standardBlobTier); options.RehydratePriority = Util.ConvertRehydratePriority_Track1ToTrack2(rehydratePriority); } if (this.BlobTag != null) { options.Tags = this.BlobTag.Cast <DictionaryEntry>().ToDictionary(d => (string)d.Key, d => (string)d.Value); } options.SourceConditions = this.BlobRequestConditions; if (this.DestTagCondition != null) { options.DestinationConditions = new Track2Models.BlobRequestConditions(); options.DestinationConditions.TagConditions = DestTagCondition; } Track2Models.CopyFromUriOperation copyId = await destBlob.StartCopyFromUriAsync(srcUri, options, this.CmdletCancellationToken).ConfigureAwait(false); this.OutputStream.WriteVerbose(taskId, String.Format(Resources.CopyDestinationBlobPending, destBlob.Name, destBlob.BlobContainerName, copyId)); OutputStream.WriteObject(taskId, new AzureStorageBlob(destBlob, destChannel.StorageContext, properties, options: ClientOptions)); } }