mirror of https://github.com/apache/jclouds.git
Issue 73: normalizing names of objects; break metadata into interfaces so that they can be implemented differently
git-svn-id: http://jclouds.googlecode.com/svn/trunk@1986 3d8758e0-26b5-11de-8745-db77d3ebf521
This commit is contained in:
parent
ff9abb6884
commit
ee6ffff298
|
@ -49,7 +49,7 @@ import org.jclouds.aws.s3.xml.ListAllMyBucketsHandler;
|
|||
import org.jclouds.aws.s3.xml.ListBucketHandler;
|
||||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ReturnVoidOnNotFoundOr404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
import org.jclouds.http.functions.ParseETagHeader;
|
||||
|
@ -181,7 +181,7 @@ public interface S3BlobStore extends BlobStore<BucketMetadata, ObjectMetadata, S
|
|||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putBlob(
|
||||
@HostPrefixParam String bucketName,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(BindS3ObjectToEntity.class) S3Object object);
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(BindS3ObjectToEntity.class) S3Object object);
|
||||
|
||||
@PUT
|
||||
@Path("/")
|
||||
|
|
|
@ -55,7 +55,7 @@ import org.jclouds.aws.s3.xml.CopyObjectHandler;
|
|||
import org.jclouds.aws.s3.xml.ListAllMyBucketsHandler;
|
||||
import org.jclouds.aws.s3.xml.ListBucketHandler;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ReturnVoidOnNotFoundOr404;
|
||||
import org.jclouds.blobstore.functions.ThrowContainerNotFoundOn404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
|
@ -206,7 +206,7 @@ public interface S3Connection {
|
|||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putObject(
|
||||
@HostPrefixParam String bucketName,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(BindS3ObjectToEntity.class) S3Object object,
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(BindS3ObjectToEntity.class) S3Object object,
|
||||
PutObjectOptions... options);
|
||||
|
||||
/**
|
||||
|
|
|
@ -31,11 +31,11 @@ import javax.inject.Named;
|
|||
import javax.ws.rs.core.HttpHeaders;
|
||||
|
||||
import org.jclouds.aws.s3.domain.S3Object;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntity;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.http.HttpRequest;
|
||||
|
||||
public class BindS3ObjectToEntity extends BindBlobToEntity {
|
||||
public class BindS3ObjectToEntity extends BindBlobToEntityAndUserMetadataToHeadersWithPrefix {
|
||||
@Inject
|
||||
public BindS3ObjectToEntity(@Named(PROPERTY_USER_METADATA_PREFIX) String metadataPrefix) {
|
||||
super(metadataPrefix);
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
*/
|
||||
package org.jclouds.aws.s3.domain;
|
||||
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
/**
|
||||
|
@ -31,7 +31,7 @@ import org.joda.time.DateTime;
|
|||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class BucketMetadata extends ContainerMetadata {
|
||||
public class BucketMetadata extends ContainerMetadataImpl {
|
||||
protected DateTime creationDate;
|
||||
|
||||
public DateTime getCreationDate() {
|
||||
|
|
|
@ -25,7 +25,7 @@ package org.jclouds.aws.s3.domain;
|
|||
|
||||
import java.io.Serializable;
|
||||
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
|
||||
/**
|
||||
* /** Amazon S3 is designed to store objects. Objects are stored in {@link S3BucketListing buckets}
|
||||
|
@ -38,7 +38,7 @@ import org.jclouds.blobstore.domain.BlobMetadata;
|
|||
*
|
||||
* @see <a href= "http://docs.amazonwebservices.com/AmazonS3/2006-03-01/UsingMetadata.html" />
|
||||
*/
|
||||
public class ObjectMetadata extends BlobMetadata implements Serializable {
|
||||
public class ObjectMetadata extends BlobMetadataImpl implements Serializable {
|
||||
|
||||
/** The serialVersionUID */
|
||||
private static final long serialVersionUID = -4415449798024051115L;
|
||||
|
@ -51,7 +51,7 @@ public class ObjectMetadata extends BlobMetadata implements Serializable {
|
|||
dataDisposition).append(", owner=").append(owner).append(", storageClass=").append(
|
||||
storageClass).append(", allHeaders=").append(allHeaders).append(", dataEncoding=")
|
||||
.append(dataEncoding).append(", dataType=").append(dataType).append(", eTag=")
|
||||
.append(eTag).append(", key=").append(key).append(", lastModified=").append(
|
||||
.append(eTag).append(", key=").append(name).append(", lastModified=").append(
|
||||
lastModified).append(", size=").append(size).append(", userMetadata=")
|
||||
.append(userMetadata).append("]");
|
||||
return builder.toString();
|
||||
|
@ -186,7 +186,7 @@ public class ObjectMetadata extends BlobMetadata implements Serializable {
|
|||
}
|
||||
|
||||
public int compareTo(ObjectMetadata o) {
|
||||
return (this == o) ? 0 : getKey().compareTo(o.getKey());
|
||||
return (this == o) ? 0 : getName().compareTo(o.getName());
|
||||
}
|
||||
|
||||
public void setContentEncoding(String dataEncoding) {
|
||||
|
|
|
@ -25,7 +25,7 @@ package org.jclouds.aws.s3.domain;
|
|||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
|
||||
/**
|
||||
* Amazon S3 is designed to store objects. Objects are stored in {@link S3Bucket buckets} and
|
||||
|
@ -37,7 +37,7 @@ import org.jclouds.blobstore.domain.Blob;
|
|||
* @see <a href="http://docs.amazonwebservices.com/AmazonS3/2006-03-01/index.html?UsingObjects.html"
|
||||
* />
|
||||
*/
|
||||
public class S3Object extends Blob<ObjectMetadata> {
|
||||
public class S3Object extends BlobImpl<ObjectMetadata> {
|
||||
|
||||
public S3Object(ObjectMetadata metadata, Object data) {
|
||||
super(metadata, data);
|
||||
|
|
|
@ -121,7 +121,7 @@ public class StubS3Connection extends StubBlobStore<BucketMetadata, ObjectMetada
|
|||
ObjectMetadata lastMarkerMetadata = Iterables.find(contents,
|
||||
new Predicate<ObjectMetadata>() {
|
||||
public boolean apply(ObjectMetadata metadata) {
|
||||
return metadata.getKey().equals(finalMarker);
|
||||
return metadata.getName().equals(finalMarker);
|
||||
}
|
||||
});
|
||||
contents = contents.tailSet(lastMarkerMetadata);
|
||||
|
@ -133,7 +133,7 @@ public class StubS3Connection extends StubBlobStore<BucketMetadata, ObjectMetada
|
|||
contents = Sets.newTreeSet(Iterables.filter(contents,
|
||||
new Predicate<ObjectMetadata>() {
|
||||
public boolean apply(ObjectMetadata o) {
|
||||
return (o != null && o.getKey().startsWith(prefix));
|
||||
return (o != null && o.getName().startsWith(prefix));
|
||||
}
|
||||
}));
|
||||
}
|
||||
|
@ -161,7 +161,7 @@ public class StubS3Connection extends StubBlobStore<BucketMetadata, ObjectMetada
|
|||
if (!contentsSlice.contains(contents.last())) {
|
||||
// Partial listing
|
||||
truncated = true;
|
||||
marker = contentsSlice.last().getKey();
|
||||
marker = contentsSlice.last().getName();
|
||||
} else {
|
||||
marker = null;
|
||||
}
|
||||
|
@ -229,7 +229,7 @@ public class StubS3Connection extends StubBlobStore<BucketMetadata, ObjectMetada
|
|||
final PutObjectOptions options = (nullableOptions == null) ? new PutObjectOptions()
|
||||
: nullableOptions;
|
||||
if (options.getAcl() != null)
|
||||
keyToAcl.put(bucketName + "/" + object.getKey(), options.getAcl());
|
||||
keyToAcl.put(bucketName + "/" + object.getName(), options.getAcl());
|
||||
return super.putBlob(bucketName, object);
|
||||
}
|
||||
|
||||
|
|
|
@ -132,7 +132,7 @@ public class S3ParserTest extends PerformanceTest {
|
|||
assert container.getBucketName().equals("adrianjbosstest");
|
||||
assert container.size() == 1;
|
||||
ObjectMetadata object = container.iterator().next();
|
||||
assert object.getKey().equals("3366");
|
||||
assert object.getName().equals("3366");
|
||||
DateTime expected = new DateTime("2009-03-12T02:00:13.000Z");
|
||||
assert object.getLastModified().equals(expected) : String.format(
|
||||
"expected %1$s, but got %1$s", expected, object.getLastModified());
|
||||
|
|
|
@ -96,7 +96,7 @@ public class Util {
|
|||
}
|
||||
|
||||
public static S3Object convertObjectHead(org.jclouds.aws.s3.domain.ObjectMetadata jcObjectMD) {
|
||||
S3Object jsObject = new S3Object(jcObjectMD.getKey());
|
||||
S3Object jsObject = new S3Object(jcObjectMD.getName());
|
||||
if (jcObjectMD.getOwner() != null) {
|
||||
jsObject.setOwner(new S3Owner(jcObjectMD.getOwner().getId(), jcObjectMD.getOwner()
|
||||
.getDisplayName()));
|
||||
|
|
|
@ -51,9 +51,9 @@ import org.jclouds.azure.storage.domain.BoundedSortedSet;
|
|||
import org.jclouds.azure.storage.filters.SharedKeyAuthentication;
|
||||
import org.jclouds.azure.storage.options.ListOptions;
|
||||
import org.jclouds.azure.storage.reference.AzureStorageHeaders;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntity;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.binders.BindMapToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ReturnVoidOnNotFoundOr404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
import org.jclouds.http.functions.ParseETagHeader;
|
||||
|
@ -271,7 +271,7 @@ public interface AzureBlobConnection {
|
|||
@Path("{container}/{key}")
|
||||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putBlob(@PathParam("container") String container,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(BindBlobToEntity.class) Blob object);
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(BindBlobToEntityAndUserMetadataToHeadersWithPrefix.class) Blob object);
|
||||
|
||||
/**
|
||||
* The Get Blob operation reads or downloads a blob from the system, including its metadata and
|
||||
|
|
|
@ -50,7 +50,7 @@ import org.jclouds.azure.storage.filters.SharedKeyAuthentication;
|
|||
import org.jclouds.azure.storage.options.ListOptions;
|
||||
import org.jclouds.azure.storage.reference.AzureStorageHeaders;
|
||||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ReturnVoidOnNotFoundOr404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
import org.jclouds.http.functions.ParseETagHeader;
|
||||
|
@ -149,7 +149,7 @@ public interface AzureBlobStore extends BlobStore<ContainerMetadata, BlobMetadat
|
|||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putBlob(
|
||||
@PathParam("container") String container,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(GenerateMD5AndBindBlobToEntity.class) Blob object);
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(GenerateMD5AndBindBlobToEntity.class) Blob object);
|
||||
|
||||
@GET
|
||||
@ResponseParser(ParseBlobFromHeadersAndHttpContent.class)
|
||||
|
|
|
@ -34,7 +34,7 @@ import org.jclouds.azure.storage.blob.domain.BlobMetadata;
|
|||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.http.HttpRequest;
|
||||
|
||||
public class BindBlobToEntity extends org.jclouds.blobstore.binders.BindBlobToEntity {
|
||||
public class BindBlobToEntity extends org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix {
|
||||
@Inject
|
||||
public BindBlobToEntity(@Named(PROPERTY_USER_METADATA_PREFIX) String metadataPrefix) {
|
||||
super(metadataPrefix);
|
||||
|
|
|
@ -47,7 +47,7 @@ public class GenerateMD5AndBindBlobToEntity extends BindBlobToEntity {
|
|||
try {
|
||||
object.generateMD5();
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException("Could not generate MD5 for " + object.getKey(), e);
|
||||
throw new RuntimeException("Could not generate MD5 for " + object.getName(), e);
|
||||
}
|
||||
}
|
||||
super.bindToRequest(request, entity);
|
||||
|
|
|
@ -23,10 +23,12 @@
|
|||
*/
|
||||
package org.jclouds.azure.storage.blob.domain;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
|
||||
/**
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class Blob extends org.jclouds.blobstore.domain.Blob<BlobMetadata> {
|
||||
public class Blob extends BlobImpl<BlobMetadata> {
|
||||
|
||||
public Blob(BlobMetadata metadata, BlobMetadata data) {
|
||||
super(metadata, data);
|
||||
|
|
|
@ -27,6 +27,7 @@ import java.net.URI;
|
|||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
import com.google.inject.internal.Nullable;
|
||||
|
@ -36,7 +37,7 @@ import com.google.inject.internal.Nullable;
|
|||
* @author Adrian Cole
|
||||
*
|
||||
*/
|
||||
public class BlobMetadata extends org.jclouds.blobstore.domain.BlobMetadata {
|
||||
public class BlobMetadata extends BlobMetadataImpl {
|
||||
/** The serialVersionUID */
|
||||
private static final long serialVersionUID = 1L;
|
||||
private URI url;
|
||||
|
|
|
@ -36,7 +36,7 @@ import com.google.common.collect.Multimap;
|
|||
* @author Adrian Cole
|
||||
*
|
||||
*/
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.domain.ContainerMetadata {
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.internal.ContainerMetadataImpl {
|
||||
private URI url;
|
||||
private DateTime lastModified;
|
||||
private byte[] eTag;
|
||||
|
|
|
@ -53,8 +53,8 @@ public class AddMD5ToListBlobsResponse extends ContainerNameEnumerationResultsHa
|
|||
ListBlobsResponse response = super.getResult();
|
||||
checkNotNull(response.getContainerUrl(), "containerUrl");
|
||||
for (BlobMetadata md : response) {
|
||||
checkNotNull(md.getKey(), "key");
|
||||
md.setContentMD5(util.getMD5(response.getContainerUrl(), md.getKey()));
|
||||
checkNotNull(md.getName(), "key");
|
||||
md.setContentMD5(util.getMD5(response.getContainerUrl(), md.getName()));
|
||||
}
|
||||
return response;
|
||||
}
|
||||
|
|
|
@ -251,8 +251,8 @@ public class AzureBlobConnectionLiveTest {
|
|||
}
|
||||
|
||||
// Test HEAD of object
|
||||
BlobMetadata metadata = connection.getBlobProperties(privateContainer, object.getKey());
|
||||
// TODO assertEquals(metadata.getKey(), object.getKey());
|
||||
BlobMetadata metadata = connection.getBlobProperties(privateContainer, object.getName());
|
||||
// TODO assertEquals(metadata.getName(), object.getName());
|
||||
// we can't check this while hacking around lack of content-md5, as GET of the first byte will
|
||||
// show incorrect length 1, the returned size, as opposed to the real length. This is an ok
|
||||
// tradeoff, as a container list will contain the correct size of the objects in an
|
||||
|
@ -271,7 +271,7 @@ public class AzureBlobConnectionLiveTest {
|
|||
// Multimap<String, String> userMetadata = HashMultimap.create();
|
||||
// userMetadata.put("New-Metadata-1", "value-1");
|
||||
// userMetadata.put("New-Metadata-2", "value-2");
|
||||
// assertTrue(connection.setObjectMetadata(privateContainer, object.getKey(), userMetadata));
|
||||
// assertTrue(connection.setObjectMetadata(privateContainer, object.getName(), userMetadata));
|
||||
|
||||
// Test GET of missing object
|
||||
try {
|
||||
|
@ -281,10 +281,10 @@ public class AzureBlobConnectionLiveTest {
|
|||
e.printStackTrace();
|
||||
}
|
||||
// Test GET of object (including updated metadata)
|
||||
Blob getBlob = connection.getBlob(privateContainer, object.getKey()).get(120,
|
||||
Blob getBlob = connection.getBlob(privateContainer, object.getName()).get(120,
|
||||
TimeUnit.SECONDS);
|
||||
assertEquals(IOUtils.toString((InputStream) getBlob.getData()), data);
|
||||
// TODO assertEquals(getBlob.getKey(), object.getKey());
|
||||
// TODO assertEquals(getBlob.getName(), object.getName());
|
||||
assertEquals(getBlob.getContentLength(), data.length());
|
||||
assertEquals(getBlob.getMetadata().getContentType(), "text/plain");
|
||||
assertEquals(HttpUtils.toHexString(md5), HttpUtils.toHexString(getBlob.getMetadata()
|
||||
|
@ -323,7 +323,7 @@ public class AzureBlobConnectionLiveTest {
|
|||
// Test GET with options
|
||||
// Non-matching ETag
|
||||
try {
|
||||
connection.getBlob(privateContainer, object.getKey(),
|
||||
connection.getBlob(privateContainer, object.getName(),
|
||||
GetOptions.Builder.ifETagDoesntMatch(newEtag)).get(120, TimeUnit.SECONDS);
|
||||
} catch (Exception e) {
|
||||
assertEquals(e.getCause().getClass(), HttpResponseException.class);
|
||||
|
@ -331,7 +331,7 @@ public class AzureBlobConnectionLiveTest {
|
|||
}
|
||||
|
||||
// Matching ETag
|
||||
getBlob = connection.getBlob(privateContainer, object.getKey(),
|
||||
getBlob = connection.getBlob(privateContainer, object.getName(),
|
||||
GetOptions.Builder.ifETagMatches(newEtag)).get(120, TimeUnit.SECONDS);
|
||||
assertEquals(getBlob.getMetadata().getETag(), newEtag);
|
||||
|
||||
|
@ -339,7 +339,7 @@ public class AzureBlobConnectionLiveTest {
|
|||
// doesn't work per
|
||||
// http://social.msdn.microsoft.com/Forums/en-US/windowsazure/thread/479fa63f-51df-4b66-96b5-33ae362747b6
|
||||
// getBlob = connection
|
||||
// .getBlob(privateContainer, object.getKey(), GetOptions.Builder.startAt(8)).get(120,
|
||||
// .getBlob(privateContainer, object.getName(), GetOptions.Builder.startAt(8)).get(120,
|
||||
// TimeUnit.SECONDS);
|
||||
// assertEquals(IOUtils.toString((InputStream) getBlob.getData()), data.substring(8));
|
||||
|
||||
|
|
|
@ -122,7 +122,7 @@ public class AddMD5ToListBlobsResponseTest extends BaseHandlerTest {
|
|||
), null, null, 4, "newblob2.txt", null, "myfolder/");
|
||||
|
||||
BoundedSortedSet<ListBlobsResponse> result = (BoundedSortedSet<ListBlobsResponse>) factory
|
||||
.create(injector.getInstance(ContainerNameEnumerationResultsHandler.class))
|
||||
.create(injector.getInstance(AddMD5ToListBlobsResponse.class))
|
||||
.parse(is);
|
||||
|
||||
assertEquals(result, list);
|
||||
|
|
|
@ -66,7 +66,7 @@ public class BlobStoreContextImpl<S, C extends ContainerMetadata, M extends Blob
|
|||
public B newBlob(String key) {
|
||||
Object object = blobProvider.get();
|
||||
B blob = (B) object;
|
||||
blob.getMetadata().setKey(key);
|
||||
blob.getMetadata().setName(key);
|
||||
return blob;
|
||||
}
|
||||
|
||||
|
|
|
@ -24,10 +24,7 @@
|
|||
package org.jclouds.blobstore.binders;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
import static org.jclouds.blobstore.reference.BlobStoreConstants.PROPERTY_USER_METADATA_PREFIX;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import javax.ws.rs.core.HttpHeaders;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
|
@ -36,20 +33,10 @@ import org.jclouds.http.HttpUtils;
|
|||
import org.jclouds.rest.Binder;
|
||||
|
||||
public class BindBlobToEntity implements Binder {
|
||||
private final String metadataPrefix;
|
||||
|
||||
@Inject
|
||||
public BindBlobToEntity(@Named(PROPERTY_USER_METADATA_PREFIX) String metadataPrefix) {
|
||||
this.metadataPrefix = metadataPrefix;
|
||||
}
|
||||
|
||||
public void bindToRequest(HttpRequest request, Object entity) {
|
||||
Blob<?> object = (Blob<?>) entity;
|
||||
|
||||
for (String key : object.getMetadata().getUserMetadata().keySet()) {
|
||||
request.getHeaders().put(key.startsWith(metadataPrefix) ? key : metadataPrefix + key,
|
||||
object.getMetadata().getUserMetadata().get(key));
|
||||
}
|
||||
request.setEntity(checkNotNull(object.getData(), "object.getContent()"));
|
||||
request.getHeaders()
|
||||
.put(
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (C) 2009 Global Cloud Specialists, Inc. <info@globalcloudspecialists.com>
|
||||
*
|
||||
* ====================================================================
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
* ====================================================================
|
||||
*/
|
||||
package org.jclouds.blobstore.binders;
|
||||
|
||||
import static org.jclouds.blobstore.reference.BlobStoreConstants.PROPERTY_USER_METADATA_PREFIX;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.http.HttpRequest;
|
||||
|
||||
public class BindBlobToEntityAndUserMetadataToHeadersWithPrefix extends BindBlobToEntity {
|
||||
private final String metadataPrefix;
|
||||
|
||||
@Inject
|
||||
public BindBlobToEntityAndUserMetadataToHeadersWithPrefix(
|
||||
@Named(PROPERTY_USER_METADATA_PREFIX) String metadataPrefix) {
|
||||
this.metadataPrefix = metadataPrefix;
|
||||
}
|
||||
|
||||
public void bindToRequest(HttpRequest request, Object entity) {
|
||||
Blob<?> object = (Blob<?>) entity;
|
||||
|
||||
for (String key : object.getMetadata().getUserMetadata().keySet()) {
|
||||
request.getHeaders().put(key.startsWith(metadataPrefix) ? key : metadataPrefix + key,
|
||||
object.getMetadata().getUserMetadata().get(key));
|
||||
}
|
||||
super.bindToRequest(request, entity);
|
||||
}
|
||||
}
|
|
@ -52,7 +52,7 @@ public class BindBlobToMultipartForm implements Binder {
|
|||
|
||||
public void bindToRequest(HttpRequest request, Object entity) {
|
||||
Blob<?> object = (Blob<?>) entity;
|
||||
Key key = BlobStoreUtils.parseKey(new Key("junk", object.getKey()));
|
||||
Key key = BlobStoreUtils.parseKey(new Key("junk", object.getName()));
|
||||
Multimap<String, String> partHeaders = ImmutableMultimap.of("Content-Disposition", String
|
||||
.format("form-data; name=\"%s\"; filename=\"%s\"", key.getKey(), key.getKey()),
|
||||
HttpHeaders.CONTENT_TYPE, checkNotNull(object.getMetadata().getContentType(),
|
||||
|
|
|
@ -23,17 +23,12 @@
|
|||
*/
|
||||
package org.jclouds.blobstore.domain;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
import static com.google.common.base.Preconditions.checkState;
|
||||
|
||||
import java.awt.Container;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
|
||||
import org.jclouds.http.HttpUtils;
|
||||
import org.jclouds.http.HttpUtils.MD5InputStreamResult;
|
||||
import com.google.inject.ImplementedBy;
|
||||
|
||||
/**
|
||||
* Value type for an HTTP Blob service. Blobs are stored in {@link Container containers} and consist
|
||||
|
@ -43,81 +38,13 @@ import org.jclouds.http.HttpUtils.MD5InputStreamResult;
|
|||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class Blob<M extends BlobMetadata> implements Comparable<Blob<M>> {
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
Blob<M> other = (Blob<M>) obj;
|
||||
if (contentLength != other.contentLength)
|
||||
return false;
|
||||
if (contentRange == null) {
|
||||
if (other.contentRange != null)
|
||||
return false;
|
||||
} else if (!contentRange.equals(other.contentRange))
|
||||
return false;
|
||||
if (data == null) {
|
||||
if (other.data != null)
|
||||
return false;
|
||||
} else if (!data.equals(other.data))
|
||||
return false;
|
||||
if (getMetadata() == null) {
|
||||
if (other.getMetadata() != null)
|
||||
return false;
|
||||
} else if (!getMetadata().equals(other.getMetadata()))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Blob [contentLength=" + contentLength + ", contentRange=" + contentRange + ", data="
|
||||
+ data + ", metadata=" + getMetadata() + "]";
|
||||
}
|
||||
|
||||
protected Object data;
|
||||
private M metadata;
|
||||
protected long contentLength = -1;
|
||||
protected String contentRange;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public Blob(String key) {
|
||||
// TODO: why are we getting a generic warning here?
|
||||
this((M) new BlobMetadata(key));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Inject
|
||||
public Blob() {
|
||||
this((M) new BlobMetadata());
|
||||
}
|
||||
|
||||
public Blob(M metadata) {
|
||||
this.setMetadata(metadata);
|
||||
}
|
||||
|
||||
public Blob(M metadata, Object data) {
|
||||
this(metadata);
|
||||
setData(data);
|
||||
}
|
||||
|
||||
public Blob(String key, Object data) {
|
||||
this(key);
|
||||
setData(data);
|
||||
}
|
||||
@ImplementedBy(BlobImpl.class)
|
||||
public interface Blob<M extends BlobMetadata> {
|
||||
|
||||
/**
|
||||
* @see BlobMetadata#getKey()
|
||||
* @see BlobMetadata#getName()
|
||||
*/
|
||||
public String getKey() {
|
||||
return getMetadata().getKey();
|
||||
}
|
||||
String getName();
|
||||
|
||||
/**
|
||||
* Sets entity for the request or the content from the response. If size isn't set, this will
|
||||
|
@ -127,11 +54,7 @@ public class Blob<M extends BlobMetadata> implements Comparable<Blob<M>> {
|
|||
* typically InputStream for downloads, or File, byte [], String, or InputStream for
|
||||
* uploads.
|
||||
*/
|
||||
public void setData(Object data) {
|
||||
this.data = checkNotNull(data, "data");
|
||||
if (getMetadata().getSize() == -1)
|
||||
this.getMetadata().setSize(HttpUtils.calculateSize(data));
|
||||
}
|
||||
void setData(Object data);
|
||||
|
||||
/**
|
||||
* generate an MD5 Hash for the current data.
|
||||
|
@ -143,46 +66,19 @@ public class Blob<M extends BlobMetadata> implements Comparable<Blob<M>> {
|
|||
* @throws IOException
|
||||
* if there is a problem generating the hash.
|
||||
*/
|
||||
public void generateMD5() throws IOException {
|
||||
checkState(data != null, "data");
|
||||
if (data instanceof InputStream) {
|
||||
MD5InputStreamResult result = HttpUtils.generateMD5Result((InputStream) data);
|
||||
getMetadata().setSize(result.length);
|
||||
getMetadata().setContentMD5(result.eTag);
|
||||
setData(result.data);
|
||||
} else {
|
||||
getMetadata().setContentMD5(HttpUtils.md5(data));
|
||||
}
|
||||
}
|
||||
void generateMD5() throws IOException;
|
||||
|
||||
/**
|
||||
* @return InputStream, if downloading, or whatever was set during {@link #setData(Object)}
|
||||
*/
|
||||
public Object getData() {
|
||||
return data;
|
||||
}
|
||||
Object getData();
|
||||
|
||||
/**
|
||||
* @return System and User metadata relevant to this object.
|
||||
*/
|
||||
public M getMetadata() {
|
||||
return metadata;
|
||||
}
|
||||
M getMetadata();
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + (int) (contentLength ^ (contentLength >>> 32));
|
||||
result = prime * result + ((contentRange == null) ? 0 : contentRange.hashCode());
|
||||
result = prime * result + ((data == null) ? 0 : data.hashCode());
|
||||
result = prime * result + ((getMetadata() == null) ? 0 : getMetadata().hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
public void setContentLength(long contentLength) {
|
||||
this.contentLength = contentLength;
|
||||
}
|
||||
void setContentLength(long contentLength);
|
||||
|
||||
/**
|
||||
* Returns the total size of the downloaded object, or the chunk that's available.
|
||||
|
@ -194,13 +90,9 @@ public class Blob<M extends BlobMetadata> implements Comparable<Blob<M>> {
|
|||
* @see org.jclouds.http.HttpHeaders#CONTENT_LENGTH
|
||||
* @see GetObjectOptions
|
||||
*/
|
||||
public long getContentLength() {
|
||||
return contentLength;
|
||||
}
|
||||
long getContentLength();
|
||||
|
||||
public void setContentRange(String contentRange) {
|
||||
this.contentRange = contentRange;
|
||||
}
|
||||
void setContentRange(String contentRange);
|
||||
|
||||
/**
|
||||
* If this is not-null, {@link #getContentLength() } will the size of chunk of the Value available
|
||||
|
@ -209,16 +101,8 @@ public class Blob<M extends BlobMetadata> implements Comparable<Blob<M>> {
|
|||
* @see org.jclouds.http.HttpHeaders#CONTENT_RANGE
|
||||
* @see GetObjectOptions
|
||||
*/
|
||||
public String getContentRange() {
|
||||
return contentRange;
|
||||
}
|
||||
String getContentRange();
|
||||
|
||||
public void setMetadata(M metadata) {
|
||||
this.metadata = metadata;
|
||||
}
|
||||
|
||||
public int compareTo(Blob<M> o) {
|
||||
return (this == o) ? 0 : getKey().compareTo(o.getKey());
|
||||
}
|
||||
void setMetadata(M metadata);
|
||||
|
||||
}
|
|
@ -23,120 +23,23 @@
|
|||
*/
|
||||
package org.jclouds.blobstore.domain;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.Map;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.ws.rs.core.MediaType;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
import com.google.common.collect.HashMultimap;
|
||||
import com.google.common.collect.Maps;
|
||||
import com.google.common.collect.Multimap;
|
||||
import com.google.inject.ImplementedBy;
|
||||
|
||||
/**
|
||||
* System and user Metadata for the {@link Blob}.
|
||||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class BlobMetadata implements Comparable<BlobMetadata>, Serializable {
|
||||
/** The serialVersionUID */
|
||||
private static final long serialVersionUID = -5932618957134612231L;
|
||||
@ImplementedBy(BlobMetadataImpl.class)
|
||||
public interface BlobMetadata {
|
||||
|
||||
protected String key;
|
||||
protected String eTag;
|
||||
protected volatile long size = -1;
|
||||
private byte[] contentMD5;
|
||||
|
||||
protected Multimap<String, String> allHeaders = HashMultimap.create();
|
||||
protected Map<String, String> userMetadata = Maps.newHashMap();
|
||||
protected DateTime lastModified;
|
||||
protected String dataType = MediaType.APPLICATION_OCTET_STREAM;
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder builder = new StringBuilder();
|
||||
builder.append("BlobMetadata [key=").append(key).append(", eTag=").append(eTag).append(
|
||||
", lastModified=").append(lastModified).append(", size=").append(size).append(
|
||||
", dataType=").append(dataType).append(", userMetadata=").append(userMetadata)
|
||||
.append("]");
|
||||
return builder.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((dataType == null) ? 0 : dataType.hashCode());
|
||||
result = prime * result + ((eTag == null) ? 0 : eTag.hashCode());
|
||||
result = prime * result + ((key == null) ? 0 : key.hashCode());
|
||||
result = prime * result + ((lastModified == null) ? 0 : lastModified.hashCode());
|
||||
result = prime * result + (int) (size ^ (size >>> 32));
|
||||
result = prime * result + ((userMetadata == null) ? 0 : userMetadata.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
BlobMetadata other = (BlobMetadata) obj;
|
||||
if (dataType == null) {
|
||||
if (other.dataType != null)
|
||||
return false;
|
||||
} else if (!dataType.equals(other.dataType))
|
||||
return false;
|
||||
if (eTag == null) {
|
||||
if (other.eTag != null)
|
||||
return false;
|
||||
} else if (!eTag.equals(other.eTag))
|
||||
return false;
|
||||
if (key == null) {
|
||||
if (other.key != null)
|
||||
return false;
|
||||
} else if (!key.equals(other.key))
|
||||
return false;
|
||||
if (lastModified == null) {
|
||||
if (other.lastModified != null)
|
||||
return false;
|
||||
} else if (!lastModified.equals(other.lastModified))
|
||||
return false;
|
||||
if (size != other.size)
|
||||
return false;
|
||||
if (userMetadata == null) {
|
||||
if (other.userMetadata != null)
|
||||
return false;
|
||||
} else if (!userMetadata.equals(other.userMetadata))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Inject
|
||||
public BlobMetadata() {
|
||||
super();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param key
|
||||
* @see #getKey()
|
||||
*/
|
||||
public BlobMetadata(String key) {
|
||||
setKey(key);
|
||||
}
|
||||
|
||||
public void setKey(String key) {
|
||||
checkNotNull(key, "key");
|
||||
checkArgument(!key.startsWith("/"), "keys cannot start with /");
|
||||
this.key = key;
|
||||
}
|
||||
void setName(String key);
|
||||
|
||||
/**
|
||||
* The key is the handle that you assign to an object that allows you retrieve it later. A key is
|
||||
|
@ -145,30 +48,20 @@ public class BlobMetadata implements Comparable<BlobMetadata>, Serializable {
|
|||
*
|
||||
* @see <a href= "http://docs.amazonwebservices.com/AmazonHTTP/2006-03-01/UsingKeys.html" />
|
||||
*/
|
||||
public String getKey() {
|
||||
return key;
|
||||
}
|
||||
String getName();
|
||||
|
||||
public DateTime getLastModified() {
|
||||
return lastModified;
|
||||
}
|
||||
DateTime getLastModified();
|
||||
|
||||
public void setLastModified(DateTime lastModified) {
|
||||
this.lastModified = lastModified;
|
||||
}
|
||||
void setLastModified(DateTime lastModified);
|
||||
|
||||
/**
|
||||
* The size of the object, in bytes.
|
||||
*
|
||||
* @see <a href= "http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html?sec14.13." />
|
||||
*/
|
||||
public long getSize() {
|
||||
return size;
|
||||
}
|
||||
long getSize();
|
||||
|
||||
public void setSize(long size) {
|
||||
this.size = size;
|
||||
}
|
||||
void setSize(long size);
|
||||
|
||||
/**
|
||||
* A standard MIME type describing the format of the contents. If none is provided, the default
|
||||
|
@ -176,65 +69,28 @@ public class BlobMetadata implements Comparable<BlobMetadata>, Serializable {
|
|||
*
|
||||
* @see <a href= "http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html?sec14.17." />
|
||||
*/
|
||||
public String getContentType() {
|
||||
return dataType;
|
||||
}
|
||||
String getContentType();
|
||||
|
||||
public void setContentType(String dataType) {
|
||||
this.dataType = dataType;
|
||||
}
|
||||
void setContentType(String dataType);
|
||||
|
||||
public void setContentMD5(byte[] contentMD5) {
|
||||
if (contentMD5 != null) {
|
||||
this.contentMD5 = new byte[contentMD5.length];
|
||||
System.arraycopy(contentMD5, 0, this.contentMD5, 0, contentMD5.length);
|
||||
}
|
||||
}
|
||||
void setContentMD5(byte[] contentMD5);
|
||||
|
||||
public byte[] getContentMD5() {
|
||||
if (contentMD5 != null) {
|
||||
byte[] retval = new byte[contentMD5.length];
|
||||
System.arraycopy(this.contentMD5, 0, retval, 0, contentMD5.length);
|
||||
return retval;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
byte[] getContentMD5();
|
||||
|
||||
public void setETag(String eTag) {
|
||||
this.eTag = eTag;
|
||||
}
|
||||
void setETag(String eTag);
|
||||
|
||||
/**
|
||||
* @return the eTag value stored in the Etag header returned by HTTP.
|
||||
*/
|
||||
public String getETag() {
|
||||
return eTag;
|
||||
}
|
||||
String getETag();
|
||||
|
||||
public void setUserMetadata(Map<String, String> userMetadata) {
|
||||
this.userMetadata = userMetadata;
|
||||
}
|
||||
void setUserMetadata(Map<String, String> userMetadata);
|
||||
|
||||
/**
|
||||
* Any key-value pairs associated with the object.
|
||||
*/
|
||||
public Map<String, String> getUserMetadata() {
|
||||
return userMetadata;
|
||||
}
|
||||
Map<String, String> getUserMetadata();
|
||||
|
||||
public void setAllHeaders(Multimap<String, String> allHeaders) {
|
||||
this.allHeaders = allHeaders;
|
||||
}
|
||||
Multimap<String, String> getAllHeaders();
|
||||
|
||||
/**
|
||||
* @return all http response headers associated with this Value
|
||||
*/
|
||||
public Multimap<String, String> getAllHeaders() {
|
||||
return allHeaders;
|
||||
}
|
||||
|
||||
public int compareTo(BlobMetadata o) {
|
||||
return (this == o) ? 0 : getKey().compareTo(o.getKey());
|
||||
}
|
||||
}
|
|
@ -23,62 +23,20 @@
|
|||
*/
|
||||
package org.jclouds.blobstore.domain;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
|
||||
import com.google.inject.ImplementedBy;
|
||||
|
||||
/**
|
||||
* System metadata of the Container
|
||||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class ContainerMetadata implements Comparable<ContainerMetadata> {
|
||||
@ImplementedBy(ContainerMetadataImpl.class)
|
||||
public interface ContainerMetadata {
|
||||
|
||||
protected String name;
|
||||
void setName(String name);
|
||||
|
||||
/**
|
||||
* @see #getName()
|
||||
*/
|
||||
public ContainerMetadata(String name) {
|
||||
this.name = checkNotNull(name, "name");
|
||||
}
|
||||
String getName();
|
||||
|
||||
public ContainerMetadata() {
|
||||
super();
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = checkNotNull(name, "name");
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((name == null) ? 0 : name.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
ContainerMetadata other = (ContainerMetadata) obj;
|
||||
if (name == null) {
|
||||
if (other.name != null)
|
||||
return false;
|
||||
} else if (!name.equals(other.name))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
public int compareTo(ContainerMetadata o) {
|
||||
return (this == o) ? 0 : getName().compareTo(o.getName());
|
||||
}
|
||||
}
|
|
@ -28,11 +28,11 @@ import org.jclouds.blobstore.domain.BlobMetadata;
|
|||
|
||||
import com.google.common.base.Function;
|
||||
|
||||
public class BlobKey implements Function<Object, String> {
|
||||
public class BlobName implements Function<Object, String> {
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public String apply(Object from) {
|
||||
return ((Blob<BlobMetadata>) from).getKey();
|
||||
return ((Blob<BlobMetadata>) from).getName();
|
||||
}
|
||||
|
||||
}
|
|
@ -52,7 +52,7 @@ public class ParseContentTypeFromHeaders<M extends BlobMetadata> implements
|
|||
public M apply(HttpResponse from) {
|
||||
String objectKey = getKeyFor(from);
|
||||
M to = metadataFactory.get();
|
||||
to.setKey(objectKey);
|
||||
to.setName(objectKey);
|
||||
addAllHeadersTo(from, to);
|
||||
setContentTypeOrThrowException(from, to);
|
||||
return to;
|
||||
|
|
|
@ -140,7 +140,7 @@ public abstract class BaseBlobMap<C extends ContainerMetadata, M extends BlobMet
|
|||
public Set<String> keySet() {
|
||||
Set<String> keys = Sets.newHashSet();
|
||||
for (BlobMetadata object : getAllBlobMetadata.execute(connection, containerName))
|
||||
keys.add(object.getKey());
|
||||
keys.add(object.getName());
|
||||
return keys;
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,226 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (C) 2009 Global Cloud Specialists, Inc. <info@globalcloudspecialists.com>
|
||||
*
|
||||
* ====================================================================
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
* ====================================================================
|
||||
*/
|
||||
package org.jclouds.blobstore.internal;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
import static com.google.common.base.Preconditions.checkState;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.http.HttpUtils;
|
||||
import org.jclouds.http.HttpUtils.MD5InputStreamResult;
|
||||
|
||||
/**
|
||||
* Value type for an HTTP Blob service. Blobs are stored in {@link ContainerMetadata containers} and consist
|
||||
* of a {@link org.jclouds.blobstore.domain.Value#getData() value}, a {@link Blob#getKey key and
|
||||
*
|
||||
* @link Blob.Metadata#getUserMetadata() metadata}
|
||||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class BlobImpl<M extends BlobMetadata> implements Blob<M>, Comparable<Blob<M>> {
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
BlobImpl<M> other = (BlobImpl<M>) obj;
|
||||
if (contentLength != other.contentLength)
|
||||
return false;
|
||||
if (contentRange == null) {
|
||||
if (other.contentRange != null)
|
||||
return false;
|
||||
} else if (!contentRange.equals(other.contentRange))
|
||||
return false;
|
||||
if (data == null) {
|
||||
if (other.data != null)
|
||||
return false;
|
||||
} else if (!data.equals(other.data))
|
||||
return false;
|
||||
if (getMetadata() == null) {
|
||||
if (other.getMetadata() != null)
|
||||
return false;
|
||||
} else if (!getMetadata().equals(other.getMetadata()))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Blob [contentLength=" + contentLength + ", contentRange=" + contentRange + ", data="
|
||||
+ data + ", metadata=" + getMetadata() + "]";
|
||||
}
|
||||
|
||||
protected Object data;
|
||||
private M metadata;
|
||||
protected long contentLength = -1;
|
||||
protected String contentRange;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public BlobImpl(String key) {
|
||||
// TODO: why are we getting a generic warning here?
|
||||
this((M) new BlobMetadataImpl(key));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Inject
|
||||
public BlobImpl() {
|
||||
this((M) new BlobMetadataImpl());
|
||||
}
|
||||
|
||||
public BlobImpl(M metadata) {
|
||||
this.setMetadata(metadata);
|
||||
}
|
||||
|
||||
public BlobImpl(M metadata, Object data) {
|
||||
this(metadata);
|
||||
setData(data);
|
||||
}
|
||||
|
||||
public BlobImpl(String key, Object data) {
|
||||
this(key);
|
||||
setData(data);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see BlobMetadata#getName()
|
||||
*/
|
||||
public String getName() {
|
||||
return getMetadata().getName();
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets entity for the request or the content from the response. If size isn't set, this will
|
||||
* attempt to discover it.
|
||||
*
|
||||
* @param data
|
||||
* typically InputStream for downloads, or File, byte [], String, or InputStream for
|
||||
* uploads.
|
||||
*/
|
||||
public void setData(Object data) {
|
||||
this.data = checkNotNull(data, "data");
|
||||
if (getMetadata().getSize() == -1)
|
||||
this.getMetadata().setSize(HttpUtils.calculateSize(data));
|
||||
}
|
||||
|
||||
/**
|
||||
* generate an MD5 Hash for the current data.
|
||||
* <p/>
|
||||
* <h2>Note</h2>
|
||||
* <p/>
|
||||
* If this is an InputStream, it will be converted to a byte array first.
|
||||
*
|
||||
* @throws IOException
|
||||
* if there is a problem generating the hash.
|
||||
*/
|
||||
public void generateMD5() throws IOException {
|
||||
checkState(data != null, "data");
|
||||
if (data instanceof InputStream) {
|
||||
MD5InputStreamResult result = HttpUtils.generateMD5Result((InputStream) data);
|
||||
getMetadata().setSize(result.length);
|
||||
getMetadata().setContentMD5(result.eTag);
|
||||
setData(result.data);
|
||||
} else {
|
||||
getMetadata().setContentMD5(HttpUtils.md5(data));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return InputStream, if downloading, or whatever was set during {@link #setData(Object)}
|
||||
*/
|
||||
public Object getData() {
|
||||
return data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return System and User metadata relevant to this object.
|
||||
*/
|
||||
public M getMetadata() {
|
||||
return metadata;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + (int) (contentLength ^ (contentLength >>> 32));
|
||||
result = prime * result + ((contentRange == null) ? 0 : contentRange.hashCode());
|
||||
result = prime * result + ((data == null) ? 0 : data.hashCode());
|
||||
result = prime * result + ((getMetadata() == null) ? 0 : getMetadata().hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
public void setContentLength(long contentLength) {
|
||||
this.contentLength = contentLength;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the total size of the downloaded object, or the chunk that's available.
|
||||
* <p/>
|
||||
* Chunking is only used when org.jclouds.http.GetOptions is called with options like tail,
|
||||
* range, or startAt.
|
||||
*
|
||||
* @return the length in bytes that can be be obtained from {@link #getData()}
|
||||
* @see org.jclouds.http.HttpHeaders#CONTENT_LENGTH
|
||||
* @see GetObjectOptions
|
||||
*/
|
||||
public long getContentLength() {
|
||||
return contentLength;
|
||||
}
|
||||
|
||||
public void setContentRange(String contentRange) {
|
||||
this.contentRange = contentRange;
|
||||
}
|
||||
|
||||
/**
|
||||
* If this is not-null, {@link #getContentLength() } will the size of chunk of the Value available
|
||||
* via {@link #getData()}
|
||||
*
|
||||
* @see org.jclouds.http.HttpHeaders#CONTENT_RANGE
|
||||
* @see GetObjectOptions
|
||||
*/
|
||||
public String getContentRange() {
|
||||
return contentRange;
|
||||
}
|
||||
|
||||
public void setMetadata(M metadata) {
|
||||
this.metadata = metadata;
|
||||
}
|
||||
|
||||
public int compareTo(Blob<M> o) {
|
||||
return (this == o) ? 0 : getName().compareTo(o.getName());
|
||||
}
|
||||
|
||||
}
|
|
@ -79,7 +79,7 @@ public class BlobMapImpl<C extends ContainerMetadata, M extends BlobMetadata, B
|
|||
public Set<java.util.Map.Entry<String, B>> entrySet() {
|
||||
Set<Map.Entry<String, B>> entrySet = new HashSet<Map.Entry<String, B>>();
|
||||
for (B value : values()) {
|
||||
Map.Entry<String, B> entry = new Entry(value.getKey(), value);
|
||||
Map.Entry<String, B> entry = new Entry(value.getName(), value);
|
||||
entrySet.add(entry);
|
||||
}
|
||||
return entrySet;
|
||||
|
|
|
@ -0,0 +1,247 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (C) 2009 Global Cloud Specialists, Inc. <info@globalcloudspecialists.com>
|
||||
*
|
||||
* ====================================================================
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
* ====================================================================
|
||||
*/
|
||||
package org.jclouds.blobstore.internal;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.Arrays;
|
||||
import java.util.Map;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.ws.rs.core.MediaType;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
import com.google.common.collect.HashMultimap;
|
||||
import com.google.common.collect.Maps;
|
||||
import com.google.common.collect.Multimap;
|
||||
|
||||
/**
|
||||
* System and user Metadata for the {@link Blob}.
|
||||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class BlobMetadataImpl implements Serializable, BlobMetadata, Comparable<BlobMetadata> {
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
BlobMetadataImpl other = (BlobMetadataImpl) obj;
|
||||
if (!Arrays.equals(contentMD5, other.contentMD5))
|
||||
return false;
|
||||
if (dataType == null) {
|
||||
if (other.dataType != null)
|
||||
return false;
|
||||
} else if (!dataType.equals(other.dataType))
|
||||
return false;
|
||||
if (eTag == null) {
|
||||
if (other.eTag != null)
|
||||
return false;
|
||||
} else if (!eTag.equals(other.eTag))
|
||||
return false;
|
||||
if (name == null) {
|
||||
if (other.name != null)
|
||||
return false;
|
||||
} else if (!name.equals(other.name))
|
||||
return false;
|
||||
if (lastModified == null) {
|
||||
if (other.lastModified != null)
|
||||
return false;
|
||||
} else if (!lastModified.equals(other.lastModified))
|
||||
return false;
|
||||
if (size != other.size)
|
||||
return false;
|
||||
if (userMetadata == null) {
|
||||
if (other.userMetadata != null)
|
||||
return false;
|
||||
} else if (!userMetadata.equals(other.userMetadata))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
/** The serialVersionUID */
|
||||
private static final long serialVersionUID = -5932618957134612231L;
|
||||
|
||||
protected String name;
|
||||
protected String eTag;
|
||||
protected volatile long size = -1;
|
||||
private byte[] contentMD5;
|
||||
|
||||
protected Multimap<String, String> allHeaders = HashMultimap.create();
|
||||
protected Map<String, String> userMetadata = Maps.newHashMap();
|
||||
protected DateTime lastModified;
|
||||
protected String dataType = MediaType.APPLICATION_OCTET_STREAM;
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuilder builder = new StringBuilder();
|
||||
builder.append("BlobMetadata [name=").append(name).append(", eTag=").append(eTag).append(
|
||||
", lastModified=").append(lastModified).append(", size=").append(size).append(
|
||||
", dataType=").append(dataType).append(", userMetadata=").append(userMetadata)
|
||||
.append("]");
|
||||
return builder.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + Arrays.hashCode(contentMD5);
|
||||
result = prime * result + ((dataType == null) ? 0 : dataType.hashCode());
|
||||
result = prime * result + ((eTag == null) ? 0 : eTag.hashCode());
|
||||
result = prime * result + ((name == null) ? 0 : name.hashCode());
|
||||
result = prime * result + ((lastModified == null) ? 0 : lastModified.hashCode());
|
||||
result = prime * result + (int) (size ^ (size >>> 32));
|
||||
result = prime * result + ((userMetadata == null) ? 0 : userMetadata.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Inject
|
||||
public BlobMetadataImpl() {
|
||||
super();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param name
|
||||
* @see #getKey()
|
||||
*/
|
||||
public BlobMetadataImpl(String name) {
|
||||
setName(name);
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
checkNotNull(name, "name");
|
||||
checkArgument(!name.startsWith("/"), "names cannot start with /");
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
/**
|
||||
* The name is the handle that you assign to an object that allows you retrieve it later. A name
|
||||
* is a sequence of Unicode characters whose UTF-8 encoding is at most 1024 bytes long. Each
|
||||
* object in a bucket must have a unique name.
|
||||
*
|
||||
* @see <a href= "http://docs.amazonwebservices.com/AmazonHTTP/2006-03-01/UsingKeys.html" />
|
||||
*/
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public DateTime getLastModified() {
|
||||
return lastModified;
|
||||
}
|
||||
|
||||
public void setLastModified(DateTime lastModified) {
|
||||
this.lastModified = lastModified;
|
||||
}
|
||||
|
||||
/**
|
||||
* The size of the object, in bytes.
|
||||
*
|
||||
* @see <a href= "http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html?sec14.13." />
|
||||
*/
|
||||
public long getSize() {
|
||||
return size;
|
||||
}
|
||||
|
||||
public void setSize(long size) {
|
||||
this.size = size;
|
||||
}
|
||||
|
||||
/**
|
||||
* A standard MIME type describing the format of the contents. If none is provided, the default
|
||||
* is binary/octet-stream.
|
||||
*
|
||||
* @see <a href= "http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html?sec14.17." />
|
||||
*/
|
||||
public String getContentType() {
|
||||
return dataType;
|
||||
}
|
||||
|
||||
public void setContentType(String dataType) {
|
||||
this.dataType = dataType;
|
||||
}
|
||||
|
||||
public void setContentMD5(byte[] contentMD5) {
|
||||
if (contentMD5 != null) {
|
||||
this.contentMD5 = new byte[contentMD5.length];
|
||||
System.arraycopy(contentMD5, 0, this.contentMD5, 0, contentMD5.length);
|
||||
}
|
||||
}
|
||||
|
||||
public byte[] getContentMD5() {
|
||||
if (contentMD5 != null) {
|
||||
byte[] retval = new byte[contentMD5.length];
|
||||
System.arraycopy(this.contentMD5, 0, retval, 0, contentMD5.length);
|
||||
return retval;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public void setETag(String eTag) {
|
||||
this.eTag = eTag;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the eTag value stored in the Etag header returned by HTTP.
|
||||
*/
|
||||
public String getETag() {
|
||||
return eTag;
|
||||
}
|
||||
|
||||
public void setUserMetadata(Map<String, String> userMetadata) {
|
||||
this.userMetadata = userMetadata;
|
||||
}
|
||||
|
||||
/**
|
||||
* Any key-value pairs associated with the object.
|
||||
*/
|
||||
public Map<String, String> getUserMetadata() {
|
||||
return userMetadata;
|
||||
}
|
||||
|
||||
public void setAllHeaders(Multimap<String, String> allHeaders) {
|
||||
this.allHeaders = allHeaders;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return all http response headers associated with this Value
|
||||
*/
|
||||
public Multimap<String, String> getAllHeaders() {
|
||||
return allHeaders;
|
||||
}
|
||||
|
||||
public int compareTo(BlobMetadata o) {
|
||||
return (this == o) ? 0 : getName().compareTo(o.getName());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,86 @@
|
|||
/**
|
||||
*
|
||||
* Copyright (C) 2009 Global Cloud Specialists, Inc. <info@globalcloudspecialists.com>
|
||||
*
|
||||
* ====================================================================
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
* ====================================================================
|
||||
*/
|
||||
package org.jclouds.blobstore.internal;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
|
||||
/**
|
||||
* System metadata of the Container
|
||||
*
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class ContainerMetadataImpl implements ContainerMetadata, Comparable<ContainerMetadata> {
|
||||
|
||||
protected String name;
|
||||
|
||||
/**
|
||||
* @see #getName()
|
||||
*/
|
||||
public ContainerMetadataImpl(String name) {
|
||||
this.name = checkNotNull(name, "name");
|
||||
}
|
||||
|
||||
public ContainerMetadataImpl() {
|
||||
super();
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = checkNotNull(name, "name");
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((name == null) ? 0 : name.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj)
|
||||
return true;
|
||||
if (obj == null)
|
||||
return false;
|
||||
if (getClass() != obj.getClass())
|
||||
return false;
|
||||
ContainerMetadataImpl other = (ContainerMetadataImpl) obj;
|
||||
if (name == null) {
|
||||
if (other.name != null)
|
||||
return false;
|
||||
} else if (!name.equals(other.name))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
public int compareTo(ContainerMetadata o) {
|
||||
return (this == o) ? 0 : getName().compareTo(o.getName());
|
||||
}
|
||||
}
|
|
@ -144,7 +144,7 @@ public class InputStreamMapImpl<C extends ContainerMetadata, M extends BlobMetad
|
|||
public Set<Map.Entry<String, InputStream>> entrySet() {
|
||||
Set<Map.Entry<String, InputStream>> entrySet = new HashSet<Map.Entry<String, InputStream>>();
|
||||
for (B object : this.getAllBlobs.execute(connection, containerName)) {
|
||||
entrySet.add(new Entry(object.getKey(), (InputStream) object.getData()));
|
||||
entrySet.add(new Entry(object.getName(), (InputStream) object.getData()));
|
||||
}
|
||||
return entrySet;
|
||||
}
|
||||
|
@ -226,7 +226,7 @@ public class InputStreamMapImpl<C extends ContainerMetadata, M extends BlobMetad
|
|||
Set<Future<String>> puts = Sets.newHashSet();
|
||||
for (Map.Entry<? extends String, ? extends Object> entry : map.entrySet()) {
|
||||
B object = blobFactory.get();
|
||||
object.getMetadata().setKey(entry.getKey());
|
||||
object.getMetadata().setName(entry.getKey());
|
||||
object.setData(entry.getValue());
|
||||
object.generateMD5();
|
||||
puts.add(connection.putBlob(containerName, object));
|
||||
|
@ -288,7 +288,7 @@ public class InputStreamMapImpl<C extends ContainerMetadata, M extends BlobMetad
|
|||
@VisibleForTesting
|
||||
InputStream putInternal(String s, Object o) {
|
||||
B object = blobFactory.get();
|
||||
object.getMetadata().setKey(s);
|
||||
object.getMetadata().setName(s);
|
||||
try {
|
||||
InputStream returnVal = containsKey(s) ? get(s) : null;
|
||||
object.setData(o);
|
||||
|
|
|
@ -65,7 +65,7 @@ public class DeleteAllKeysClearContainerStrategy<C extends ContainerMetadata, M
|
|||
public void execute(BlobStore<C, M, B> connection, final String containerName) {
|
||||
Set<Future<Void>> deletes = Sets.newHashSet();
|
||||
for (M md : getAllBlobMetadata.execute(connection, containerName)) {
|
||||
deletes.add(connection.removeBlob(containerName, md.getKey()));
|
||||
deletes.add(connection.removeBlob(containerName, md.getName()));
|
||||
}
|
||||
for (Future<Void> isdeleted : deletes) {
|
||||
try {
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
*/
|
||||
package org.jclouds.blobstore.strategy.internal;
|
||||
|
||||
import java.util.Comparator;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.SortedSet;
|
||||
|
@ -78,10 +79,16 @@ public class RetryOnNotFoundGetAllBlobsStrategy<C extends ContainerMetadata, M e
|
|||
}
|
||||
|
||||
public SortedSet<B> execute(BlobStore<C, M, B> connection, String container) {
|
||||
SortedSet<B> objects = Sets.<B> newTreeSet();
|
||||
SortedSet<B> objects = Sets.<B> newTreeSet(new Comparator<B>() {
|
||||
|
||||
public int compare(B o1, B o2) {
|
||||
return (o1 == o2) ? 0 : o1.getName().compareTo(o2.getName());
|
||||
}
|
||||
|
||||
});
|
||||
Map<String, Future<B>> futureObjects = Maps.newHashMap();
|
||||
for (M md : getAllBlobMetadata.execute(connection, container)) {
|
||||
futureObjects.put(md.getKey(), connection.getBlob(container, md.getKey()));
|
||||
futureObjects.put(md.getName(), connection.getBlob(container, md.getName()));
|
||||
}
|
||||
for (Entry<String, Future<B>> futureObjectEntry : futureObjects.entrySet()) {
|
||||
try {
|
||||
|
@ -103,7 +110,7 @@ public class RetryOnNotFoundGetAllBlobsStrategy<C extends ContainerMetadata, M e
|
|||
for (int i = 0; i < 3; i++) {
|
||||
try {
|
||||
B object = value.get(requestTimeoutMilliseconds, TimeUnit.MILLISECONDS);
|
||||
object.getMetadata().setKey(key);
|
||||
object.getMetadata().setName(key);
|
||||
objects.add(object);
|
||||
return;
|
||||
} catch (KeyNotFoundException e) {
|
||||
|
|
|
@ -34,6 +34,7 @@ import javax.ws.rs.core.MediaType;
|
|||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.jclouds.http.HttpRequest;
|
||||
import org.jclouds.util.Utils;
|
||||
import org.testng.annotations.Test;
|
||||
|
@ -55,7 +56,7 @@ public class BindBlobToMultipartFormTest {
|
|||
addData(BOUNDRY, "hello", builder);
|
||||
builder.append("--").append(BOUNDRY).append("--").append("\r\n");
|
||||
EXPECTS = builder.toString();
|
||||
TEST_BLOB = new Blob<BlobMetadata>("hello");
|
||||
TEST_BLOB = new BlobImpl<BlobMetadata>("hello");
|
||||
TEST_BLOB.setData("hello");
|
||||
TEST_BLOB.getMetadata().setContentType(MediaType.TEXT_PLAIN);
|
||||
}
|
||||
|
|
|
@ -29,6 +29,7 @@ import java.io.File;
|
|||
|
||||
import javax.ws.rs.core.MediaType;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
@Test(groups = "unit", testName = "blobstore.BlobTest")
|
||||
|
@ -36,7 +37,7 @@ public class BlobTest {
|
|||
|
||||
@Test
|
||||
void testSetNoContentType() {
|
||||
Blob<BlobMetadata> object = new Blob<BlobMetadata>("test");
|
||||
Blob<BlobMetadata> object = new BlobImpl<BlobMetadata>("test");
|
||||
File file = new File("hello.txt");
|
||||
object.setData(file);
|
||||
assertEquals(object.getMetadata().getContentType(), MediaType.APPLICATION_OCTET_STREAM);
|
||||
|
|
|
@ -36,6 +36,7 @@ import javax.ws.rs.core.HttpHeaders;
|
|||
import org.apache.commons.io.IOUtils;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.jclouds.http.HttpException;
|
||||
import org.jclouds.http.HttpResponse;
|
||||
import org.testng.annotations.Test;
|
||||
|
@ -65,7 +66,7 @@ public class ParseBlobFromHeadersAndHttpContentTest {
|
|||
private Provider<Blob<BlobMetadata>> blobProvider = new Provider<Blob<BlobMetadata>>() {
|
||||
|
||||
public Blob<BlobMetadata> get() {
|
||||
return new Blob<BlobMetadata>("key");
|
||||
return new BlobImpl<BlobMetadata>("key");
|
||||
}
|
||||
|
||||
};
|
||||
|
|
|
@ -36,6 +36,7 @@ import javax.ws.rs.core.HttpHeaders;
|
|||
import javax.ws.rs.core.MediaType;
|
||||
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.jclouds.http.HttpException;
|
||||
import org.jclouds.http.HttpResponse;
|
||||
import org.jclouds.rest.internal.GeneratedHttpRequest;
|
||||
|
@ -52,7 +53,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
private Provider<BlobMetadata> blobMetadataProvider = new Provider<BlobMetadata>() {
|
||||
|
||||
public BlobMetadata get() {
|
||||
return new BlobMetadata("key");
|
||||
return new BlobMetadataImpl("key");
|
||||
}
|
||||
|
||||
};
|
||||
|
@ -74,7 +75,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
Multimap<String, String> allHeaders = ImmutableMultimap.of("key", "value");
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.setHeaders(allHeaders);
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.addAllHeadersTo(from, metadata);
|
||||
assertEquals(metadata.getAllHeaders().get("key"), Collections.singletonList("value"));
|
||||
}
|
||||
|
@ -86,14 +87,14 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
from.getHeaders().put(HttpHeaders.LAST_MODIFIED, "Wed, 09 Sep 2009 19:50:23 GMT");
|
||||
from.getHeaders().put(HttpHeaders.CONTENT_LENGTH, "100");
|
||||
BlobMetadata metadata = parser.apply(from);
|
||||
assertEquals(metadata.getKey(), "key");
|
||||
assertEquals(metadata.getName(), "key");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSetContentLength() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.getHeaders().put(HttpHeaders.CONTENT_LENGTH, "100");
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.setContentLengthOrThrowException(from, metadata);
|
||||
assertEquals(metadata.getSize(), 100);
|
||||
}
|
||||
|
@ -101,7 +102,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
@Test(expectedExceptions = HttpException.class)
|
||||
public void testSetContentLengthException() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.setContentLengthOrThrowException(from, metadata);
|
||||
}
|
||||
|
||||
|
@ -109,7 +110,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
public void testSetContentType() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.getHeaders().put(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON);
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.setContentTypeOrThrowException(from, metadata);
|
||||
assertEquals(metadata.getContentType(), MediaType.APPLICATION_JSON);
|
||||
}
|
||||
|
@ -117,7 +118,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
@Test(expectedExceptions = HttpException.class)
|
||||
public void testSetContentTypeException() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.setContentTypeOrThrowException(from, metadata);
|
||||
}
|
||||
|
||||
|
@ -125,7 +126,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
public void testSetLastModified() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.getHeaders().put(HttpHeaders.LAST_MODIFIED, "Wed, 09 Sep 2009 19:50:23 GMT");
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.parseLastModifiedOrThrowException(from, metadata);
|
||||
assertEquals(metadata.getLastModified(), new DateService()
|
||||
.rfc822DateParse("Wed, 09 Sep 2009 19:50:23 GMT"));
|
||||
|
@ -134,7 +135,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
@Test(expectedExceptions = HttpException.class)
|
||||
public void testSetLastModifiedException() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.parseLastModifiedOrThrowException(from, metadata);
|
||||
}
|
||||
|
||||
|
@ -142,7 +143,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
public void testAddETagTo() {
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.getHeaders().put(HttpHeaders.ETAG, "0xfeb");
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.addETagTo(from, metadata);
|
||||
assertEquals(metadata.getETag(), "0xfeb");
|
||||
}
|
||||
|
@ -152,7 +153,7 @@ public class ParseBlobMetadataFromHeadersTest {
|
|||
Multimap<String, String> allHeaders = ImmutableMultimap.of("prefix" + "key", "value");
|
||||
HttpResponse from = new HttpResponse();
|
||||
from.setHeaders(allHeaders);
|
||||
BlobMetadata metadata = new BlobMetadata("test");
|
||||
BlobMetadata metadata = new BlobMetadataImpl("test");
|
||||
parser.addUserMetadataTo(from, metadata);
|
||||
assertEquals(metadata.getUserMetadata().get("key"), "value");
|
||||
}
|
||||
|
|
|
@ -26,8 +26,8 @@ package org.jclouds.blobstore.integration;
|
|||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseBlobIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -37,6 +37,6 @@ import org.testng.annotations.Test;
|
|||
*/
|
||||
@Test(groups = { "integration"}, testName = "blobstore.StubBlobIntegrationTest")
|
||||
public class StubBlobIntegrationTest extends
|
||||
BaseBlobIntegrationTest<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>> {
|
||||
BaseBlobIntegrationTest<BlobStore<ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>> {
|
||||
|
||||
}
|
|
@ -26,8 +26,8 @@ package org.jclouds.blobstore.integration;
|
|||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseBlobMapIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -36,6 +36,6 @@ import org.testng.annotations.Test;
|
|||
|
||||
@Test(groups = { "integration", "live" }, testName = "blobstore.StubBlobMapIntegrationTest")
|
||||
public class StubBlobMapIntegrationTest extends
|
||||
BaseBlobMapIntegrationTest<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>> {
|
||||
BaseBlobMapIntegrationTest<BlobStore<ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>> {
|
||||
|
||||
}
|
|
@ -26,8 +26,8 @@ package org.jclouds.blobstore.integration;
|
|||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseContainerIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -37,6 +37,6 @@ import org.testng.annotations.Test;
|
|||
@Test(groups = { "integration", "live" }, testName = "blobstore.StubContainerIntegrationTest")
|
||||
public class StubContainerIntegrationTest
|
||||
extends
|
||||
BaseContainerIntegrationTest<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>> {
|
||||
BaseContainerIntegrationTest<BlobStore<ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>> {
|
||||
|
||||
}
|
|
@ -26,8 +26,8 @@ package org.jclouds.blobstore.integration;
|
|||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseInputStreamMapIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -35,6 +35,6 @@ import org.testng.annotations.Test;
|
|||
*/
|
||||
@Test(groups = { "integration", "live" }, testName = "blobstore.StubInputStreamMapIntegrationTest")
|
||||
public class StubInputStreamMapIntegrationTest extends
|
||||
BaseInputStreamMapIntegrationTest<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>> {
|
||||
BaseInputStreamMapIntegrationTest<BlobStore<ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>> {
|
||||
|
||||
}
|
|
@ -26,8 +26,8 @@ package org.jclouds.blobstore.integration;
|
|||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseServiceIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -36,6 +36,6 @@ import org.testng.annotations.Test;
|
|||
@Test(groups = { "integration", "live" }, testName = "blobstore.StubServiceIntegrationTest")
|
||||
public class StubServiceIntegrationTest
|
||||
extends
|
||||
BaseServiceIntegrationTest<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>> {
|
||||
BaseServiceIntegrationTest<BlobStore<ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadataImpl, BlobMetadata, Blob<BlobMetadata>> {
|
||||
|
||||
}
|
|
@ -46,8 +46,11 @@ public class StubBlobStoreConnectionModule extends AbstractModule {
|
|||
protected void configure() {
|
||||
bind(new TypeLiteral<Map<String, Map<String, Blob<BlobMetadata>>>>() {
|
||||
}).toInstance(map);
|
||||
bind(new TypeLiteral<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
}).to(new TypeLiteral<StubBlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
}).asEagerSingleton();
|
||||
bind(
|
||||
new TypeLiteral<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
})
|
||||
.to(
|
||||
new TypeLiteral<StubBlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
}).asEagerSingleton();
|
||||
}
|
||||
}
|
|
@ -357,7 +357,7 @@ public class BaseBlobIntegrationTest<S, C extends ContainerMetadata, M extends B
|
|||
try {
|
||||
assertNotNull(context.getBlobStore().putBlob(containerName, object).get(30,
|
||||
TimeUnit.SECONDS));
|
||||
object = context.getBlobStore().getBlob(containerName, object.getKey()).get(30,
|
||||
object = context.getBlobStore().getBlob(containerName, object.getName()).get(30,
|
||||
TimeUnit.SECONDS);
|
||||
String returnedString = BlobStoreUtils.getContentAsStringAndClose(object);
|
||||
assertEquals(returnedString, realObject);
|
||||
|
|
|
@ -168,11 +168,11 @@ public class BaseBlobMapIntegrationTest<S, C extends ContainerMetadata, M extend
|
|||
B object = context.newBlob("one");
|
||||
object.setData(IOUtils.toInputStream("apple"));
|
||||
object.generateMD5();
|
||||
B old = map.put(object.getKey(), object);
|
||||
B old = map.put(object.getName(), object);
|
||||
getOneReturnsAppleAndOldValueIsNull(map, old);
|
||||
object.setData(IOUtils.toInputStream("bear"));
|
||||
object.generateMD5();
|
||||
B apple = map.put(object.getKey(), object);
|
||||
B apple = map.put(object.getName(), object);
|
||||
getOneReturnsBearAndOldValueIsApple(map, apple);
|
||||
} finally {
|
||||
returnContainer(bucketName);
|
||||
|
|
|
@ -43,6 +43,7 @@ import org.jclouds.blobstore.BlobStoreContext;
|
|||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.jclouds.blobstore.util.BlobStoreUtils;
|
||||
import org.jclouds.http.config.JavaUrlHttpCommandExecutorServiceModule;
|
||||
import org.jclouds.util.Utils;
|
||||
|
@ -166,10 +167,10 @@ public class BaseBlobStoreIntegrationTest<S, C extends ContainerMetadata, M exte
|
|||
throws Exception {
|
||||
try {
|
||||
for (int i = 0; i < 2; i++) {
|
||||
Iterable<ContainerMetadata> testContainers = Iterables.filter(
|
||||
(SortedSet<ContainerMetadata>) context.getBlobStore().listContainers(),
|
||||
new Predicate<ContainerMetadata>() {
|
||||
public boolean apply(ContainerMetadata input) {
|
||||
Iterable<ContainerMetadataImpl> testContainers = Iterables.filter(
|
||||
(SortedSet<ContainerMetadataImpl>) context.getBlobStore().listContainers(),
|
||||
new Predicate<ContainerMetadataImpl>() {
|
||||
public boolean apply(ContainerMetadataImpl input) {
|
||||
return input.getName().startsWith(CONTAINER_PREFIX.toLowerCase());
|
||||
}
|
||||
});
|
||||
|
|
|
@ -28,6 +28,7 @@ import java.util.SortedSet;
|
|||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.internal.ContainerMetadataImpl;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
|
@ -40,7 +41,7 @@ public class BaseServiceIntegrationTest<S, C extends ContainerMetadata, M extend
|
|||
@Test(groups = { "integration", "live" })
|
||||
void containerDoesntExist() throws Exception {
|
||||
SortedSet<C> list = context.getBlobStore().listContainers();
|
||||
assert !list.contains(new ContainerMetadata("shouldntexist"));
|
||||
assert !list.contains(new ContainerMetadataImpl("shouldntexist"));
|
||||
}
|
||||
|
||||
}
|
|
@ -35,6 +35,7 @@ import java.io.ObjectInputStream;
|
|||
import java.io.ObjectOutput;
|
||||
import java.io.ObjectOutputStream;
|
||||
import java.util.Collection;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.SortedSet;
|
||||
|
@ -146,14 +147,22 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
|
||||
if (realContents == null)
|
||||
throw new ContainerNotFoundException(name);
|
||||
SortedSet<M> contents = Sets.newTreeSet(Iterables.transform(realContents.keySet(),
|
||||
SortedSet<M> contents = Sets.newTreeSet(new Comparator<M>() {
|
||||
|
||||
public int compare(M o1, M o2) {
|
||||
return (o1 == o2) ? 0 : o1.getName().compareTo(o2.getName());
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
Iterables.addAll(contents, Iterables.transform(realContents.keySet(),
|
||||
new Function<String, M>() {
|
||||
public M apply(String key) {
|
||||
return realContents.get(key).getMetadata();
|
||||
}
|
||||
}));
|
||||
|
||||
return Sets.newTreeSet(contents);
|
||||
return contents;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
@ -184,7 +193,7 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
|
||||
public M copy(M in, String newKey) {
|
||||
M newMd = copy(in);
|
||||
newMd.setKey(newKey);
|
||||
newMd.setName(newKey);
|
||||
return newMd;
|
||||
}
|
||||
|
||||
|
@ -257,7 +266,14 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
}
|
||||
|
||||
public SortedSet<C> listContainers() {
|
||||
return Sets.newTreeSet(Iterables.transform(getContainerToBlobs().keySet(),
|
||||
SortedSet<C> returnVal = Sets.newTreeSet(new Comparator<C>() {
|
||||
|
||||
public int compare(C o1, C o2) {
|
||||
return (o1 == o2) ? 0 : o1.getName().compareTo(o2.getName());
|
||||
}
|
||||
|
||||
});
|
||||
Iterables.addAll(returnVal, Iterables.transform(getContainerToBlobs().keySet(),
|
||||
new Function<String, C>() {
|
||||
public C apply(String name) {
|
||||
C cmd = containerMetaProvider.get();
|
||||
|
@ -266,6 +282,7 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
}
|
||||
|
||||
}));
|
||||
return returnVal;
|
||||
}
|
||||
|
||||
public Future<Boolean> createContainer(final String name) {
|
||||
|
@ -297,9 +314,9 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
|
||||
public boolean apply(M metadata) {
|
||||
if (prefix == null)
|
||||
return metadata.getKey().indexOf(delimiter) == -1;
|
||||
if (metadata.getKey().startsWith(prefix))
|
||||
return metadata.getKey().replaceFirst(prefix, "").indexOf(delimiter) == -1;
|
||||
return metadata.getName().indexOf(delimiter) == -1;
|
||||
if (metadata.getName().startsWith(prefix))
|
||||
return metadata.getName().replaceFirst(prefix, "").indexOf(delimiter) == -1;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -315,7 +332,7 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
}
|
||||
|
||||
public String apply(M metadata) {
|
||||
String working = metadata.getKey();
|
||||
String working = metadata.getName();
|
||||
|
||||
if (prefix != null) {
|
||||
if (working.startsWith(prefix)) {
|
||||
|
@ -401,7 +418,7 @@ public class StubBlobStore<C extends ContainerMetadata, M extends BlobMetadata,
|
|||
B blob = blobProvider.get();
|
||||
blob.setMetadata(newMd);
|
||||
blob.setData(data);
|
||||
container.put(object.getKey(), blob);
|
||||
container.put(object.getName(), blob);
|
||||
|
||||
// Set HTTP headers to match metadata
|
||||
newMd.getAllHeaders().put(HttpHeaders.LAST_MODIFIED,
|
||||
|
|
|
@ -30,7 +30,6 @@ import java.util.Map;
|
|||
import org.jclouds.blobstore.BlobMap;
|
||||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.BlobStoreContext;
|
||||
import org.jclouds.blobstore.BlobStoreContextImpl;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
|
@ -86,14 +85,14 @@ public class BaseBlobMapTest {
|
|||
|
||||
assertEquals(type4, type5);
|
||||
|
||||
TypeLiteral type6 = new TypeLiteral<BlobStoreContextImpl<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
TypeLiteral type6 = new TypeLiteral<BlobStoreContext<BlobStore<ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>, ContainerMetadata, BlobMetadata, Blob<BlobMetadata>>>() {
|
||||
};
|
||||
|
||||
TypeLiteral type7 = TypeLiteral.get(Types.newParameterizedType(BlobStoreContextImpl.class,
|
||||
Types.newParameterizedType(BlobStore.class, ContainerMetadata.class,
|
||||
BlobMetadata.class, Types.newParameterizedType(Blob.class,
|
||||
BlobMetadata.class)), ContainerMetadata.class, BlobMetadata.class,
|
||||
Types.newParameterizedType(Blob.class, BlobMetadata.class)));
|
||||
TypeLiteral type7 = TypeLiteral.get(Types.newParameterizedType(BlobStoreContext.class, Types
|
||||
.newParameterizedType(BlobStore.class, ContainerMetadata.class, BlobMetadata.class,
|
||||
Types.newParameterizedType(Blob.class, BlobMetadata.class)),
|
||||
ContainerMetadata.class, BlobMetadata.class, Types.newParameterizedType(Blob.class,
|
||||
BlobMetadata.class)));
|
||||
assertEquals(type6, type7);
|
||||
|
||||
}
|
||||
|
|
|
@ -25,7 +25,6 @@ package org.jclouds.blobstore.strategy.internal;
|
|||
|
||||
import static org.easymock.EasyMock.expect;
|
||||
import static org.easymock.classextension.EasyMock.createMock;
|
||||
import static org.easymock.classextension.EasyMock.createNiceMock;
|
||||
import static org.easymock.classextension.EasyMock.replay;
|
||||
|
||||
import java.util.HashSet;
|
||||
|
@ -40,6 +39,7 @@ import org.jclouds.blobstore.domain.Blob;
|
|||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.domain.ContainerMetadata;
|
||||
import org.jclouds.blobstore.integration.StubBlobStoreContextBuilder;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.testng.annotations.BeforeClass;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
|
@ -73,7 +73,7 @@ public class RetryOnNotFoundGetAllBlobsStrategyTest {
|
|||
public void testIfNotFoundRetryOtherwiseAddToSet() throws InterruptedException,
|
||||
ExecutionException, TimeoutException {
|
||||
Future<Blob<BlobMetadata>> futureObject = createMock(Future.class);
|
||||
Blob<BlobMetadata> object = new Blob<BlobMetadata>("key");
|
||||
Blob<BlobMetadata> object = new BlobImpl<BlobMetadata>("key");
|
||||
expect(futureObject.get(map.requestTimeoutMilliseconds, TimeUnit.MILLISECONDS)).andThrow(
|
||||
new KeyNotFoundException());
|
||||
expect(futureObject.get(map.requestTimeoutMilliseconds, TimeUnit.MILLISECONDS)).andReturn(
|
||||
|
@ -92,7 +92,7 @@ public class RetryOnNotFoundGetAllBlobsStrategyTest {
|
|||
public void testIfNotFoundRetryOtherwiseAddToSetButNeverGetsIt() throws InterruptedException,
|
||||
ExecutionException, TimeoutException {
|
||||
Future<Blob<BlobMetadata>> futureObject = createMock(Future.class);
|
||||
Blob object = createNiceMock(Blob.class);
|
||||
Blob object = createMock(Blob.class);
|
||||
expect(futureObject.get(map.requestTimeoutMilliseconds, TimeUnit.MILLISECONDS)).andThrow(
|
||||
new KeyNotFoundException()).atLeastOnce();
|
||||
replay(futureObject);
|
||||
|
|
|
@ -42,7 +42,7 @@ public class BindFileInfoToXmlEntity implements Binder {
|
|||
|
||||
public void bindToRequest(HttpRequest request, Object toBind) {
|
||||
Blob<?> blob = (Blob<?>) toBind;
|
||||
String bareKey = BlobStoreUtils.parseKey(new Key("trash", blob.getKey())).getKey();
|
||||
String bareKey = BlobStoreUtils.parseKey(new Key("trash", blob.getName())).getKey();
|
||||
String file = String.format(
|
||||
"<file><name>%s</name><mime_type>%s</mime_type><public>false</public></file>",
|
||||
bareKey, blob.getMetadata().getContentType());
|
||||
|
|
|
@ -32,7 +32,7 @@ import org.joda.time.DateTime;
|
|||
* @author Adrian Cole
|
||||
*
|
||||
*/
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.domain.ContainerMetadata implements
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.internal.ContainerMetadataImpl implements
|
||||
PCSObject {
|
||||
private URI url;
|
||||
private URI parent;
|
||||
|
|
|
@ -25,6 +25,7 @@ package org.jclouds.mezeo.pcs2.domain;
|
|||
|
||||
import java.net.URI;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.jclouds.mezeo.pcs2.util.PCSUtils;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
|
@ -33,7 +34,7 @@ import org.joda.time.DateTime;
|
|||
* @author Adrian Cole
|
||||
*
|
||||
*/
|
||||
public class FileMetadata extends org.jclouds.blobstore.domain.BlobMetadata {
|
||||
public class FileMetadata extends BlobMetadataImpl {
|
||||
/** The serialVersionUID */
|
||||
private static final long serialVersionUID = 1L;
|
||||
private URI url;
|
||||
|
@ -47,7 +48,7 @@ public class FileMetadata extends org.jclouds.blobstore.domain.BlobMetadata {
|
|||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "FileMetadata [key=" + key + ", created=" + created + ", isInProject=" + isInProject
|
||||
return "FileMetadata [key=" + name + ", created=" + created + ", isInProject=" + isInProject
|
||||
+ ", isPublic=" + isPublic + ", isShared=" + isShared + ", owner=" + owner
|
||||
+ ", url=" + url + ", version=" + version + ", allHeaders=" + allHeaders
|
||||
+ ", dataType=" + dataType + ", eTag=" + eTag + ", accessed="
|
||||
|
|
|
@ -23,11 +23,13 @@
|
|||
*/
|
||||
package org.jclouds.mezeo.pcs2.domain;
|
||||
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
|
||||
|
||||
/**
|
||||
* @author Adrian Cole
|
||||
*/
|
||||
public class PCSFile extends org.jclouds.blobstore.domain.Blob<FileMetadata> {
|
||||
public class PCSFile extends BlobImpl<FileMetadata> {
|
||||
|
||||
public PCSFile(FileMetadata metadata, FileMetadata data) {
|
||||
super(metadata, data);
|
||||
|
|
|
@ -89,7 +89,7 @@ public class AddMetadataAndReturnId implements Function<HttpResponse, String>,
|
|||
String container = request.getArgs()[0].toString();
|
||||
PCSFile file = (PCSFile) request.getArgs()[1];
|
||||
|
||||
Key key = new Key(container, file.getKey());
|
||||
Key key = new Key(container, file.getName());
|
||||
String id = checkNotNull(fileCache.get(key), String.format(
|
||||
"file %s should have an id in cache by now", key));
|
||||
|
||||
|
|
|
@ -87,7 +87,7 @@ public class CreateSubFolderIfNotExistsAndGetResourceId implements Function<Obje
|
|||
Object[] args = (Object[]) from;
|
||||
checkArgument(args[0] instanceof String, "arg[0] must be a container name");
|
||||
checkArgument(args[1] instanceof Blob, "arg[1] must be a pcsfile");
|
||||
Key key = BlobStoreUtils.parseKey(new Key(args[0].toString(), ((Blob) args[1]).getKey()));
|
||||
Key key = BlobStoreUtils.parseKey(new Key(args[0].toString(), ((Blob) args[1]).getName()));
|
||||
try {
|
||||
return finder.get(key.getContainer());
|
||||
} catch (ComputationException e) {
|
||||
|
|
|
@ -93,7 +93,7 @@ public class CreateSubFolderIfNotExistsAndNewFileResource implements Function<Ob
|
|||
URI newFile = connection.createFile(containerUri, file).get(
|
||||
this.requestTimeoutMilliseconds, TimeUnit.MILLISECONDS);
|
||||
String id = PCSUtils.getFileId(newFile);
|
||||
fileCache.put(new Key(container, file.getKey()), id);
|
||||
fileCache.put(new Key(container, file.getName()), id);
|
||||
return id;
|
||||
} catch (Exception e) {
|
||||
Utils.<ContainerNotFoundException> rethrowIfRuntimeOrSameType(e);
|
||||
|
|
|
@ -67,7 +67,7 @@ public class FindIdInFileList implements Function<Key, String> {
|
|||
String idForNameInListOrException(String container, String toFind,
|
||||
SortedSet<FileMetadata> response) {
|
||||
for (FileMetadata data : response) {
|
||||
if (toFind.equals(data.getKey())) {
|
||||
if (toFind.equals(data.getName())) {
|
||||
String path = data.getUrl().getPath();
|
||||
int indexAfterContainersSlash = path.indexOf("files/") + "files/".length();
|
||||
return path.substring(indexAfterContainersSlash);
|
||||
|
|
|
@ -202,7 +202,7 @@ public class PCSBlobStoreTest {
|
|||
return new StubBlobStore.FutureBase<URI>() {
|
||||
|
||||
public URI get() throws InterruptedException, ExecutionException {
|
||||
return URI.create("http://localhost/" + object.getKey());
|
||||
return URI.create("http://localhost/" + object.getName());
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -133,7 +133,7 @@ public class PCSConnectionLiveTest {
|
|||
connection.deleteFile(objectURI).get(10, TimeUnit.SECONDS);
|
||||
|
||||
// try sending it in 2 parts
|
||||
object.getMetadata().setKey("sad");
|
||||
object.getMetadata().setName("sad");
|
||||
objectURI = connection.createFile(container, object).get(30, TimeUnit.SECONDS);
|
||||
|
||||
object.setData(data.substring(0, 2));
|
||||
|
|
|
@ -47,7 +47,7 @@ import org.jclouds.concurrent.config.ExecutorServiceModule;
|
|||
import org.jclouds.http.config.JavaUrlHttpCommandExecutorServiceModule;
|
||||
import org.jclouds.http.filters.BasicAuthentication;
|
||||
import org.jclouds.http.functions.ParseSax;
|
||||
import org.jclouds.http.functions.ParseURIList;
|
||||
import org.jclouds.http.functions.ParseURIFromListOrLocationHeaderIf20x;
|
||||
import org.jclouds.http.functions.ReturnInputStream;
|
||||
import org.jclouds.http.functions.ReturnVoidIf2xx;
|
||||
import org.jclouds.logging.Logger;
|
||||
|
@ -108,7 +108,7 @@ public class PCSConnectionTest {
|
|||
.singletonList("application/vnd.csp.container-info+xml"));
|
||||
assertEquals(httpMethod.getEntity(), "<container><name>container</name></container>");
|
||||
assertEquals(processor.createResponseParser(method, httpMethod).getClass(),
|
||||
ParseURIList.class);
|
||||
ParseURIFromListOrLocationHeaderIf20x.class);
|
||||
// TODO check generic type of response parser
|
||||
}
|
||||
|
||||
|
@ -181,7 +181,7 @@ public class PCSConnectionTest {
|
|||
assertEquals(Utils.toStringAndClose((InputStream) httpMethod.getEntity()),
|
||||
BindBlobToMultipartFormTest.EXPECTS);
|
||||
assertEquals(processor.createResponseParser(method, httpMethod).getClass(),
|
||||
ParseURIList.class);
|
||||
ParseURIFromListOrLocationHeaderIf20x.class);
|
||||
}
|
||||
|
||||
public void testDownloadFile() throws SecurityException, NoSuchMethodException, IOException {
|
||||
|
|
|
@ -59,7 +59,7 @@ public class AssembleBlobFromBlobMetadataCallTest {
|
|||
replay(response);
|
||||
PCSFile file = callable.apply(response);
|
||||
assertEquals(file.getMetadata(), metadata);
|
||||
assertEquals(file.getKey(), "blob");
|
||||
assertEquals(file.getName(), "blob");
|
||||
assertEquals(file.getData(), data);
|
||||
assertEquals(file.getContentLength(), metadata.getSize());
|
||||
}
|
||||
|
|
|
@ -33,9 +33,9 @@ import java.util.concurrent.ExecutionException;
|
|||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.TimeoutException;
|
||||
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseBlobStoreIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.jclouds.logging.log4j.config.Log4JLoggingModule;
|
||||
import org.jclouds.nirvanix.sdn.domain.UploadInfo;
|
||||
import org.testng.annotations.BeforeGroups;
|
||||
|
@ -77,7 +77,7 @@ public class SDNConnectionLiveTest {
|
|||
assertNotNull(uploadInfo.getToken());
|
||||
|
||||
connection.upload(uploadInfo.getHost(), uploadInfo.getToken(), containerName,
|
||||
new Blob<BlobMetadata>("test.txt", "value")).get(30, TimeUnit.SECONDS);
|
||||
new BlobImpl<BlobMetadata>("test.txt", "value")).get(30, TimeUnit.SECONDS);
|
||||
|
||||
String metadataS = connection.getMetadata(containerName + "/test.txt").get(30,
|
||||
TimeUnit.SECONDS);
|
||||
|
|
|
@ -35,10 +35,10 @@ import javax.ws.rs.Path;
|
|||
import javax.ws.rs.PathParam;
|
||||
|
||||
import org.jclouds.blobstore.BlobStore;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntity;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ReturnVoidOnNotFoundOr404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
import org.jclouds.http.functions.ParseETagHeader;
|
||||
|
@ -113,7 +113,7 @@ public interface CloudFilesBlobStore extends
|
|||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putBlob(
|
||||
@PathParam("container") String container,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(BindBlobToEntity.class) Blob<BlobMetadata> object);
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(BindBlobToEntityAndUserMetadataToHeadersWithPrefix.class) Blob<BlobMetadata> object);
|
||||
|
||||
@GET
|
||||
@ResponseParser(ParseObjectFromHeadersAndHttpContent.class)
|
||||
|
|
|
@ -37,11 +37,11 @@ import javax.ws.rs.PUT;
|
|||
import javax.ws.rs.Path;
|
||||
import javax.ws.rs.PathParam;
|
||||
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntity;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.binders.BindMapToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.functions.BlobKey;
|
||||
import org.jclouds.blobstore.functions.BlobName;
|
||||
import org.jclouds.blobstore.functions.ThrowContainerNotFoundOn404;
|
||||
import org.jclouds.blobstore.functions.ThrowKeyNotFoundOn404;
|
||||
import org.jclouds.http.functions.ParseETagHeader;
|
||||
|
@ -205,7 +205,7 @@ public interface CloudFilesConnection {
|
|||
@ResponseParser(ParseETagHeader.class)
|
||||
Future<String> putObject(
|
||||
@PathParam("container") String container,
|
||||
@PathParam("key") @ParamParser(BlobKey.class) @BinderParam(BindBlobToEntity.class) Blob<BlobMetadata> object);
|
||||
@PathParam("key") @ParamParser(BlobName.class) @BinderParam(BindBlobToEntityAndUserMetadataToHeadersWithPrefix.class) Blob<BlobMetadata> object);
|
||||
|
||||
@GET
|
||||
@ResponseParser(ParseObjectFromHeadersAndHttpContent.class)
|
||||
|
|
|
@ -30,12 +30,12 @@ import javax.inject.Inject;
|
|||
import javax.inject.Named;
|
||||
import javax.ws.rs.core.HttpHeaders;
|
||||
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntity;
|
||||
import org.jclouds.blobstore.binders.BindBlobToEntityAndUserMetadataToHeadersWithPrefix;
|
||||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.http.HttpRequest;
|
||||
import org.jclouds.http.HttpUtils;
|
||||
|
||||
public class BindCFObjectAsEntity extends BindBlobToEntity {
|
||||
public class BindCFObjectAsEntity extends BindBlobToEntityAndUserMetadataToHeadersWithPrefix {
|
||||
@Inject
|
||||
public BindCFObjectAsEntity(@Named(PROPERTY_USER_METADATA_PREFIX) String metadataPrefix) {
|
||||
super(metadataPrefix);
|
||||
|
|
|
@ -28,7 +28,7 @@ package org.jclouds.rackspace.cloudfiles.domain;
|
|||
* @author James Murty
|
||||
*
|
||||
*/
|
||||
public class ContainerCDNMetadata extends org.jclouds.blobstore.domain.ContainerMetadata {
|
||||
public class ContainerCDNMetadata extends org.jclouds.blobstore.internal.ContainerMetadataImpl {
|
||||
|
||||
private long ttl;
|
||||
private boolean cdn_enabled;
|
||||
|
|
|
@ -28,7 +28,7 @@ package org.jclouds.rackspace.cloudfiles.domain;
|
|||
* @author Adrian Cole
|
||||
*
|
||||
*/
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.domain.ContainerMetadata {
|
||||
public class ContainerMetadata extends org.jclouds.blobstore.internal.ContainerMetadataImpl {
|
||||
private long count;
|
||||
private long bytes;
|
||||
|
||||
|
|
|
@ -27,11 +27,13 @@ import java.io.InputStream;
|
|||
import java.io.InputStreamReader;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.Comparator;
|
||||
import java.util.SortedSet;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.jclouds.http.HttpUtils;
|
||||
import org.jclouds.http.functions.ParseJson;
|
||||
import org.joda.time.DateTime;
|
||||
|
@ -76,10 +78,17 @@ public class ParseBlobMetadataListFromJsonResponse extends ParseJson<SortedSet<B
|
|||
try {
|
||||
SortedSet<CloudFilesMetadata> list = gson.fromJson(new InputStreamReader(stream, "UTF-8"),
|
||||
listType);
|
||||
return Sets.newTreeSet(Iterables.transform(list,
|
||||
SortedSet<BlobMetadata> returnVal = Sets.newTreeSet(new Comparator<BlobMetadata>() {
|
||||
|
||||
public int compare(BlobMetadata o1, BlobMetadata o2) {
|
||||
return (o1 == o2) ? 0 : o1.getName().compareTo(o2.getName());
|
||||
}
|
||||
|
||||
});
|
||||
Iterables.addAll(returnVal, Iterables.transform(list,
|
||||
new Function<CloudFilesMetadata, BlobMetadata>() {
|
||||
public BlobMetadata apply(CloudFilesMetadata from) {
|
||||
BlobMetadata metadata = new BlobMetadata(from.name);
|
||||
BlobMetadata metadata = new BlobMetadataImpl(from.name);
|
||||
metadata.setSize(from.bytes);
|
||||
metadata.setLastModified(from.last_modified);
|
||||
metadata.setContentType(from.content_type);
|
||||
|
@ -88,6 +97,7 @@ public class ParseBlobMetadataListFromJsonResponse extends ParseJson<SortedSet<B
|
|||
return metadata;
|
||||
}
|
||||
}));
|
||||
return returnVal;
|
||||
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
throw new RuntimeException("jclouds requires UTF-8 encoding", e);
|
||||
|
|
|
@ -40,6 +40,7 @@ import org.jclouds.blobstore.KeyNotFoundException;
|
|||
import org.jclouds.blobstore.domain.Blob;
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.integration.internal.BaseBlobStoreIntegrationTest;
|
||||
import org.jclouds.blobstore.internal.BlobImpl;
|
||||
import org.jclouds.http.HttpResponseException;
|
||||
import org.jclouds.http.HttpUtils;
|
||||
import org.jclouds.http.options.GetOptions;
|
||||
|
@ -277,7 +278,7 @@ public class CloudFilesConnectionLiveTest {
|
|||
assertTrue(connection.createContainer(containerName).get(10, TimeUnit.SECONDS));
|
||||
|
||||
// Test PUT with string data, ETag hash, and a piece of metadata
|
||||
Blob<BlobMetadata> object = new Blob<BlobMetadata>("object");
|
||||
Blob<BlobMetadata> object = new BlobImpl<BlobMetadata>("object");
|
||||
object.setData(data);
|
||||
object.setContentLength(data.length());
|
||||
object.generateMD5();
|
||||
|
@ -296,8 +297,8 @@ public class CloudFilesConnectionLiveTest {
|
|||
}
|
||||
|
||||
// Test HEAD of object
|
||||
BlobMetadata metadata = connection.getObjectMetadata(containerName, object.getKey());
|
||||
// TODO assertEquals(metadata.getKey(), object.getKey());
|
||||
BlobMetadata metadata = connection.getObjectMetadata(containerName, object.getName());
|
||||
// TODO assertEquals(metadata.getName(), object.getName());
|
||||
assertEquals(metadata.getSize(), data.length());
|
||||
assertEquals(metadata.getContentType(), "text/plain");
|
||||
assertEquals(HttpUtils.toHexString(md5), HttpUtils.toHexString(object.getMetadata()
|
||||
|
@ -310,7 +311,7 @@ public class CloudFilesConnectionLiveTest {
|
|||
Map<String, String> userMetadata = Maps.newHashMap();
|
||||
userMetadata.put("New-Metadata-1", "value-1");
|
||||
userMetadata.put("New-Metadata-2", "value-2");
|
||||
assertTrue(connection.setObjectMetadata(containerName, object.getKey(), userMetadata));
|
||||
assertTrue(connection.setObjectMetadata(containerName, object.getName(), userMetadata));
|
||||
|
||||
// Test GET of missing object
|
||||
try {
|
||||
|
@ -319,10 +320,10 @@ public class CloudFilesConnectionLiveTest {
|
|||
} catch (KeyNotFoundException e) {
|
||||
}
|
||||
// Test GET of object (including updated metadata)
|
||||
Blob<BlobMetadata> getBlob = connection.getObject(containerName, object.getKey()).get(120,
|
||||
Blob<BlobMetadata> getBlob = connection.getObject(containerName, object.getName()).get(120,
|
||||
TimeUnit.SECONDS);
|
||||
assertEquals(IOUtils.toString((InputStream) getBlob.getData()), data);
|
||||
// TODO assertEquals(getBlob.getKey(), object.getKey());
|
||||
// TODO assertEquals(getBlob.getName(), object.getName());
|
||||
assertEquals(getBlob.getContentLength(), data.length());
|
||||
assertEquals(getBlob.getMetadata().getContentType(), "text/plain");
|
||||
assertEquals(HttpUtils.toHexString(md5), HttpUtils.toHexString(getBlob.getMetadata()
|
||||
|
@ -345,7 +346,7 @@ public class CloudFilesConnectionLiveTest {
|
|||
|
||||
// Test PUT chunked/streamed upload with data of "unknown" length
|
||||
ByteArrayInputStream bais = new ByteArrayInputStream(data.getBytes("UTF-8"));
|
||||
object = new Blob<BlobMetadata>("chunked-object");
|
||||
object = new BlobImpl<BlobMetadata>("chunked-object");
|
||||
object.setData(bais);
|
||||
newEtag = connection.putObject(containerName, object).get(10, TimeUnit.SECONDS);
|
||||
assertEquals(HttpUtils.toHexString(md5), HttpUtils.toHexString(getBlob.getMetadata()
|
||||
|
@ -354,7 +355,7 @@ public class CloudFilesConnectionLiveTest {
|
|||
// Test GET with options
|
||||
// Non-matching ETag
|
||||
try {
|
||||
connection.getObject(containerName, object.getKey(),
|
||||
connection.getObject(containerName, object.getName(),
|
||||
GetOptions.Builder.ifETagDoesntMatch(newEtag)).get(120, TimeUnit.SECONDS);
|
||||
} catch (Exception e) {
|
||||
assertEquals(e.getCause().getClass(), HttpResponseException.class);
|
||||
|
@ -362,11 +363,12 @@ public class CloudFilesConnectionLiveTest {
|
|||
}
|
||||
|
||||
// Matching ETag
|
||||
getBlob = connection.getObject(containerName, object.getKey(),
|
||||
getBlob = connection.getObject(containerName, object.getName(),
|
||||
GetOptions.Builder.ifETagMatches(newEtag)).get(120, TimeUnit.SECONDS);
|
||||
assertEquals(getBlob.getMetadata().getETag(), newEtag);
|
||||
getBlob = connection.getObject(containerName, object.getKey(), GetOptions.Builder.startAt(8))
|
||||
.get(120, TimeUnit.SECONDS);
|
||||
getBlob = connection
|
||||
.getObject(containerName, object.getName(), GetOptions.Builder.startAt(8)).get(120,
|
||||
TimeUnit.SECONDS);
|
||||
assertEquals(IOUtils.toString((InputStream) getBlob.getData()), data.substring(8));
|
||||
|
||||
assertTrue(connection.removeObject(containerName, "object").get(10, TimeUnit.SECONDS));
|
||||
|
|
|
@ -29,6 +29,8 @@ import java.io.InputStream;
|
|||
import java.util.List;
|
||||
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.jclouds.http.HttpUtils;
|
||||
import org.jclouds.http.functions.config.ParserModule;
|
||||
import org.joda.time.DateTime;
|
||||
import org.testng.annotations.Test;
|
||||
|
@ -51,14 +53,16 @@ public class ParseBlobMetadataListFromJsonResponseTest {
|
|||
public void testApplyInputStream() {
|
||||
InputStream is = getClass().getResourceAsStream("/test_list_container.json");
|
||||
List<BlobMetadata> expects = Lists.newArrayList();
|
||||
BlobMetadata one = new BlobMetadata("test_obj_1");
|
||||
BlobMetadata one = new BlobMetadataImpl("test_obj_1");
|
||||
one.setETag("4281c348eaf83e70ddce0e07221c3d28");
|
||||
one.setContentMD5(HttpUtils.fromHexString(one.getETag()));
|
||||
one.setSize(14);
|
||||
one.setContentType("application/octet-stream");
|
||||
one.setLastModified(new DateTime("2009-02-03T05:26:32.612278"));
|
||||
expects.add(one);
|
||||
BlobMetadata two = new BlobMetadata("test_obj_2");
|
||||
BlobMetadata two = new BlobMetadataImpl("test_obj_2");
|
||||
two.setETag("b039efe731ad111bc1b0ef221c3849d0");
|
||||
two.setContentMD5(HttpUtils.fromHexString(two.getETag()));
|
||||
two.setSize(64);
|
||||
two.setContentType("application/octet-stream");
|
||||
two.setLastModified(new DateTime("2009-02-03T05:26:32.612278"));
|
||||
|
|
|
@ -29,6 +29,7 @@ import static org.testng.Assert.assertNotNull;
|
|||
import javax.inject.Provider;
|
||||
|
||||
import org.jclouds.blobstore.domain.BlobMetadata;
|
||||
import org.jclouds.blobstore.internal.BlobMetadataImpl;
|
||||
import org.jclouds.http.HttpResponse;
|
||||
import org.jclouds.util.DateService;
|
||||
import org.testng.annotations.Test;
|
||||
|
@ -45,7 +46,7 @@ public class ParseObjectMetadataFromHeadersTest {
|
|||
public void testEtagCaseIssue() {
|
||||
ParseObjectMetadataFromHeaders parser = new ParseObjectMetadataFromHeaders(
|
||||
createNiceMock(DateService.class), "", createNiceMock(Provider.class));
|
||||
BlobMetadata md = new BlobMetadata("hello");
|
||||
BlobMetadata md = new BlobMetadataImpl("hello");
|
||||
HttpResponse response = new HttpResponse();
|
||||
response.getHeaders().put("Etag", "feb1");
|
||||
parser.addETagTo(response, md);
|
||||
|
|
Loading…
Reference in New Issue