Skip to content

Commit

Permalink
Merge pull request #58 from aozarov/master
Browse files Browse the repository at this point in the history
add metadata update to example and fix builder user-settable fields
  • Loading branch information
jboynes committed May 14, 2015
2 parents 76776e3 + 0299172 commit 05e3f0a
Show file tree
Hide file tree
Showing 11 changed files with 433 additions and 94 deletions.
177 changes: 154 additions & 23 deletions src/main/java/com/google/gcloud/examples/StorageExample.java
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@
/**
* An example of using the Google Cloud Storage.
* <p>
* This example demonstrates a simple/typical usage.
* This example demonstrates a simple/typical storage usage.
* <p>
* Steps needed for running the example:
* <ol>
Expand All @@ -57,9 +57,14 @@
* -Dexec.args="[<project_id>] list [<bucket>]| info [<bucket> [<file>]]|
* download <bucket> <path> [local_file]| upload <local_file> <bucket> [<path>]|
* delete <bucket> <path>+| cp <from_bucket> <from_path> <to_bucket> <to_path>|
* compose <bucket> <from_path>+ <to_path>"}
* compose <bucket> <from_path>+ <to_path>| update_metadata <bucket> <file> [key=value]*"}
* </li>
* </ol>
*
* The first parameter is an optional project_id (logged-in project will be used if not supplied).
* Second parameter is a Storage operation (list, delete, compose,...) to demonstrate the its
* usage. Any other arguments are specific to the operation.
* See each action's run method for the specific Storage interaction.
*/
public class StorageExample {

Expand Down Expand Up @@ -112,24 +117,36 @@ public String params() {
}
}

/**
* This class demonstrates how to retrieve Bucket or Blob metadata.
* If more than one blob is supplied a Batch operation would be used to get all blobs metadata
* in a single RPC.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/get">Objects: get</a>
*/
private static class InfoAction extends BlobsAction {
@Override
public void run(StorageService storage, Blob... blobs) {


if (blobs.length == 1) {
if (blobs[0].name().isEmpty()) {
System.out.println(storage.get(blobs[0].bucket()));
// get Bucket
Bucket bucket = storage.get(blobs[0].bucket());
System.out.println("Bucket info: " + bucket);
} else {
System.out.println(storage.get(blobs[0].bucket(), blobs[0].name()));
// get Blob
Blob blob = storage.get(blobs[0].bucket(), blobs[0].name());
System.out.println("Blob info: " + blob);
}
} else {
// use batch to get multiple blobs.
BatchRequest.Builder batch = BatchRequest.builder();
for (Blob blob : blobs) {
batch.get(blob.bucket(), blob.name());
}
BatchResponse response = storage.apply(batch.build());
System.out.println(response.gets());
for (BatchResponse.Result<Blob> result : response.gets()) {
System.out.println(result.get());
}
}
}

Expand All @@ -147,22 +164,45 @@ public String params() {
}
}

/**
* This class demonstrates how to delete a blob.
* If more than one blob is supplied a Batch operation would be used to delete all requested
* blobs in a single RPC.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/delete">Objects: delete</a>
*/
private static class DeleteAction extends BlobsAction {
@Override
public void run(StorageService storage, Blob... blobs) {
if (blobs.length == 1) {
System.out.println(storage.delete(blobs[0].bucket(), blobs[0].name()));
boolean wasDeleted = storage.delete(blobs[0].bucket(), blobs[0].name());
if (wasDeleted) {
System.out.println("Blob " + blobs[0] + " was deleted");
}
} else {
// use batch operation
BatchRequest.Builder batch = BatchRequest.builder();
for (Blob blob : blobs) {
batch.delete(blob.bucket(), blob.name());
}
int index = 0;
BatchResponse response = storage.apply(batch.build());
System.out.println(response.deletes());
for (BatchResponse.Result<Boolean> result : response.deletes()) {
if (result.get()) {
// request order is maintained
System.out.println("Blob " + blobs[index] + " was deleted");
}
index++;
}
}
}
}

