4

I have following code snippet, that is supposed to run in a AWS Lambda function:

AWSSecretsManager client = AWSSecretsManagerClientBuilder.standard().withRegion(AWS_REGION).build();
GetSecretValueRequest getSecretValueRequest = new GetSecretValueRequest().withSecretId(SECRET_NAME);
GetSecretValueResult secretValue = client.getSecretValue(getSecretValueRequest);

As the lambda function is going to be run in the same VPC as the secret manager I don't have to provide credentials (AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY) for it.

I use Localstack with Testcontainers for integration tests and set up the secret in the test setup like this:

AWSSecretsManager secretsManager = AWSSecretsManagerClientBuilder.standard()
        .withEndpointConfiguration(secretsmanager.getEndpointConfiguration(SECRETSMANAGER))
        .withCredentials(secretsmanager.getDefaultCredentialsProvider())
        .build();
String secretString = "{'engine':'mysql','port':" + mysql.getMappedPort(3306) + ",'host':'" + mysql.getContainerIpAddress() + "'}";
CreateSecretRequest request = new CreateSecretRequest().withName("aurora")
        .withSecretString(secretString)
        .withRequestCredentialsProvider(secretsmanager.getDefaultCredentialsProvider());
secretsManager.createSecret(request);

Now the test crashes with an error:

com.amazonaws.services.secretsmanager.model.AWSSecretsManagerException: 
The security token included in the request is invalid. 
(Service: AWSSecretsManager; 
Status Code: 400; Error Code: 
UnrecognizedClientException; 
Request ID: ...

Here is also the definition of the localstack container used in the test:

@ClassRule
public static LocalStackContainer secretsmanager = new LocalStackContainer("0.10.4")
    .withServices(LocalStackContainer.Service.SECRETSMANAGER)
    .withEnv("DEFAULT_REGION", "eu-west-1")
    .withExposedPorts(4584);

How could I configure the LocalStackContainer to accept requests without any credentials validation going on?

Ira Re
  • 730
  • 3
  • 9
  • 25
  • 'How could I configure the LocalStackContainer to accept requests without any credentials validation going on?' - I don't think you can because you're trying to make requests to aws secretsmanager which requires valid aws credentials – committedandroider Nov 18 '19 at 19:38
  • @Ira Re, I am also facing the same issue. did you find any solution? – unknown Mar 23 '21 at 01:49
  • I don't exactly remember how the error was solved. I can see now that my LocalStackContainer has two other env vars: .withEnv("HOSTNAME", "https://secretsmanager.eu-west-1.amazonaws.com") .withEnv("LOCALSTACK_HOSTNAME", "https://secretsmanager.eu-west-1.amazonaws.com") Not sure though, if that's what I was missing. – Ira Re Mar 23 '21 at 13:19
  • Thanks for the quick reply. I have tried but still, I get the same error. Could you please have a look https://github.com/testcontainers/testcontainers-java/issues/3926. – unknown Mar 24 '21 at 14:04
  • @Ira Re instead of secretsmanager.eu-west-1.amazonaws.com I use localhost.. – unknown 2 hours ago Delete – unknown Mar 24 '21 at 16:08
  • @Ira Re, it would be great if you post the answer here with a sample working code – unknown Mar 25 '21 at 04:40
  • you can find the working sample here https://stackoverflow.com/questions/66811893/localstack-throws-the-security-token-included-in-the-request-is-invalid – unknown Mar 26 '21 at 12:46
  • Thanks for posting the answer here. Sorry, didn't have time to get to it earlier. – Ira Re Apr 01 '21 at 11:04

1 Answers1

-1

Assuming you prefer spring boot test and junit5 over alternatives, @DynamicPropertySource can be quite handy here

private static final LocalStackContainer LOCALSTACK = ...;

@DynamicPropertySource
static void setCredentials(DynamicPropertyRegistry registry) {
    var credentials = LOCALSTACK.getDefaultCredentialsProvider().getCredentials();
    registry.add("cloud.aws.region.static", () -> "eu-central-1");
    registry.add("cloud.aws.credentials.access-key", () -> credentials.getAWSAccessKeyId());
    registry.add("cloud.aws.credentials.secret-key", () -> credentials.getAWSSecretKey());
    registry.add("cloud.aws.s3.endpoint", () -> LOCALSTACK.getEndpointOverride(S3));
}

Also please doublecheck you've overridden the endpoints you rely on (s3 in my example), otherwise you may request real AWS API instead of the containerized one

user229044
  • 232,980
  • 40
  • 330
  • 338