Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions generator/.DevConfigs/252dad9f-d2a9-4d49-bff8-000924f0add4.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"services": [
{
"serviceName": "S3",
"type": "minor",
"changeLogMessages": [
"Add GetObjectResponse to TransferUtilityDownloadResponse mapping."
]
}
]
}
11 changes: 11 additions & 0 deletions generator/.DevConfigs/77d980ad-8f58-4f2e-97f8-d2c8c5ba3732.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"services": [
{
"serviceName": "S3",
"type": "minor",
"changeLogMessages": [
"Create new UploadWithResponse API that returns response metadata information for transfer utility."
]
}
]
}
11 changes: 11 additions & 0 deletions generator/.DevConfigs/c49077d9-90b3-437f-b316-6d8d8833ae75.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"services": [
{
"serviceName": "S3",
"type": "patch",
"changeLogMessages": [
"Remove AmazonWebServiceResponse as base class for transfer utility repsonse objects."
]
}
]
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class AbortMultipartUploadsCommand : BaseCommand
internal partial class AbortMultipartUploadsCommand : BaseCommand<TransferUtilityAbortMultipartUploadsResponse>
{
IAmazonS3 _s3Client;
string _bucketName;
Expand Down
13 changes: 6 additions & 7 deletions sdk/src/Services/S3/Custom/Transfer/Internal/BaseCommand.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,14 +30,13 @@

namespace Amazon.S3.Transfer.Internal
{
internal abstract partial class BaseCommand
/// <summary>
/// Generic base command that returns a typed response
/// </summary>
/// <typeparam name="TResponse">Type of response returned by the command</typeparam>
internal abstract partial class BaseCommand<TResponse> where TResponse : class
{
public virtual object Return
{
get { return null; }
}

internal GetObjectRequest ConvertToGetObjectRequest(BaseDownloadRequest request)
protected GetObjectRequest ConvertToGetObjectRequest(BaseDownloadRequest request)
{
GetObjectRequest getRequest = new GetObjectRequest()
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class DownloadCommand : BaseCommand
internal partial class DownloadCommand : BaseCommand<TransferUtilityDownloadResponse>
{
static int MAX_BACKOFF_IN_MILLISECONDS = (int)TimeSpan.FromSeconds(30).TotalMilliseconds;

Expand Down Expand Up @@ -176,4 +176,3 @@ static ByteRange ByteRangeRemainingForDownload(string filepath)
}
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class DownloadDirectoryCommand : BaseCommand
internal partial class DownloadDirectoryCommand : BaseCommand<TransferUtilityDownloadDirectoryResponse>
{
private readonly IAmazonS3 _s3Client;
private readonly TransferUtilityDownloadDirectoryRequest _request;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ namespace Amazon.S3.Transfer.Internal
/// <summary>
/// The command to manage an upload using the S3 multipart API.
/// </summary>
internal partial class MultipartUploadCommand : BaseCommand
internal partial class MultipartUploadCommand : BaseCommand<TransferUtilityUploadResponse>
{
IAmazonS3 _s3Client;
long _partSize;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class OpenStreamCommand : BaseCommand
internal partial class OpenStreamCommand : BaseCommand<TransferUtilityOpenStreamResponse>
{
IAmazonS3 _s3Client;
TransferUtilityOpenStreamRequest _request;
Expand Down Expand Up @@ -59,10 +59,5 @@ internal Stream ResponseStream
{
get { return this._responseStream; }
}

public override object Return
{
get { return this.ResponseStream; }
}
}
}
128 changes: 76 additions & 52 deletions sdk/src/Services/S3/Custom/Transfer/Internal/ResponseMapper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
*
*/

using System;
using System.Collections.Generic;
using Amazon.S3.Model;

Expand All @@ -37,10 +38,11 @@ internal static class ResponseMapper
/// </summary>
/// <param name="source">The PutObjectResponse to map from</param>
/// <returns>A new TransferUtilityUploadResponse with mapped fields</returns>
/// <exception cref="ArgumentNullException">Thrown when source is null</exception>
internal static TransferUtilityUploadResponse MapPutObjectResponse(PutObjectResponse source)
{
if (source == null)
return null;
throw new ArgumentNullException(nameof(source));

var response = new TransferUtilityUploadResponse();

Expand All @@ -63,11 +65,6 @@ internal static TransferUtilityUploadResponse MapPutObjectResponse(PutObjectResp
response.VersionId = source.VersionId;
response.Size = source.Size;

// Copy response metadata
response.ResponseMetadata = source.ResponseMetadata;
response.ContentLength = source.ContentLength;
response.HttpStatusCode = source.HttpStatusCode;

return response;
}

Expand All @@ -77,10 +74,11 @@ internal static TransferUtilityUploadResponse MapPutObjectResponse(PutObjectResp
/// </summary>
/// <param name="source">The CompleteMultipartUploadResponse to map from</param>
/// <returns>A new TransferUtilityUploadResponse with mapped fields</returns>
/// <exception cref="ArgumentNullException">Thrown when source is null</exception>
internal static TransferUtilityUploadResponse MapCompleteMultipartUploadResponse(CompleteMultipartUploadResponse source)
{
if (source == null)
return null;
throw new ArgumentNullException(nameof(source));

var response = new TransferUtilityUploadResponse();

Expand All @@ -102,69 +100,95 @@ internal static TransferUtilityUploadResponse MapCompleteMultipartUploadResponse
response.Key = source.Key;
response.Location = source.Location;

// Copy response metadata
response.ResponseMetadata = source.ResponseMetadata;
response.ContentLength = source.ContentLength;
response.HttpStatusCode = source.HttpStatusCode;

return response;
}

/// <summary>
/// Private helper method to populate the common properties from GetObjectResponse to the base response class.
/// Contains all the shared mapping logic for GetObjectResponse fields.
/// </summary>
/// <param name="source">The GetObjectResponse to map from</param>
/// <param name="target">The TransferUtilityGetObjectResponseBase to populate</param>
/// <exception cref="ArgumentNullException">Thrown when source or target is null</exception>
private static void PopulateGetObjectResponseBase(GetObjectResponse source, TransferUtilityGetObjectResponseBase target)
{
if (source == null)
throw new ArgumentNullException(nameof(source));
if (target == null)
throw new ArgumentNullException(nameof(target));

// Map all fields as defined in mapping.json "Conversion" -> "GetObjectResponse" -> "DownloadResponse"
target.AcceptRanges = source.AcceptRanges;
target.BucketKeyEnabled = source.BucketKeyEnabled.GetValueOrDefault();
target.ChecksumCRC32 = source.ChecksumCRC32;
target.ChecksumCRC32C = source.ChecksumCRC32C;
target.ChecksumCRC64NVME = source.ChecksumCRC64NVME;
target.ChecksumSHA1 = source.ChecksumSHA1;
target.ChecksumSHA256 = source.ChecksumSHA256;
target.ChecksumType = source.ChecksumType;
target.ContentRange = source.ContentRange;
target.Headers = source.Headers;
target.DeleteMarker = source.DeleteMarker;
target.ETag = source.ETag;
target.Expiration = source.Expiration;
target.ExpiresString = source.ExpiresString;
target.LastModified = source.LastModified;
target.Metadata = source.Metadata;
target.MissingMeta = source.MissingMeta;
target.ObjectLockLegalHoldStatus = source.ObjectLockLegalHoldStatus;
target.ObjectLockMode = source.ObjectLockMode;
target.ObjectLockRetainUntilDate = source.ObjectLockRetainUntilDate;
target.PartsCount = source.PartsCount;
target.ReplicationStatus = source.ReplicationStatus;
target.RequestCharged = source.RequestCharged;
target.RestoreExpiration = source.RestoreExpiration;
target.RestoreInProgress = source.RestoreInProgress;
target.ServerSideEncryptionCustomerMethod = source.ServerSideEncryptionCustomerMethod;
target.ServerSideEncryptionCustomerProvidedKeyMD5 = source.ServerSideEncryptionCustomerProvidedKeyMD5;
target.ServerSideEncryptionKeyManagementServiceKeyId = source.ServerSideEncryptionKeyManagementServiceKeyId;
target.ServerSideEncryptionMethod = source.ServerSideEncryptionMethod;
target.StorageClass = source.StorageClass;
target.TagCount = source.TagCount;
target.VersionId = source.VersionId;
target.WebsiteRedirectLocation = source.WebsiteRedirectLocation;
}

/// <summary>
/// Maps a GetObjectResponse to TransferUtilityDownloadResponse.
/// Uses the field mappings defined in mapping.json "Conversion" -> "GetObjectResponse" -> "DownloadResponse".
/// </summary>
/// <param name="source">The GetObjectResponse to map from</param>
/// <returns>A new TransferUtilityDownloadResponse with mapped fields</returns>
/// <exception cref="ArgumentNullException">Thrown when source is null</exception>
internal static TransferUtilityDownloadResponse MapGetObjectResponse(GetObjectResponse source)
{
if (source == null)
return null;
throw new ArgumentNullException(nameof(source));

var response = new TransferUtilityDownloadResponse();
PopulateGetObjectResponseBase(source, response);
return response;
}

// Map all fields as defined in mapping.json "Conversion" -> "GetObjectResponse" -> "DownloadResponse"
response.AcceptRanges = source.AcceptRanges;
response.BucketKeyEnabled = source.BucketKeyEnabled.GetValueOrDefault();
response.ChecksumCRC32 = source.ChecksumCRC32;
response.ChecksumCRC32C = source.ChecksumCRC32C;
response.ChecksumCRC64NVME = source.ChecksumCRC64NVME;
response.ChecksumSHA1 = source.ChecksumSHA1;
response.ChecksumSHA256 = source.ChecksumSHA256;
response.ChecksumType = source.ChecksumType;
response.ContentRange = source.ContentRange;
response.Headers = source.Headers;
response.DeleteMarker = source.DeleteMarker;
response.ETag = source.ETag;
response.Expiration = source.Expiration;
response.ExpiresString = source.ExpiresString;
response.LastModified = source.LastModified;
response.Metadata = source.Metadata;
response.MissingMeta = source.MissingMeta;
response.ObjectLockLegalHoldStatus = source.ObjectLockLegalHoldStatus;
response.ObjectLockMode = source.ObjectLockMode;
response.ObjectLockRetainUntilDate = source.ObjectLockRetainUntilDate;
response.PartsCount = source.PartsCount;
response.ReplicationStatus = source.ReplicationStatus;
response.RequestCharged = source.RequestCharged;
response.RestoreExpiration = source.RestoreExpiration;
response.RestoreInProgress = source.RestoreInProgress;
response.ServerSideEncryptionCustomerMethod = source.ServerSideEncryptionCustomerMethod;
response.ServerSideEncryptionCustomerProvidedKeyMD5 = source.ServerSideEncryptionCustomerProvidedKeyMD5;
response.ServerSideEncryptionKeyManagementServiceKeyId = source.ServerSideEncryptionKeyManagementServiceKeyId;
response.ServerSideEncryptionMethod = source.ServerSideEncryptionMethod;
response.StorageClass = source.StorageClass;
response.TagCount = source.TagCount;
response.VersionId = source.VersionId;
response.WebsiteRedirectLocation = source.WebsiteRedirectLocation;
/// <summary>
/// Maps a GetObjectResponse to TransferUtilityOpenStreamResponse.
/// Uses the same field mappings as DownloadResponse plus the ResponseStream property.
/// </summary>
/// <param name="source">The GetObjectResponse to map from</param>
/// <returns>A new TransferUtilityOpenStreamResponse with mapped fields</returns>
/// <exception cref="ArgumentNullException">Thrown when source is null</exception>
internal static TransferUtilityOpenStreamResponse MapGetObjectResponseToOpenStream(GetObjectResponse source)
{
if (source == null)
throw new ArgumentNullException(nameof(source));

// Copy response metadata
response.ResponseMetadata = source.ResponseMetadata;
response.ContentLength = source.ContentLength;
response.HttpStatusCode = source.HttpStatusCode;
var response = new TransferUtilityOpenStreamResponse();
PopulateGetObjectResponseBase(source, response);
response.ResponseStream = source.ResponseStream;

return response;
return response;
}


}
}
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ namespace Amazon.S3.Transfer.Internal
/// <summary>
/// This command is for doing regular PutObject requests.
/// </summary>
internal partial class SimpleUploadCommand : BaseCommand
internal partial class SimpleUploadCommand : BaseCommand<TransferUtilityUploadResponse>
{
IAmazonS3 _s3Client;
TransferUtilityConfig _config;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ namespace Amazon.S3.Transfer.Internal
/// This command files all the files that meets the criteria specified in the TransferUtilityUploadDirectoryRequest request
/// and uploads them.
/// </summary>
internal partial class UploadDirectoryCommand : BaseCommand
internal partial class UploadDirectoryCommand : BaseCommand<TransferUtilityUploadDirectoryResponse>
{
TransferUtilityUploadDirectoryRequest _request;
TransferUtility _utility;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class AbortMultipartUploadsCommand : BaseCommand
internal partial class AbortMultipartUploadsCommand : BaseCommand<TransferUtilityAbortMultipartUploadsResponse>
{
TransferUtilityConfig _config;

Expand All @@ -36,7 +36,7 @@ internal AbortMultipartUploadsCommand(IAmazonS3 s3Client, string bucketName, Dat
this._config = config;
}

public override async Task ExecuteAsync(CancellationToken cancellationToken)
public override async Task<TransferUtilityAbortMultipartUploadsResponse> ExecuteAsync(CancellationToken cancellationToken)
{
if (string.IsNullOrEmpty(this._bucketName))
{
Expand Down Expand Up @@ -88,6 +88,8 @@ await asyncThrottler.WaitAsync(cancellationToken)

await WhenAllOrFirstExceptionAsync(pendingTasks,cancellationToken)
.ConfigureAwait(continueOnCapturedContext: false);

return new TransferUtilityAbortMultipartUploadsResponse();
}
finally
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,12 @@

namespace Amazon.S3.Transfer.Internal
{
internal abstract partial class BaseCommand
internal abstract partial class BaseCommand<TResponse> where TResponse : class
{
public abstract Task ExecuteAsync(CancellationToken cancellationToken);
/// <summary>
/// Executes the command and returns a typed response
/// </summary>
public abstract Task<TResponse> ExecuteAsync(CancellationToken cancellationToken);

/// <summary>
/// Waits for all of the tasks to complete or till any task fails or is canceled.
Expand Down Expand Up @@ -80,7 +83,7 @@ await completedTask
}
}

protected static async Task ExecuteCommandAsync(BaseCommand command, CancellationTokenSource internalCts, SemaphoreSlim throttler)
protected static async Task ExecuteCommandAsync<T>(BaseCommand<T> command, CancellationTokenSource internalCts, SemaphoreSlim throttler) where T : class
{
try
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@

namespace Amazon.S3.Transfer.Internal
{
internal partial class DownloadCommand : BaseCommand
internal partial class DownloadCommand : BaseCommand<TransferUtilityDownloadResponse>
{
public override async Task ExecuteAsync(CancellationToken cancellationToken)
public override async Task<TransferUtilityDownloadResponse> ExecuteAsync(CancellationToken cancellationToken)
{
ValidateRequest();
GetObjectRequest getRequest = ConvertToGetObjectRequest(this._request);
Expand Down Expand Up @@ -130,6 +130,9 @@ await response.WriteResponseStreamToFileAsync(this._request.FilePath, true, canc
}
WaitBeforeRetry(retries);
} while (shouldRetry);

// TODO map and return response
return new TransferUtilityDownloadResponse();
}

private static bool HandleExceptionForHttpClient(Exception exception, int retries, int maxRetries)
Expand Down
Loading