Return more metadata from listMultipartUpload

Include Content-Length and Last-Modified.
This commit is contained in:
Andrew Gaul 2017-03-08 14:43:58 -08:00
parent 49f4617afa
commit 87eda15085
6 changed files with 42 additions and 17 deletions

View File

@ -35,6 +35,7 @@ import java.lang.reflect.Method;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;
@ -528,7 +529,8 @@ public class RegionScopedSwiftBlobStore implements BlobStore {
String partName = getMPUPartName(mpu, partNumber);
String eTag = api.getObjectApi(regionId, mpu.containerName()).put(partName, payload);
long partSize = payload.getContentMetadata().getContentLength();
return MultipartPart.create(partNumber, partSize, eTag);
Date lastModified = null; // Swift does not return Last-Modified
return MultipartPart.create(partNumber, partSize, eTag, lastModified);
}
@Override
@ -540,7 +542,7 @@ public class RegionScopedSwiftBlobStore implements BlobStore {
for (StorageMetadata sm : pageSet) {
int lastSlash = sm.getName().lastIndexOf('/');
int partNumber = Integer.parseInt(sm.getName().substring(lastSlash + 1));
parts.add(MultipartPart.create(partNumber, sm.getSize(), sm.getETag()));
parts.add(MultipartPart.create(partNumber, sm.getSize(), sm.getETag(), sm.getLastModified()));
}
return parts.build();
}

View File

