@Test public void testWrite() throws Exception { final Path container = new Path("test.cyberduck.ch", EnumSet.of(Path.Type.directory, Path.Type.volume)); final Path test = new Path(container, String.format("%s %s", new AlphanumericRandomStringService().random(), new AlphanumericRandomStringService().random()), EnumSet.of(Path.Type.file)); { final TransferStatus status = new TransferStatus(); final byte[] content = RandomUtils.nextBytes(2048); status.setLength(content.length); status.setMime("application/octet-stream"); status.setStorageClass("multi_regional"); status.setMetadata(Collections.singletonMap("c", "d")); final HttpResponseOutputStream<VersionId> out = new GoogleStorageWriteFeature(session).write(test, status, new DisabledConnectionCallback()); new StreamCopier(new TransferStatus(), new TransferStatus()).transfer(new ByteArrayInputStream(content), out); out.close(); assertNotNull(out.getStatus().id); assertTrue(new GoogleStorageFindFeature(session).find(test)); final Write.Append append = new GoogleStorageWriteFeature(session).append(test, status.getLength(), PathCache.empty()); assertTrue(append.override); assertEquals(content.length, append.size, 0L); final byte[] buffer = new byte[content.length]; final InputStream in = new GoogleStorageReadFeature(session).read(test, new TransferStatus().length(content.length), new DisabledConnectionCallback()); IOUtils.readFully(in, buffer); in.close(); assertArrayEquals(content, buffer); } { final TransferStatus status = new TransferStatus(); status.setExists(true); final byte[] content = RandomUtils.nextBytes(1024); status.setLength(content.length); final HttpResponseOutputStream<VersionId> out = new GoogleStorageWriteFeature(session).write(test, status, new DisabledConnectionCallback()); new StreamCopier(new TransferStatus(), new TransferStatus()).transfer(new ByteArrayInputStream(content), out); out.close(); assertNotNull(out.getStatus().id); final PathAttributes attributes = new GoogleStorageAttributesFinderFeature(session).find(test); assertEquals(content.length, attributes.getSize()); } new GoogleStorageDeleteFeature(session).delete(Collections.singletonList(test), new DisabledLoginCallback(), new Delete.DisabledCallback()); }
@Override public HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback) throws BackgroundException { final DelayedHttpEntityCallable<VersionId> command = new DelayedHttpEntityCallable<VersionId>() { @Override public VersionId call(final AbstractHttpEntity entity) throws BackgroundException { try { final HttpEntityEnclosingRequestBase request = new HttpPost(String.format("%supload/storage/v1/b/%s/o?uploadType=resumable", session.getClient().getRootUrl(), containerService.getContainer(file).getName())); final StringBuilder metadata = new StringBuilder(); metadata.append(String.format("{\"name\": \"%s\"", containerService.getKey(file))); metadata.append(",\"metadata\": {"); for(Map.Entry<String, String> item : status.getMetadata().entrySet()) { metadata.append(String.format("\"%s\": \"%s\"", item.getKey(), item.getValue())); } metadata.append("}"); if(StringUtils.isNotBlank(status.getMime())) { metadata.append(String.format(", \"contentType\": \"%s\"", status.getMime())); } if(StringUtils.isNotBlank(status.getStorageClass())) { metadata.append(String.format(", \"storageClass\": \"%s\"", status.getStorageClass())); } metadata.append("}"); request.setEntity(new StringEntity(metadata.toString(), ContentType.create("application/json", StandardCharsets.UTF_8.name()))); if(StringUtils.isNotBlank(status.getMime())) { request.addHeader("X-Upload-Content-Type", status.getMime()); } request.addHeader(HTTP.CONTENT_TYPE, MEDIA_TYPE); final HttpClient client = session.getHttpClient(); final HttpResponse response = client.execute(request); try { switch(response.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(response.getEntity()); } if(response.containsHeader(HttpHeaders.LOCATION)) { final String putTarget = response.getFirstHeader(HttpHeaders.LOCATION).getValue(); final HttpPut put = new HttpPut(putTarget); put.setEntity(entity); final HttpResponse putResponse = client.execute(put); try { switch(putResponse.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: case HttpStatus.SC_CREATED: try (JsonReader reader = new JsonReader(new InputStreamReader(putResponse.getEntity().getContent(), StandardCharsets.UTF_8))) { reader.beginObject(); while(reader.hasNext()) { final String name = reader.nextName(); final String value = reader.nextString(); switch(name) { case "generation": final VersionId version = new VersionId(value); status.setVersion(version); return version; } } reader.endObject(); } break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(putResponse.getEntity()); } } else { throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } return new VersionId(null); } catch(IOException e) { throw new GoogleStorageExceptionMappingService().map("Upload failed", e, file); } } @Override public long getContentLength() { return status.getLength(); } }; return this.write(file, status, command); }
GoogleStorageWriteFeature extends AbstractHttpWriteFeature<VersionId> implements Write<VersionId> { @Override public HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback) throws BackgroundException { final DelayedHttpEntityCallable<VersionId> command = new DelayedHttpEntityCallable<VersionId>() { @Override public VersionId call(final AbstractHttpEntity entity) throws BackgroundException { try { final HttpEntityEnclosingRequestBase request = new HttpPost(String.format("%supload/storage/v1/b/%s/o?uploadType=resumable", session.getClient().getRootUrl(), containerService.getContainer(file).getName())); final StringBuilder metadata = new StringBuilder(); metadata.append(String.format("{\"name\": \"%s\"", containerService.getKey(file))); metadata.append(",\"metadata\": {"); for(Map.Entry<String, String> item : status.getMetadata().entrySet()) { metadata.append(String.format("\"%s\": \"%s\"", item.getKey(), item.getValue())); } metadata.append("}"); if(StringUtils.isNotBlank(status.getMime())) { metadata.append(String.format(", \"contentType\": \"%s\"", status.getMime())); } if(StringUtils.isNotBlank(status.getStorageClass())) { metadata.append(String.format(", \"storageClass\": \"%s\"", status.getStorageClass())); } metadata.append("}"); request.setEntity(new StringEntity(metadata.toString(), ContentType.create("application/json", StandardCharsets.UTF_8.name()))); if(StringUtils.isNotBlank(status.getMime())) { request.addHeader("X-Upload-Content-Type", status.getMime()); } request.addHeader(HTTP.CONTENT_TYPE, MEDIA_TYPE); final HttpClient client = session.getHttpClient(); final HttpResponse response = client.execute(request); try { switch(response.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(response.getEntity()); } if(response.containsHeader(HttpHeaders.LOCATION)) { final String putTarget = response.getFirstHeader(HttpHeaders.LOCATION).getValue(); final HttpPut put = new HttpPut(putTarget); put.setEntity(entity); final HttpResponse putResponse = client.execute(put); try { switch(putResponse.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: case HttpStatus.SC_CREATED: try (JsonReader reader = new JsonReader(new InputStreamReader(putResponse.getEntity().getContent(), StandardCharsets.UTF_8))) { reader.beginObject(); while(reader.hasNext()) { final String name = reader.nextName(); final String value = reader.nextString(); switch(name) { case "generation": final VersionId version = new VersionId(value); status.setVersion(version); return version; } } reader.endObject(); } break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(putResponse.getEntity()); } } else { throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } return new VersionId(null); } catch(IOException e) { throw new GoogleStorageExceptionMappingService().map("Upload failed", e, file); } } @Override public long getContentLength() { return status.getLength(); } }; return this.write(file, status, command); } }
GoogleStorageWriteFeature extends AbstractHttpWriteFeature<VersionId> implements Write<VersionId> { @Override public HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback) throws BackgroundException { final DelayedHttpEntityCallable<VersionId> command = new DelayedHttpEntityCallable<VersionId>() { @Override public VersionId call(final AbstractHttpEntity entity) throws BackgroundException { try { final HttpEntityEnclosingRequestBase request = new HttpPost(String.format("%supload/storage/v1/b/%s/o?uploadType=resumable", session.getClient().getRootUrl(), containerService.getContainer(file).getName())); final StringBuilder metadata = new StringBuilder(); metadata.append(String.format("{\"name\": \"%s\"", containerService.getKey(file))); metadata.append(",\"metadata\": {"); for(Map.Entry<String, String> item : status.getMetadata().entrySet()) { metadata.append(String.format("\"%s\": \"%s\"", item.getKey(), item.getValue())); } metadata.append("}"); if(StringUtils.isNotBlank(status.getMime())) { metadata.append(String.format(", \"contentType\": \"%s\"", status.getMime())); } if(StringUtils.isNotBlank(status.getStorageClass())) { metadata.append(String.format(", \"storageClass\": \"%s\"", status.getStorageClass())); } metadata.append("}"); request.setEntity(new StringEntity(metadata.toString(), ContentType.create("application/json", StandardCharsets.UTF_8.name()))); if(StringUtils.isNotBlank(status.getMime())) { request.addHeader("X-Upload-Content-Type", status.getMime()); } request.addHeader(HTTP.CONTENT_TYPE, MEDIA_TYPE); final HttpClient client = session.getHttpClient(); final HttpResponse response = client.execute(request); try { switch(response.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(response.getEntity()); } if(response.containsHeader(HttpHeaders.LOCATION)) { final String putTarget = response.getFirstHeader(HttpHeaders.LOCATION).getValue(); final HttpPut put = new HttpPut(putTarget); put.setEntity(entity); final HttpResponse putResponse = client.execute(put); try { switch(putResponse.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: case HttpStatus.SC_CREATED: try (JsonReader reader = new JsonReader(new InputStreamReader(putResponse.getEntity().getContent(), StandardCharsets.UTF_8))) { reader.beginObject(); while(reader.hasNext()) { final String name = reader.nextName(); final String value = reader.nextString(); switch(name) { case "generation": final VersionId version = new VersionId(value); status.setVersion(version); return version; } } reader.endObject(); } break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(putResponse.getEntity()); } } else { throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } return new VersionId(null); } catch(IOException e) { throw new GoogleStorageExceptionMappingService().map("Upload failed", e, file); } } @Override public long getContentLength() { return status.getLength(); } }; return this.write(file, status, command); } GoogleStorageWriteFeature(final GoogleStorageSession session);  GoogleStorageWriteFeature(final GoogleStorageSession session, final Find finder, final AttributesFinder attributes); }
GoogleStorageWriteFeature extends AbstractHttpWriteFeature<VersionId> implements Write<VersionId> { @Override public HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback) throws BackgroundException { final DelayedHttpEntityCallable<VersionId> command = new DelayedHttpEntityCallable<VersionId>() { @Override public VersionId call(final AbstractHttpEntity entity) throws BackgroundException { try { final HttpEntityEnclosingRequestBase request = new HttpPost(String.format("%supload/storage/v1/b/%s/o?uploadType=resumable", session.getClient().getRootUrl(), containerService.getContainer(file).getName())); final StringBuilder metadata = new StringBuilder(); metadata.append(String.format("{\"name\": \"%s\"", containerService.getKey(file))); metadata.append(",\"metadata\": {"); for(Map.Entry<String, String> item : status.getMetadata().entrySet()) { metadata.append(String.format("\"%s\": \"%s\"", item.getKey(), item.getValue())); } metadata.append("}"); if(StringUtils.isNotBlank(status.getMime())) { metadata.append(String.format(", \"contentType\": \"%s\"", status.getMime())); } if(StringUtils.isNotBlank(status.getStorageClass())) { metadata.append(String.format(", \"storageClass\": \"%s\"", status.getStorageClass())); } metadata.append("}"); request.setEntity(new StringEntity(metadata.toString(), ContentType.create("application/json", StandardCharsets.UTF_8.name()))); if(StringUtils.isNotBlank(status.getMime())) { request.addHeader("X-Upload-Content-Type", status.getMime()); } request.addHeader(HTTP.CONTENT_TYPE, MEDIA_TYPE); final HttpClient client = session.getHttpClient(); final HttpResponse response = client.execute(request); try { switch(response.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(response.getEntity()); } if(response.containsHeader(HttpHeaders.LOCATION)) { final String putTarget = response.getFirstHeader(HttpHeaders.LOCATION).getValue(); final HttpPut put = new HttpPut(putTarget); put.setEntity(entity); final HttpResponse putResponse = client.execute(put); try { switch(putResponse.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: case HttpStatus.SC_CREATED: try (JsonReader reader = new JsonReader(new InputStreamReader(putResponse.getEntity().getContent(), StandardCharsets.UTF_8))) { reader.beginObject(); while(reader.hasNext()) { final String name = reader.nextName(); final String value = reader.nextString(); switch(name) { case "generation": final VersionId version = new VersionId(value); status.setVersion(version); return version; } } reader.endObject(); } break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(putResponse.getEntity()); } } else { throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } return new VersionId(null); } catch(IOException e) { throw new GoogleStorageExceptionMappingService().map("Upload failed", e, file); } } @Override public long getContentLength() { return status.getLength(); } }; return this.write(file, status, command); } GoogleStorageWriteFeature(final GoogleStorageSession session);  GoogleStorageWriteFeature(final GoogleStorageSession session, final Find finder, final AttributesFinder attributes); @Override HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback); @Override Append append(final Path file, final Long length, final Cache<Path> cache); @Override boolean temporary(); @Override boolean random(); @Override ChecksumCompute checksum(final Path file, final TransferStatus status); }
GoogleStorageWriteFeature extends AbstractHttpWriteFeature<VersionId> implements Write<VersionId> { @Override public HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback) throws BackgroundException { final DelayedHttpEntityCallable<VersionId> command = new DelayedHttpEntityCallable<VersionId>() { @Override public VersionId call(final AbstractHttpEntity entity) throws BackgroundException { try { final HttpEntityEnclosingRequestBase request = new HttpPost(String.format("%supload/storage/v1/b/%s/o?uploadType=resumable", session.getClient().getRootUrl(), containerService.getContainer(file).getName())); final StringBuilder metadata = new StringBuilder(); metadata.append(String.format("{\"name\": \"%s\"", containerService.getKey(file))); metadata.append(",\"metadata\": {"); for(Map.Entry<String, String> item : status.getMetadata().entrySet()) { metadata.append(String.format("\"%s\": \"%s\"", item.getKey(), item.getValue())); } metadata.append("}"); if(StringUtils.isNotBlank(status.getMime())) { metadata.append(String.format(", \"contentType\": \"%s\"", status.getMime())); } if(StringUtils.isNotBlank(status.getStorageClass())) { metadata.append(String.format(", \"storageClass\": \"%s\"", status.getStorageClass())); } metadata.append("}"); request.setEntity(new StringEntity(metadata.toString(), ContentType.create("application/json", StandardCharsets.UTF_8.name()))); if(StringUtils.isNotBlank(status.getMime())) { request.addHeader("X-Upload-Content-Type", status.getMime()); } request.addHeader(HTTP.CONTENT_TYPE, MEDIA_TYPE); final HttpClient client = session.getHttpClient(); final HttpResponse response = client.execute(request); try { switch(response.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(response.getEntity()); } if(response.containsHeader(HttpHeaders.LOCATION)) { final String putTarget = response.getFirstHeader(HttpHeaders.LOCATION).getValue(); final HttpPut put = new HttpPut(putTarget); put.setEntity(entity); final HttpResponse putResponse = client.execute(put); try { switch(putResponse.getStatusLine().getStatusCode()) { case HttpStatus.SC_OK: case HttpStatus.SC_CREATED: try (JsonReader reader = new JsonReader(new InputStreamReader(putResponse.getEntity().getContent(), StandardCharsets.UTF_8))) { reader.beginObject(); while(reader.hasNext()) { final String name = reader.nextName(); final String value = reader.nextString(); switch(name) { case "generation": final VersionId version = new VersionId(value); status.setVersion(version); return version; } } reader.endObject(); } break; default: throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } } finally { EntityUtils.consume(putResponse.getEntity()); } } else { throw new DefaultHttpResponseExceptionMappingService().map( new HttpResponseException(response.getStatusLine().getStatusCode(), response.getStatusLine().getReasonPhrase())); } return new VersionId(null); } catch(IOException e) { throw new GoogleStorageExceptionMappingService().map("Upload failed", e, file); } } @Override public long getContentLength() { return status.getLength(); } }; return this.write(file, status, command); } GoogleStorageWriteFeature(final GoogleStorageSession session);  GoogleStorageWriteFeature(final GoogleStorageSession session, final Find finder, final AttributesFinder attributes); @Override HttpResponseOutputStream<VersionId> write(final Path file, final TransferStatus status, final ConnectionCallback callback); @Override Append append(final Path file, final Long length, final Cache<Path> cache); @Override boolean temporary(); @Override boolean random(); @Override ChecksumCompute checksum(final Path file, final TransferStatus status);  }