/**
* This class demonstrates how to list buckets or a bucket's blobs.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/list">Objects: list</a>
*/
private static class ListAction extends StorageAction<String> {

@Override
Expand All @@ -179,10 +219,12 @@ String parse(String... args) {
@Override
public void run(StorageService storage, String bucket) {
if (bucket == null) {
// list buckets
for (Bucket b : storage.list()) {
System.out.println(b);
}
} else {
// list a bucket's blobs
for (Blob b : storage.list(bucket)) {
System.out.println(b);
}
Expand All @@ -195,13 +237,24 @@ public String params() {
}
}

/**
* This class demonstrates how to create a new Blob or to update its content.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/insert">Objects: insert</a>
*/
private static class UploadAction extends StorageAction<Tuple<Path, Blob>> {
@Override
public void run(StorageService storage, Tuple<Path, Blob> tuple) throws Exception {
if (Files.size(tuple.x()) > 1024) {
try (BlobWriteChannel writer = storage.writer(tuple.y())) {
run(storage, tuple.x(), tuple.y());
}

private void run(StorageService storage, Path uploadFrom, Blob blob) throws IOException {
if (Files.size(uploadFrom) > 1_000_000) {
// When content is not available or large (1MB or more) it is recommended
// to write it in chunks via the blob's channel writer.
try (BlobWriteChannel writer = storage.writer(blob)) {
byte[] buffer = new byte[1024];
try (InputStream input = Files.newInputStream(tuple.x())) {
try (InputStream input = Files.newInputStream(uploadFrom)) {
int limit;
while ((limit = input.read(buffer)) >= 0) {
try {
Expand All @@ -213,9 +266,11 @@ public void run(StorageService storage, Tuple<Path, Blob> tuple) throws Exceptio
}
}
} else {
byte[] bytes = Files.readAllBytes(tuple.x());
System.out.println(storage.create(tuple.y(), bytes));
byte[] bytes = Files.readAllBytes(uploadFrom);
// create the blob in one request.
storage.create(blob, bytes);
}
System.out.println("Blob was created");
}

@Override
Expand All @@ -235,22 +290,37 @@ public String params() {
}
}

/**
* This class demonstrates how read a blob's content.
* The example will dump the content to a local file if one was given or write
* it to stdout otherwise.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/get">Objects: get</a>
*/
private static class DownloadAction extends StorageAction<Tuple<Blob, Path>> {

@Override
public void run(StorageService storage, Tuple<Blob, Path> tuple) throws IOException {
Blob blob = storage.get(tuple.x().bucket(), tuple.x().name());
run(storage, tuple.x().bucket(), tuple.x().name(), tuple.y());
}

private void run(StorageService storage, String bucket, String blobName, Path downloadTo)
throws IOException {
Blob blob = storage.get(bucket, blobName);
if (blob == null) {
System.out.println("No such object");
return;
}
PrintStream writeTo = System.out;
if (tuple.y() != null) {
writeTo = new PrintStream(new FileOutputStream(tuple.y().toFile()));
if (downloadTo != null) {
writeTo = new PrintStream(new FileOutputStream(downloadTo.toFile()));
}
if (blob.size() < 1024) {
writeTo.write(storage.load(blob.bucket(), blob.name()));
if (blob.size() < 1_000_000) {
// Blob is small read all its content in one request
byte[] content = storage.load(blob.bucket(), blob.name());
writeTo.write(content);
} else {
// When Blob size is big or unknown use the blob's channel reader.
try (BlobReadChannel reader = storage.reader(blob.bucket(), blob.name())) {
WritableByteChannel channel = Channels.newChannel(writeTo);
ByteBuffer bytes = ByteBuffer.allocate(64 * 1024);
Expand All @@ -261,7 +331,7 @@ public void run(StorageService storage, Tuple<Blob, Path> tuple) throws IOExcept
}
}
}
if (tuple.y() == null) {
if (downloadTo == null) {
writeTo.println();
} else {
writeTo.close();
Expand Down Expand Up @@ -291,10 +361,16 @@ public String params() {
}
}

/**
* This class demonstrates how to use the copy command.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/copy">Objects: copy</a>
*/
private static class CopyAction extends StorageAction<CopyRequest> {
@Override
public void run(StorageService storage, CopyRequest request) {
System.out.println(storage.copy(request));
Blob copiedBlob = storage.copy(request);
System.out.println("Copied " + copiedBlob);
}

@Override
Expand All @@ -311,10 +387,16 @@ public String params() {
}
}

/**
* This class demonstrates how to use the compose command.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/compose">Objects: compose</a>
*/
private static class ComposeAction extends StorageAction<ComposeRequest> {
@Override
public void run(StorageService storage, ComposeRequest request) {
System.out.println(storage.compose(request));
Blob composedBlob = storage.compose(request);
System.out.println("Composed " + composedBlob);
}

@Override
Expand All @@ -336,6 +418,54 @@ public String params() {
}
}

/**
* This class demonstrates how to update a blob's metadata.
*
* @see <a href="https://cloud.google.com/storage/docs/json_api/v1/objects/update">Objects: update</a>
*/
private static class UpdateMetadata extends StorageAction<Tuple<Blob, Map<String, String>>> {

@Override
public void run(StorageService storage, Tuple<Blob, Map<String, String>> tuple)
throws IOException {
run(storage, tuple.x().bucket(), tuple.x().name(), tuple.y());
}

private void run(StorageService storage, String bucket, String blobName,
Map<String, String> metadata) {
Blob blob = storage.get(bucket, blobName);
if (blob == null) {
System.out.println("No such object");
return;
}
blob = storage.update(blob.toBuilder().metadata(metadata).build());
System.out.println("Updated " + blob);
}

@Override
Tuple<Blob, Map<String, String>> parse(String... args) {
if (args.length < 2) {
throw new IllegalArgumentException();
}
Blob blob = Blob.of(args[0], args[1]);
Map<String, String> metadata = new HashMap<>();
for (int i = 2; i < args.length; i++) {
int idx = args[i].indexOf('=');
if (idx < 0) {
metadata.put(args[i], "");
} else {
metadata.put(args[i].substring(0, idx), args[i].substring(idx + 1));
}
}
return Tuple.of(blob, metadata);
}

@Override
public String params() {
return "<bucket> <path> [local_file]";
}
}

static {
ACTIONS.put("info", new InfoAction());
ACTIONS.put("delete", new DeleteAction());
Expand All @@ -344,6 +474,7 @@ public String params() {
ACTIONS.put("download", new DownloadAction());
ACTIONS.put("cp", new CopyAction());
ACTIONS.put("compose", new ComposeAction());
ACTIONS.put("update_metadata", new UpdateMetadata());
}

public static void printUsage() {
Expand Down Expand Up @@ -378,7 +509,7 @@ public static void main(String... args) throws Exception {
args = Arrays.copyOfRange(args, 1, args.length);
}
if (action == null) {
System.out.println("Unrecognized action '" + args[1] + "'");
System.out.println("Unrecognized action.");
printUsage();
return;
}
Expand Down
Loading

0 comments on commit 05e3f0a

Please sign in to comment.