Skip to content

Commit b78dc6c

Browse files
committed
Update as per the commend in PR.
Summary - 1. Updated README.md 2. SigV4AuthProvider.java to removed dependency on command lang3 , use getDefaultRegion(), changed getDefaultRegion() to return chain.getRegion().
1 parent 0fd08d5 commit b78dc6c

File tree

4 files changed

+93
-19
lines changed

4 files changed

+93
-19
lines changed

README.md

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ This package implements an authentication plugin for the open-source Datastax Ja
88

99
The plugin depends on the AWS SDK for Java. It uses `AWSCredentialsProvider` to obtain credentials. Because the IAuthenticator interface operates at the level of `InetSocketAddress`, you must specify the service endpoint to use for the connection.
1010
You can provide the Region in the constructor programmatically, via the `AWS_REGION` environment variable, or via the `aws.region` system property.
11-
You can also provide the IAM role, with which you want to connect with KeySpaces, in the constructor programmatically, via advanced.auth-provider.aws-role property in the conf file.
11+
You can also provide an IAM role to assume for access to KeySpaces, programmatically or via the configuration file.
1212

1313
The full documentation for the plugin is available at
1414
https://docs.aws.amazon.com/keyspaces/latest/devguide/programmatic.credentials.html#programmatic.credentials.SigV4_KEYSPACES.
@@ -57,22 +57,19 @@ One of the constructors for `software.aws.mcs.auth.SigV4AuthProvider` takes a `S
5757

5858
### Configuration
5959

60-
Set the Region explicitly in your `advanced.auth-provider.class` configuration (see example below), by specifying the `advanced.auth-provider.aws-region` property.
60+
Set the Region explicitly in your `advanced.auth-provider` configuration (see example below), by specifying the `advanced.auth-provider.aws-region` property.
6161

6262
## Assume IAM Role Configuration
6363

64-
You must configure the AWS Region that the plugin will use when authenticating using mechanism mentioned above.
65-
You can also specify IAM Role (including cross-account IAM role) configuraiton using one of the 2 methods:
66-
* Constructor
67-
* Configuration
64+
You can specify an IAM role to assume for access to KeySpaces using either the constructor or the driver configuration file
6865

6966
### Constructor
7067

71-
One of the constructors for `software.aws.mcs.auth.SigV4AuthProvider` takes two String , first represening the region and second one representing IAM role ARN.
68+
One of the constructors for `software.aws.mcs.auth.SigV4AuthProvider` takes two Strings , the first representing the region and the second representing the ARN of the IAM role to assume.
7269

7370
### Configuration
7471

75-
Set the IAM Role explicitly in your `advanced.auth-provider.class` configuration (see example below), by specifying the `advanced.auth-provider.aws-role` property.
72+
Set the IAM Role explicitly in your `advanced.auth-provider` configuration (see example below), by specifying the `advanced.auth-provider.aws-role` property.
7673

7774
## Add the Authentication Plugin to the Application
7875

@@ -155,7 +152,7 @@ The following is an example of this config without explicit role to be assumed.
155152
}
156153
```
157154

158-
Dollowing is an example of this config with explicit role to be assumed.
155+
The following is an example of this config with an explicit role to be assumed.
159156

