This is an automated email from the ASF dual-hosted git repository. htowaileb pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/asterixdb.git
The following commit(s) were added to refs/heads/master by this push: new 599c0367b6 ASTERIXDB-3031: Add support to instance profile authentication 599c0367b6 is described below commit 599c0367b69fab63b1f8ce8117a0e079f4f3b079 Author: Hussain Towaileb <hussain.towai...@couchbase.com> AuthorDate: Mon Apr 18 12:11:16 2022 +0300 ASTERIXDB-3031: Add support to instance profile authentication Change-Id: Ib82d3c032b90d3a3adacf5140bcf1868f7105425 Reviewed-on: https://asterix-gerrit.ics.uci.edu/c/asterixdb/+/16123 Reviewed-by: Hussain Towaileb <hussai...@gmail.com> Reviewed-by: Dmitry Lychagin <dmitry.lycha...@couchbase.com> Contrib: Jenkins <jenk...@fulliautomatix.ics.uci.edu> Integration-Tests: Jenkins <jenk...@fulliautomatix.ics.uci.edu> Tested-by: Jenkins <jenk...@fulliautomatix.ics.uci.edu> --- .../asterix/common/exceptions/ErrorCode.java | 1 + .../src/main/resources/asx_errormsg/en.properties | 1 + .../asterix/external/util/aws/s3/S3Constants.java | 1 + .../asterix/external/util/aws/s3/S3Utils.java | 47 ++++++++++++++++++++-- 4 files changed, 46 insertions(+), 4 deletions(-) diff --git a/asterixdb/asterix-common/src/main/java/org/apache/asterix/common/exceptions/ErrorCode.java b/asterixdb/asterix-common/src/main/java/org/apache/asterix/common/exceptions/ErrorCode.java index 068c1251f0..22394868f5 100644 --- a/asterixdb/asterix-common/src/main/java/org/apache/asterix/common/exceptions/ErrorCode.java +++ b/asterixdb/asterix-common/src/main/java/org/apache/asterix/common/exceptions/ErrorCode.java @@ -263,6 +263,7 @@ public enum ErrorCode implements IError { S3_REGION_NOT_SUPPORTED(1170), COMPILATION_SET_OPERATION_ERROR(1171), INVALID_TIMEZONE(1172), + INVALID_PARAM_VALUE_ALLOWED_VALUE(1173), // Feed errors DATAFLOW_ILLEGAL_STATE(3001), diff --git a/asterixdb/asterix-common/src/main/resources/asx_errormsg/en.properties b/asterixdb/asterix-common/src/main/resources/asx_errormsg/en.properties index f5ef79d11a..919431b5c8 100644 --- a/asterixdb/asterix-common/src/main/resources/asx_errormsg/en.properties +++ b/asterixdb/asterix-common/src/main/resources/asx_errormsg/en.properties @@ -265,6 +265,7 @@ 1170 = Provided S3 region is not supported: '%1$s' 1171 = Unable to process %1$s clause. %2$s 1172 = Provided timezone is invalid: '%1$s' +1173 = Invalid value for parameter '%1$s', allowed value(s): %2$s # Feed Errors 3001 = Illegal state. diff --git a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Constants.java b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Constants.java index e1c10ad6ef..79bbbe235e 100644 --- a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Constants.java +++ b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Constants.java @@ -24,6 +24,7 @@ public class S3Constants { } public static final String REGION_FIELD_NAME = "region"; + public static final String INSTANCE_PROFILE_FIELD_NAME = "instanceProfile"; public static final String ACCESS_KEY_ID_FIELD_NAME = "accessKeyId"; public static final String SECRET_ACCESS_KEY_FIELD_NAME = "secretAccessKey"; public static final String SESSION_TOKEN_FIELD_NAME = "sessionToken"; diff --git a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Utils.java b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Utils.java index a88d59be78..6775bf12b7 100644 --- a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Utils.java +++ b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/util/aws/s3/S3Utils.java @@ -18,6 +18,8 @@ */ package org.apache.asterix.external.util.aws.s3; +import static org.apache.asterix.common.exceptions.ErrorCode.INVALID_PARAM_VALUE_ALLOWED_VALUE; +import static org.apache.asterix.common.exceptions.ErrorCode.PARAM_NOT_ALLOWED_IF_PARAM_IS_PRESENT; import static org.apache.asterix.common.exceptions.ErrorCode.REQUIRED_PARAM_IF_PARAM_IS_PRESENT; import static org.apache.asterix.common.exceptions.ErrorCode.S3_REGION_NOT_SUPPORTED; import static org.apache.asterix.external.util.ExternalDataUtils.getPrefix; @@ -50,6 +52,7 @@ import software.amazon.awssdk.auth.credentials.AnonymousCredentialsProvider; import software.amazon.awssdk.auth.credentials.AwsBasicCredentials; import software.amazon.awssdk.auth.credentials.AwsCredentialsProvider; import software.amazon.awssdk.auth.credentials.AwsSessionCredentials; +import software.amazon.awssdk.auth.credentials.InstanceProfileCredentialsProvider; import software.amazon.awssdk.auth.credentials.StaticCredentialsProvider; import software.amazon.awssdk.core.exception.SdkException; import software.amazon.awssdk.regions.Region; @@ -81,6 +84,7 @@ public class S3Utils { */ public static S3Client buildAwsS3Client(Map<String, String> configuration) throws CompilationException { // TODO(Hussain): Need to ensure that all required parameters are present in a previous step + String instanceProfile = configuration.get(INSTANCE_PROFILE_FIELD_NAME); String accessKeyId = configuration.get(ACCESS_KEY_ID_FIELD_NAME); String secretAccessKey = configuration.get(SECRET_ACCESS_KEY_FIELD_NAME); String sessionToken = configuration.get(SESSION_TOKEN_FIELD_NAME); @@ -92,11 +96,42 @@ public class S3Utils { // Credentials AwsCredentialsProvider credentialsProvider; - // No auth required - if (accessKeyId == null) { + // nothing provided, anonymous authentication + if (instanceProfile == null && accessKeyId == null && secretAccessKey == null && sessionToken == null) { credentialsProvider = AnonymousCredentialsProvider.create(); - } else { - // auth required, check for temporary or permanent credentials + } else if (instanceProfile != null) { + + // only "true" value is allowed + if (!instanceProfile.equalsIgnoreCase("true")) { + throw new CompilationException(INVALID_PARAM_VALUE_ALLOWED_VALUE, INSTANCE_PROFILE_FIELD_NAME, "true"); + } + + // no other authentication parameters are allowed + if (accessKeyId != null) { + throw new CompilationException(PARAM_NOT_ALLOWED_IF_PARAM_IS_PRESENT, ACCESS_KEY_ID_FIELD_NAME, + INSTANCE_PROFILE_FIELD_NAME); + } + if (secretAccessKey != null) { + throw new CompilationException(PARAM_NOT_ALLOWED_IF_PARAM_IS_PRESENT, SECRET_ACCESS_KEY_FIELD_NAME, + INSTANCE_PROFILE_FIELD_NAME); + } + if (sessionToken != null) { + throw new CompilationException(PARAM_NOT_ALLOWED_IF_PARAM_IS_PRESENT, SESSION_TOKEN_FIELD_NAME, + INSTANCE_PROFILE_FIELD_NAME); + } + credentialsProvider = InstanceProfileCredentialsProvider.create(); + } else if (accessKeyId != null || secretAccessKey != null) { + // accessKeyId authentication + if (accessKeyId == null) { + throw new CompilationException(REQUIRED_PARAM_IF_PARAM_IS_PRESENT, ACCESS_KEY_ID_FIELD_NAME, + SECRET_ACCESS_KEY_FIELD_NAME); + } + if (secretAccessKey == null) { + throw new CompilationException(REQUIRED_PARAM_IF_PARAM_IS_PRESENT, SECRET_ACCESS_KEY_FIELD_NAME, + ACCESS_KEY_ID_FIELD_NAME); + } + + // use session token if provided if (sessionToken != null) { credentialsProvider = StaticCredentialsProvider .create(AwsSessionCredentials.create(accessKeyId, secretAccessKey, sessionToken)); @@ -104,6 +139,10 @@ public class S3Utils { credentialsProvider = StaticCredentialsProvider.create(AwsBasicCredentials.create(accessKeyId, secretAccessKey)); } + } else { + // if only session token is provided, accessKeyId is required + throw new CompilationException(REQUIRED_PARAM_IF_PARAM_IS_PRESENT, ACCESS_KEY_ID_FIELD_NAME, + SESSION_TOKEN_FIELD_NAME); } builder.credentialsProvider(credentialsProvider);