4242import java .util .function .Consumer ;
4343import java .util .function .Function ;
4444
45+ import static software .amazon .encryption .s3 .S3EncryptionClientUtilities .DEFAULT_BUFFER_SIZE_BYTES ;
46+ import static software .amazon .encryption .s3 .S3EncryptionClientUtilities .MAX_ALLOWED_BUFFER_SIZE_BYTES ;
47+ import static software .amazon .encryption .s3 .S3EncryptionClientUtilities .MIN_ALLOWED_BUFFER_SIZE_BYTES ;
4548import static software .amazon .encryption .s3 .internal .ApiNameVersion .API_NAME_INTERCEPTOR ;
4649
4750/**
@@ -56,6 +59,7 @@ public class S3AsyncEncryptionClient extends DelegatingS3AsyncClient {
5659 private final boolean _enableLegacyUnauthenticatedModes ;
5760 private final boolean _enableDelayedAuthenticationMode ;
5861 private final boolean _enableMultipartPutObject ;
62+ private final long _bufferSize ;
5963
6064 private S3AsyncEncryptionClient (Builder builder ) {
6165 super (builder ._wrappedClient );
@@ -65,6 +69,7 @@ private S3AsyncEncryptionClient(Builder builder) {
6569 _enableLegacyUnauthenticatedModes = builder ._enableLegacyUnauthenticatedModes ;
6670 _enableDelayedAuthenticationMode = builder ._enableDelayedAuthenticationMode ;
6771 _enableMultipartPutObject = builder ._enableMultipartPutObject ;
72+ _bufferSize = builder ._bufferSize ;
6873 }
6974
7075 /**
@@ -181,6 +186,7 @@ public <T> CompletableFuture<T> getObject(GetObjectRequest getObjectRequest,
181186 .cryptoMaterialsManager (_cryptoMaterialsManager )
182187 .enableLegacyUnauthenticatedModes (_enableLegacyUnauthenticatedModes )
183188 .enableDelayedAuthentication (_enableDelayedAuthenticationMode )
189+ .bufferSize (_bufferSize )
184190 .build ();
185191
186192 return pipeline .getObject (getObjectRequest , asyncResponseTransformer );
@@ -200,9 +206,9 @@ public CompletableFuture<DeleteObjectResponse> deleteObject(DeleteObjectRequest
200206 final DeleteObjectRequest actualRequest = deleteObjectRequest .toBuilder ()
201207 .overrideConfiguration (API_NAME_INTERCEPTOR )
202208 .build ();
203- final CompletableFuture <DeleteObjectResponse > response = _wrappedClient .deleteObject (actualRequest );
209+ final CompletableFuture <DeleteObjectResponse > response = _wrappedClient .deleteObject (actualRequest );
204210 final String instructionObjectKey = deleteObjectRequest .key () + ".instruction" ;
205- final CompletableFuture <DeleteObjectResponse > instructionResponse = _wrappedClient .deleteObject (builder -> builder
211+ final CompletableFuture <DeleteObjectResponse > instructionResponse = _wrappedClient .deleteObject (builder -> builder
206212 .overrideConfiguration (API_NAME_INTERCEPTOR )
207213 .bucket (deleteObjectRequest .bucket ())
208214 .key (instructionObjectKey ));
@@ -257,6 +263,7 @@ public static class Builder {
257263 private boolean _enableMultipartPutObject = false ;
258264 private Provider _cryptoProvider = null ;
259265 private SecureRandom _secureRandom = new SecureRandom ();
266+ private long _bufferSize = -1L ;
260267
261268 private Builder () {
262269 }
@@ -434,6 +441,22 @@ public Builder enableMultipartPutObject(boolean _enableMultipartPutObject) {
434441 return this ;
435442 }
436443
444+ /**
445+ * Sets the buffer size for safe authentication used when delayed authentication mode is disabled.
446+ * If buffer size is not given during client configuration, default buffer size is set to 64MiB.
447+ * @param bufferSize the desired buffer size in Bytes.
448+ * @return Returns a reference to this object so that method calls can be chained together.
449+ * @throws S3EncryptionClientException if the specified buffer size is outside the allowed bounds
450+ */
451+ public Builder setBufferSize (long bufferSize ) {
452+ if (bufferSize < MIN_ALLOWED_BUFFER_SIZE_BYTES || bufferSize > MAX_ALLOWED_BUFFER_SIZE_BYTES ) {
453+ throw new S3EncryptionClientException ("Invalid buffer size: " + bufferSize + " Bytes. Buffer size must be between " + MIN_ALLOWED_BUFFER_SIZE_BYTES + " and " + MAX_ALLOWED_BUFFER_SIZE_BYTES + " Bytes." );
454+ }
455+
456+ this ._bufferSize = bufferSize ;
457+ return this ;
458+ }
459+
437460 /**
438461 * Allows the user to pass an instance of {@link Provider} to be used
439462 * for cryptographic operations. By default, the S3 Encryption Client
@@ -476,6 +499,14 @@ public S3AsyncEncryptionClient build() {
476499 throw new S3EncryptionClientException ("Exactly one must be set of: crypto materials manager, keyring, AES key, RSA key pair, KMS key id" );
477500 }
478501
502+ if (_bufferSize >= 0 ) {
503+ if (_enableDelayedAuthenticationMode ) {
504+ throw new S3EncryptionClientException ("Buffer size cannot be set when delayed authentication mode is enabled" );
505+ }
506+ } else {
507+ _bufferSize = DEFAULT_BUFFER_SIZE_BYTES ;
508+ }
509+
479510 if (_keyring == null ) {
480511 if (_aesKey != null ) {
481512 _keyring = AesKeyring .builder ()
0 commit comments