160157
``` text
161158
datastax-java-driver {

src/main/java/software/aws/mcs/auth/SigV4AuthProvider.java

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,6 @@
4747
import com.datastax.oss.driver.api.core.config.DriverOption;
4848
import com.datastax.oss.driver.api.core.context.DriverContext;
4949
import com.datastax.oss.driver.api.core.metadata.EndPoint;
50-
import org.apache.commons.lang3.StringUtils;
5150
import software.amazon.awssdk.auth.credentials.AwsCredentials;
5251
import software.amazon.awssdk.auth.credentials.AwsCredentialsProvider;
5352
import software.amazon.awssdk.auth.credentials.AwsSessionCredentials;
@@ -169,9 +168,7 @@ public SigV4AuthProvider(@NotNull AwsCredentialsProvider credentialsProvider, fi
169168
this.credentialsProvider = credentialsProvider;
170169

171170
if (region == null) {
172-
DefaultAwsRegionProviderChain chain = new DefaultAwsRegionProviderChain();
173-
Region defaultRegion = chain.getRegion();
174-
this.signingRegion = defaultRegion.toString().toLowerCase();
171+
this.signingRegion = getDefaultRegion();
175172
} else {
176173
this.signingRegion = region.toLowerCase();
177174
}
@@ -398,7 +395,12 @@ static int indexOf(byte[] target, byte[] pattern) {
398395
*/
399396
private static StsAssumeRoleCredentialsProvider createSTSRoleCredentialProvider(String roleArn,
400397
String stsRegion) {
401-
final String roleName= StringUtils.substringAfterLast(roleArn,"/");
398+
//Get role name from ARN
399+
String[] arnParts = roleArn.split("/");
400+
if(arnParts.length < 2){
401+
throw new IllegalArgumentException("Invalid role ARN");
402+
}
403+
String roleName = arnParts[arnParts.length - 1];
402404
final String sessionName="keyspaces-session-"+roleName+System.currentTimeMillis();
403405
StsClient stsClient = StsClient.builder()
404406
.region(Region.of(stsRegion))
@@ -419,6 +421,6 @@ private static StsAssumeRoleCredentialsProvider createSTSRoleCredentialProvider(
419421
*/
420422
private static String getDefaultRegion() {
421423
DefaultAwsRegionProviderChain chain = new DefaultAwsRegionProviderChain();
422-
return Optional.ofNullable(chain.getRegion()).orElse(Region.US_EAST_1).toString();
424+
return chain.getRegion().toString().toLowerCase();
423425
}
424426
}
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
package software.aws.mcs.auth;
2+
3+
/*-
4+
* #%L
5+
* AWS SigV4 Auth Java Driver 4.x Plugin
6+
* %%
7+
* Copyright (C) 2020-2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
8+
* %%
9+
* Licensed under the Apache License, Version 2.0 (the "License");
10+
* you may not use this file except in compliance with the License.
11+
* You may obtain a copy of the License at
12+
*
13+
* http://www.apache.org/licenses/LICENSE-2.0
14+
*
15+
* Unless required by applicable law or agreed to in writing, software
16+
* distributed under the License is distributed on an "AS IS" BASIS,
17+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18+
* See the License for the specific language governing permissions and
19+
* limitations under the License.
20+
* #L%
21+
*/
22+
23+
import com.datastax.oss.driver.api.core.CqlSession;
24+
import com.datastax.oss.driver.api.core.config.DriverConfigLoader;
25+
import com.datastax.oss.driver.api.core.cql.ResultSet;
26+
import com.datastax.oss.driver.api.core.cql.Row;
27+
import org.junit.platform.commons.util.StringUtils;
28+
29+
import java.io.File;
30+
import java.net.InetSocketAddress;
31+
import java.net.URL;
32+
import java.util.ArrayList;
33+
import java.util.Optional;
34+
35+
public class TestSigV4AssumeRoleConfig {
36+
static String KEYSPACES_DEFAULT_CONF="keyspaces-reference-norole.conf";
37+
/**
38+
* Before executing this test, ensure that KeySpaces tables are created.
39+
* Refer ddl.cql and dml.cql to create and populate tables.
40+
* @param args
41+
* @throws Exception
42+
*/
43+
public static void main(String[] args) throws Exception {
44+
String keySpacesConf=KEYSPACES_DEFAULT_CONF;
45+
if(args.length>1){
46+
keySpacesConf=args[0];
47+
System.out.println("Using key spaces config file: "+keySpacesConf);
48+
keySpacesConf=Optional.of(keySpacesConf).filter(StringUtils::isBlank).orElse(KEYSPACES_DEFAULT_CONF);
49+
}
50+
51+
URL url = TestSigV4AssumeRoleConfig.class.getClassLoader().getResource(keySpacesConf);
52+
53+
File file = new File(url.toURI());
54+
// The CqlSession object is the main entry point of the driver.
55+
// It holds the known state of the actual Cassandra cluster (notably the Metadata).
56+
// This class is thread-safe, you should create a single instance (per target Cassandra cluster), and share
57+
// it throughout your application.
58+
try (CqlSession session = CqlSession.builder()
59+
.withConfigLoader(DriverConfigLoader.fromFile(file))
60+
.build()) {
61+
62+
// We use execute to send a query to Cassandra. This returns a ResultSet, which is essentially a collection
63+
// of Row objects.
64+
ResultSet rs = session.execute("select * from testkeyspace.testconf");
65+
// Extract the first row (which is the only one in this case).
66+
Row row = rs.one();
67+
68+
// Extract the value of the first (and only) column from the row.
69+
String releaseVersion = row.getString("category");
70+
System.out.printf("Cassandra version is: %s%n", releaseVersion);
71+
}
72+
}
73+
}

src/test/java/software/aws/mcs/auth/TestSigV4Config.java

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ public static void main(String[] args) throws Exception {
5555
//By default the reference.conf is loaded by the driver which contains all defaults.
5656
//You can override this by providing reference.conf on the classpath
5757
//to isolate test you can load conf with a custom name
58-
URL url = TestSigV4Config.class.getClassLoader().getResource("keyspaces-reference-norole.conf");
58+
URL url = TestSigV4Config.class.getClassLoader().getResource("keyspaces-reference.conf");
5959

6060
File file = new File(url.toURI());
6161
// The CqlSession object is the main entry point of the driver.
@@ -64,16 +64,18 @@ public static void main(String[] args) throws Exception {
6464
// it throughout your application.
6565
try (CqlSession session = CqlSession.builder()
6666
.withConfigLoader(DriverConfigLoader.fromFile(file))
67-
.build()) {
67+
.addContactPoints(contactPoints)
68+
.withLocalDatacenter("us-west-2")
69+
.build()) {
6870

6971
// We use execute to send a query to Cassandra. This returns a ResultSet, which is essentially a collection
7072
// of Row objects.
71-
ResultSet rs = session.execute("select * from testkeyspace.testconf");
73+
ResultSet rs = session.execute("select release_version from system.local");
7274
// Extract the first row (which is the only one in this case).
7375
Row row = rs.one();
7476

7577
// Extract the value of the first (and only) column from the row.
76-
String releaseVersion = row.getString("category");
78+
String releaseVersion = row.getString("release_version");
7779
System.out.printf("Cassandra version is: %s%n", releaseVersion);
7880
}
7981
}

0 commit comments

Comments
 (0)