@ -20,6 +20,7 @@ import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.base.Preconditions.checkState;
import static org.jclouds.util.Predicates2.retry;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;
@ -64,6 +65,7 @@ import org.jclouds.s3.domain.AccessControlList.GroupGranteeURI;
import org.jclouds.s3.domain.AccessControlList.Permission;
import org.jclouds.s3.domain.BucketMetadata;
import org.jclouds.s3.domain.CannedAccessPolicy;
import org.jclouds.s3.domain.ListMultipartUploadResponse;
import org.jclouds.s3.domain.ListMultipartUploadsResponse;
import org.jclouds.s3.options.CopyObjectOptions;
import org.jclouds.s3.options.ListBucketOptions;
@ -385,18 +387,19 @@ public class S3BlobStore extends BaseBlobStore {
@Override
public MultipartPart uploadMultipartPart(MultipartUpload mpu, int partNumber, Payload payload) {
long partSize = -1; // TODO: how to get this from payload?
long partSize = payload.getContentMetadata().getContentLength();
String eTag = sync.uploadPart(mpu.containerName(), mpu.blobName(), partNumber, mpu.id(), payload);
return MultipartPart.create(partNumber, partSize, eTag);
Date lastModified = null; // S3 does not return Last-Modified
return MultipartPart.create(partNumber, partSize, eTag, lastModified);
}
@Override
public List<MultipartPart> listMultipartUpload(MultipartUpload mpu) {
ImmutableList.Builder<MultipartPart> parts = ImmutableList.builder();
Map<Integer, String> s3Parts = sync.listMultipartParts(mpu.containerName(), mpu.blobName(), mpu.id());
for (Map.Entry<Integer, String> entry : s3Parts.entrySet()) {
long partSize = -1; // TODO: could call getContentLength but did not above
parts.add(MultipartPart.create(entry.getKey(), partSize, entry.getValue()));
Map<Integer, ListMultipartUploadResponse> s3Parts = sync.listMultipartPartsFull(mpu.containerName(), mpu.blobName(), mpu.id());
for (Map.Entry<Integer, ListMultipartUploadResponse> entry : s3Parts.entrySet()) {
ListMultipartUploadResponse response = entry.getValue();
parts.add(MultipartPart.create(entry.getKey(), response.size(), response.eTag(), response.lastModified()));
}
return parts.build();
}

View File

@ -866,7 +866,7 @@ public final class LocalBlobStore implements BlobStore {
String partETag = putBlob(mpu.containerName(), blob);
BlobMetadata metadata = blobMetadata(mpu.containerName(), partName); // TODO: racy, how to get this from payload?
long partSize = metadata.getContentMetadata().getContentLength();
return MultipartPart.create(partNumber, partSize, partETag);
return MultipartPart.create(partNumber, partSize, partETag, metadata.getLastModified());
}
@Override
@ -882,7 +882,7 @@ public final class LocalBlobStore implements BlobStore {
}
int partNumber = Integer.parseInt(sm.getName().substring((MULTIPART_PREFIX + mpu.id() + "-" + mpu.blobName() + "-").length()));
long partSize = sm.getSize();
parts.add(MultipartPart.create(partNumber, partSize, sm.getETag()));
parts.add(MultipartPart.create(partNumber, partSize, sm.getETag(), sm.getLastModified()));
}
if (pageSet.isEmpty() || pageSet.getNextMarker() == null) {
break;

View File

@ -17,6 +17,8 @@
package org.jclouds.blobstore.domain;
import java.util.Date;
import org.jclouds.javax.annotation.Nullable;
import com.google.auto.value.AutoValue;
@ -26,8 +28,14 @@ public abstract class MultipartPart {
public abstract int partNumber();
public abstract long partSize();
@Nullable public abstract String partETag();
@Nullable public abstract Date lastModified();
@Deprecated
public static MultipartPart create(int partNumber, long partSize, @Nullable String partETag) {
return new AutoValue_MultipartPart(partNumber, partSize, partETag);
return MultipartPart.create(partNumber, partSize, partETag, null);
}
public static MultipartPart create(int partNumber, long partSize, @Nullable String partETag, @Nullable Date lastModified) {
return new AutoValue_MultipartPart(partNumber, partSize, partETag, lastModified);
}
}

View File

@ -1215,7 +1215,11 @@ public class BaseBlobIntegrationTest extends BaseBlobStoreIntegrationTest {
MultipartPart part = blobStore.uploadMultipartPart(mpu, 1, payload);
List<MultipartPart> parts = blobStore.listMultipartUpload(mpu);
assertThat(parts).isEqualTo(ImmutableList.of(part));
assertThat(parts).hasSize(1);
assertThat(parts.get(0).partNumber()).isEqualTo(part.partNumber());
assertThat(parts.get(0).partSize()).isEqualTo(part.partSize());
assertThat(parts.get(0).partETag()).isEqualTo(part.partETag());
// not checking lastModified since B2, S3, and Swift do not return it from uploadMultipartPart
blobStore.completeMultipartUpload(mpu, ImmutableList.of(part));
@ -1254,7 +1258,14 @@ public class BaseBlobIntegrationTest extends BaseBlobStoreIntegrationTest {
MultipartPart part2 = blobStore.uploadMultipartPart(mpu, 2, payload2);
List<MultipartPart> parts = blobStore.listMultipartUpload(mpu);
assertThat(parts).isEqualTo(ImmutableList.of(part1, part2));
assertThat(parts).hasSize(2);
assertThat(parts.get(0).partNumber()).isEqualTo(part1.partNumber());
assertThat(parts.get(0).partSize()).isEqualTo(part1.partSize());
assertThat(parts.get(0).partETag()).isEqualTo(part1.partETag());
assertThat(parts.get(1).partNumber()).isEqualTo(part2.partNumber());
assertThat(parts.get(1).partSize()).isEqualTo(part2.partSize());
assertThat(parts.get(1).partETag()).isEqualTo(part2.partETag());
// not checking lastModified since B2, S3, and Swift do not return it from uploadMultipartPart
blobStore.completeMultipartUpload(mpu, ImmutableList.of(part1, part2));

View File

@ -21,6 +21,7 @@ import static org.jclouds.azure.storage.options.ListOptions.Builder.includeMetad
import java.io.InputStream;
import java.net.URI;
import java.util.Date;
import java.util.EnumSet;
import java.util.List;
import java.util.Map;
@ -435,8 +436,8 @@ public class AzureBlobStore extends BaseBlobStore {
String blockId = BaseEncoding.base64().encode(Ints.toByteArray(partNumber));
sync.putBlock(mpu.containerName(), mpu.blobName(), blockId, payload);
String eTag = ""; // putBlock does not return ETag
long partSize = -1; // TODO: how to get this from payload?
return MultipartPart.create(partNumber, partSize, eTag);
Date lastModified = null; // putBlob does not return Last-Modified
return MultipartPart.create(partNumber, payload.getContentMetadata().getContentLength(), eTag);
}
@Override
@ -452,8 +453,8 @@ public class AzureBlobStore extends BaseBlobStore {
for (BlobBlockProperties properties : response.getBlocks()) {
int partNumber = Ints.fromByteArray(BaseEncoding.base64().decode(properties.getBlockName()));
String eTag = ""; // getBlockList does not return ETag
long partSize = -1; // TODO: could call getContentLength but did not above
parts.add(MultipartPart.create(partNumber, partSize, eTag));
Date lastModified = null; // getBlockList does not return LastModified
parts.add(MultipartPart.create(partNumber, properties.getContentLength(), eTag, lastModified));
}
return parts.build();
}