This is an automated email from the ASF dual-hosted git repository.
aldettinger pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel-quarkus.git
The following commit(s) were added to refs/heads/main by this push:
new ff092e5066 Fix and extend aws secret manager vault integration tests
for real instance (#6609)
ff092e5066 is described below
commit ff092e50666465f93c0ac71f607886e397e81598
Author: Lukas Lowinger <[email protected]>
AuthorDate: Tue Oct 8 18:50:32 2024 +0200
Fix and extend aws secret manager vault integration tests for real instance
(#6609)
---
integration-tests-jvm/aws-secrets-manager/pom.xml | 17 ++
.../manager/it/AwsSecretsManagerResource.java | 53 +++-
.../manager/it/AwsSecretsManagerRouteBuilder.java | 35 +++
.../src/main/resources/application.properties | 26 ++
.../manager/it/AwsSecretsManagerAbstractTest.java | 90 ++++++
.../secrets/manager/it/AwsSecretsManagerTest.java | 320 +++++++++++----------
.../it/AwsSecretsManagerTestEnvCustomizer.java | 13 +
.../it/CamelContextRefreshOnSecretRefreshTest.java | 72 +++++
.../manager/it/ContextReloadTestProfile.java | 34 +++
9 files changed, 511 insertions(+), 149 deletions(-)
diff --git a/integration-tests-jvm/aws-secrets-manager/pom.xml
b/integration-tests-jvm/aws-secrets-manager/pom.xml
index be9f5ce02f..0ec2440ed3 100644
--- a/integration-tests-jvm/aws-secrets-manager/pom.xml
+++ b/integration-tests-jvm/aws-secrets-manager/pom.xml
@@ -35,6 +35,10 @@
<groupId>org.apache.camel.quarkus</groupId>
<artifactId>camel-quarkus-aws-secrets-manager</artifactId>
</dependency>
+ <dependency>
+ <groupId>org.apache.camel.quarkus</groupId>
+ <artifactId>camel-quarkus-direct</artifactId>
+ </dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-resteasy</artifactId>
@@ -90,6 +94,19 @@
</exclusion>
</exclusions>
</dependency>
+ <dependency>
+ <groupId>org.apache.camel.quarkus</groupId>
+ <artifactId>camel-quarkus-direct-deployment</artifactId>
+ <version>${project.version}</version>
+ <type>pom</type>
+ <scope>test</scope>
+ <exclusions>
+ <exclusion>
+ <groupId>*</groupId>
+ <artifactId>*</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
</dependencies>
</profile>
</profiles>
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerResource.java
b/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerResource.java
index 09ce162bab..b75644da1b 100644
---
a/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerResource.java
+++
b/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerResource.java
@@ -19,9 +19,11 @@ package
org.apache.camel.quarkus.component.aws.secrets.manager.it;
import java.net.URI;
import java.util.Map;
import java.util.Objects;
+import java.util.concurrent.atomic.AtomicBoolean;
import java.util.stream.Collectors;
import jakarta.enterprise.context.ApplicationScoped;
+import jakarta.enterprise.event.Observes;
import jakarta.inject.Inject;
import jakarta.ws.rs.Consumes;
import jakarta.ws.rs.GET;
@@ -35,12 +37,15 @@ import jakarta.ws.rs.core.Response;
import org.apache.camel.CamelContext;
import org.apache.camel.Exchange;
import org.apache.camel.ProducerTemplate;
+import org.apache.camel.component.aws.secretsmanager.SecretsManagerConstants;
import org.apache.camel.component.aws.secretsmanager.SecretsManagerOperations;
+import org.apache.camel.impl.event.CamelContextReloadedEvent;
import org.apache.camel.spi.PeriodTaskResolver;
import org.apache.camel.support.PluginHelper;
import org.apache.camel.util.CollectionHelper;
import org.jboss.logging.Logger;
import
software.amazon.awssdk.services.secretsmanager.model.CreateSecretResponse;
+import
software.amazon.awssdk.services.secretsmanager.model.DeleteSecretRequest;
import
software.amazon.awssdk.services.secretsmanager.model.DeleteSecretResponse;
import
software.amazon.awssdk.services.secretsmanager.model.DescribeSecretResponse;
import
software.amazon.awssdk.services.secretsmanager.model.ListSecretsResponse;
@@ -64,6 +69,12 @@ public class AwsSecretsManagerResource {
@Inject
ProducerTemplate producerTemplate;
+ static final AtomicBoolean contextReloaded = new AtomicBoolean(false);
+
+ void onReload(@Observes CamelContextReloadedEvent event) {
+ contextReloaded.set(true);
+ }
+
@Path("/operation/{operation}")
@POST
@Consumes(MediaType.APPLICATION_JSON)
@@ -71,10 +82,24 @@ public class AwsSecretsManagerResource {
public Response post(@PathParam("operation") String operation,
@QueryParam("body") String body, Map<String, Object> headers)
throws Exception {
- Exchange ex =
producerTemplate.send("aws-secrets-manager://test?operation=" + operation, e ->
{
- e.getIn().setHeaders(headers);
- e.getIn().setBody(body);
- });
+ final Object resultBody;
+ if (operation.equals("forceDeleteSecret")) {
+ operation = SecretsManagerOperations.deleteSecret.toString();
+ DeleteSecretRequest.Builder builder =
DeleteSecretRequest.builder();
+ builder.secretId((String)
headers.get(SecretsManagerConstants.SECRET_ID));
+ builder.forceDeleteWithoutRecovery(true);
+ resultBody = builder.build();
+ } else {
+ resultBody = body;
+ }
+
+ String region = headers.containsKey("region") ?
String.format("region=%s&", headers.get("region")) : "";
+
+ Exchange ex =
producerTemplate.send(String.format("aws-secrets-manager://test?%soperation=%s",
region, operation),
+ e -> {
+ e.getIn().setHeaders(headers);
+ e.getIn().setBody(resultBody);
+ });
Object result;
switch (SecretsManagerOperations.valueOf(operation)) {
@@ -82,7 +107,7 @@ public class AwsSecretsManagerResource {
result = ex.getIn().getBody(CreateSecretResponse.class).arn();
break;
case listSecrets:
- //returns map with ar as a key and a flag, whether is deleted or
not
+ //returns map with arn as a key and a flag, whether is deleted or
not
result =
ex.getIn().getBody(ListSecretsResponse.class).secretList().stream()
.collect(Collectors.toMap(SecretListEntry::arn, e ->
e.deletedDate() == null ? false : true));
break;
@@ -124,4 +149,22 @@ public class AwsSecretsManagerResource {
Objects.requireNonNull(periodTaskResolver, "Expected a
PeriodTaskResolver to be configured");
return periodTaskResolver.newInstance("aws-secret-refresh",
Runnable.class).isPresent();
}
+
+ @Path("/context/reload")
+ @GET
+ @Produces(MediaType.TEXT_PLAIN)
+ public boolean contextReloadStatus() {
+ return contextReloaded.get();
+ }
+
+ @Path("/propertyFunction/{secretName}")
+ @GET
+ @Produces(MediaType.TEXT_PLAIN)
+ public Response propertyFunction(@PathParam("secretName") String
secretName)
+ throws Exception {
+ Exchange ex =
producerTemplate.request(String.format("direct:{{aws:%s}}", secretName), null);
+
+ return Response.ok(new
URI("https://camel.apache.org/")).entity(ex.getIn().getBody()).build();
+ }
+
}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerRouteBuilder.java
b/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerRouteBuilder.java
new file mode 100644
index 0000000000..ce58b98d7d
--- /dev/null
+++
b/integration-tests-jvm/aws-secrets-manager/src/main/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerRouteBuilder.java
@@ -0,0 +1,35 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.quarkus.component.aws.secrets.manager.it;
+
+import jakarta.enterprise.context.ApplicationScoped;
+import org.apache.camel.builder.RouteBuilder;
+
+@ApplicationScoped
+public class AwsSecretsManagerRouteBuilder extends RouteBuilder {
+
+ public static final String MSG_FIRST = "We have received the top secret
message.";
+ public static final String MSG_SECOND = "We have received the updated top
secret message.";
+
+ @Override
+ public void configure() throws Exception {
+ from("direct:loadFirst")
+ .setBody(simple(MSG_FIRST));
+ from("direct:loadSecond")
+ .setBody(simple(MSG_SECOND));
+ }
+}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/main/resources/application.properties
b/integration-tests-jvm/aws-secrets-manager/src/main/resources/application.properties
new file mode 100644
index 0000000000..eafb9fe166
--- /dev/null
+++
b/integration-tests-jvm/aws-secrets-manager/src/main/resources/application.properties
@@ -0,0 +1,26 @@
+## ---------------------------------------------------------------------------
+## Licensed to the Apache Software Foundation (ASF) under one or more
+## contributor license agreements. See the NOTICE file distributed with
+## this work for additional information regarding copyright ownership.
+## The ASF licenses this file to You under the Apache License, Version 2.0
+## (the "License"); you may not use this file except in compliance with
+## the License. You may obtain a copy of the License at
+##
+## http://www.apache.org/licenses/LICENSE-2.0
+##
+## Unless required by applicable law or agreed to in writing, software
+## distributed under the License is distributed on an "AS IS" BASIS,
+## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+## See the License for the specific language governing permissions and
+## limitations under the License.
+## ---------------------------------------------------------------------------
+#
+# Camel :: AWS Secrets Manager options
+#
+camel.component.aws-secrets-manager.access-key=${AWS_ACCESS_KEY}
+camel.component.aws-secrets-manager.secret-key=${AWS_SECRET_KEY}
+camel.component.aws-secrets-manager.region=${AWS_REGION:us-east-1}
+camel.component.aws-secrets-manager.useDefaultCredentialsProvider=${AWS_USE_DEFAULT_CREDENTIALS_PROVIDER}
+
+# Handy for debugging purposes
+#quarkus.log.category."software.amazon.awssdk".level=TRACE
\ No newline at end of file
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerAbstractTest.java
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerAbstractTest.java
new file mode 100644
index 0000000000..cc76947c9e
--- /dev/null
+++
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerAbstractTest.java
@@ -0,0 +1,90 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.quarkus.component.aws.secrets.manager.it;
+
+import java.util.Collections;
+import java.util.Map;
+import java.util.Objects;
+import java.util.concurrent.TimeUnit;
+
+import io.quarkus.logging.Log;
+import io.restassured.RestAssured;
+import io.restassured.http.ContentType;
+import org.apache.camel.component.aws.secretsmanager.SecretsManagerConstants;
+import org.apache.camel.component.aws.secretsmanager.SecretsManagerOperations;
+import org.testcontainers.shaded.org.awaitility.Awaitility;
+
+import static org.hamcrest.CoreMatchers.is;
+
+class AwsSecretsManagerAbstractTest {
+
+ protected String createSecret(String secretName, String secretValue) {
+ String createdArn = Awaitility.await()
+ .pollInterval(5, TimeUnit.SECONDS)
+ .atMost(1, TimeUnit.MINUTES)
+ .until(() -> {
+ try {
+ return RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_NAME, secretName))
+ .queryParam("body", secretValue)
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.createSecret)
+ .then()
+ .statusCode(201)
+ .extract().asString();
+ } catch (Exception e) {
+ return null;
+ }
+ }, Objects::nonNull);
+
+ return createdArn;
+ }
+
+ protected void updateSecret(String secretArn, String newValue) {
+ RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, secretArn))
+ .queryParam("body", newValue)
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.updateSecret)
+ .then()
+ .statusCode(201)
+ .body(is("true"));
+ }
+
+ protected Map<String, Boolean> listSecrets() {
+ return RestAssured.given()
+ .contentType(ContentType.JSON)
+ .body(Collections.emptyMap())
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.listSecrets)
+ .then()
+ .statusCode(201)
+ .extract().as(Map.class);
+ }
+
+ protected void deleteSecretImmediately(String arn) {
+ if (arn != null) {
+ Log.info("Deleting secret: " + arn);
+ RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, arn))
+ .post("/aws-secrets-manager/operation/forceDeleteSecret")
+ .then()
+ .statusCode(201)
+ .body(is("true"));
+ }
+ }
+}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTest.java
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTest.java
index 93a0754a47..a867a28858 100644
---
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTest.java
+++
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTest.java
@@ -18,6 +18,7 @@ package
org.apache.camel.quarkus.component.aws.secrets.manager.it;
import java.util.Collections;
import java.util.Map;
+import java.util.concurrent.TimeUnit;
import io.quarkus.test.common.QuarkusTestResource;
import io.quarkus.test.junit.QuarkusTest;
@@ -25,8 +26,12 @@ import io.restassured.RestAssured;
import io.restassured.http.ContentType;
import org.apache.camel.component.aws.secretsmanager.SecretsManagerConstants;
import org.apache.camel.component.aws.secretsmanager.SecretsManagerOperations;
+import org.apache.camel.quarkus.test.EnabledIf;
+import org.apache.camel.quarkus.test.mock.backend.MockBackendDisabled;
+import org.apache.camel.quarkus.test.mock.backend.MockBackendUtils;
import org.apache.camel.quarkus.test.support.aws2.Aws2TestResource;
import org.junit.jupiter.api.Test;
+import org.testcontainers.shaded.org.awaitility.Awaitility;
import static org.hamcrest.CoreMatchers.is;
import static org.junit.jupiter.api.Assertions.assertEquals;
@@ -36,154 +41,149 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
@QuarkusTest
@QuarkusTestResource(Aws2TestResource.class)
-class AwsSecretsManagerTest {
+public class AwsSecretsManagerTest extends AwsSecretsManagerAbstractTest {
@Test
public void testOperations() {
- final String secretToCreate = "changeit";
+ final String secretToCreate = "loadFirst";
final String secret2ToCreate = "changeit2";
- final String secretToUpdate = "changeit123";
- final String nameToCreate = "TestSecret";
- final String name2ToCreate = "TestSecret2";
-
- String createdArn = RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_NAME,
nameToCreate))
- .queryParam("body", secretToCreate)
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.createSecret)
- .then()
- .statusCode(201)
- .extract().asString();
-
- assertNotNull(createdArn);
-
- String createdArn2 = RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_NAME,
name2ToCreate))
- .queryParam("body", secret2ToCreate)
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.createSecret)
- .then()
- .statusCode(201)
- .extract().asString();
-
- assertNotNull(createdArn);
-
- Map secrets = RestAssured.given()
- .contentType(ContentType.JSON)
- .body(Collections.emptyMap())
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.listSecrets)
- .then()
- .statusCode(201)
- .extract().as(Map.class);
-
- assertEquals(2, secrets.size());
- assertTrue(secrets.containsKey(createdArn));
- assertTrue(secrets.containsKey(createdArn2));
- //none of them is deleted
- assertFalse(secrets.containsValue(true));
-
- String secret = RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.getSecret)
- .then()
- .statusCode(201)
- .extract().asString();
-
- assertEquals(secretToCreate, secret);
-
- Map description = RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.describeSecret)
- .then()
- .statusCode(201)
- .extract().as(Map.class);
-
- assertEquals(2, description.size());
- assertEquals(true, description.get("sdkHttpSuccessful"));
- assertEquals(nameToCreate, description.get("name"));
-
- RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn2))
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.deleteSecret)
- .then()
- .statusCode(201)
- .body(is("true"));
-
- secrets = RestAssured.given()
- .contentType(ContentType.JSON)
- .body(Collections.emptyMap())
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.listSecrets)
- .then()
- .statusCode(201)
- .extract().as(Map.class);
-
- assertEquals(2, secrets.size());
- assertFalse((Boolean) secrets.get(createdArn));
- assertTrue((Boolean) secrets.get(createdArn2));
-
- // operation rotateSecret fails on local stack with 500 when upgraded
to 2.2.0
- // TODO:See https://github.com/apache/camel-quarkus/issues/5300
- // RestAssured.given()
- // .contentType(ContentType.JSON)
- //
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
- // .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.rotateSecret)
- // .then()
- // .statusCode(201)
- // .body(is("true"));
-
- RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
- .queryParam("body", secretToUpdate)
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.updateSecret)
- .then()
- .statusCode(201)
- .body(is("true"));
-
- String updatedSecret = RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.getSecret)
- .then()
- .statusCode(201)
- .extract().asString();
-
- assertEquals(secretToUpdate, updatedSecret);
-
- RestAssured.given()
- .contentType(ContentType.JSON)
-
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn2))
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.restoreSecret)
- .then()
- .statusCode(201)
- .body(is("true"));
-
- secrets = RestAssured.given()
- .contentType(ContentType.JSON)
- .body(Collections.emptyMap())
- .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.listSecrets)
- .then()
- .statusCode(201)
- .extract().as(Map.class);
-
- assertEquals(2, secrets.size());
- assertTrue(secrets.containsKey(createdArn));
- assertTrue(secrets.containsKey(createdArn2));
- //none of them is deleted, because it was restored
- assertFalse(secrets.containsValue(true));
-
- // operation replicateSecretToRegions fails on local stack with
500
- // RestAssured.given()
- // .contentType(ContentType.JSON)
- //
.body(CollectionHelper.mapOf(SecretsManagerConstants.SECRET_ID, createdArn2,
- //
SecretsManagerConstants.SECRET_REPLICATION_REGIONS, "us-east-1"))
- // .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.replicateSecretToRegions)
- // .then()
- // .statusCode(201)
- // .body(is("true"));
+ final String secretToUpdate = "loadSecond";
+ final String nameToCreate = "CQTestSecret" +
System.currentTimeMillis();
+ final String name2ToCreate = "CQTestSecret2" +
System.currentTimeMillis();
+ String createdArn = null;
+ String createdArn2 = null;
+
+ try {
+ createdArn = createSecret(nameToCreate, secretToCreate);
+ assertNotNull(createdArn);
+
+ createdArn2 = RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_NAME,
name2ToCreate))
+ .queryParam("body", secret2ToCreate)
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.createSecret)
+ .then()
+ .statusCode(201)
+ .extract().asString();
+
+ assertNotNull(createdArn);
+
+ final String finalCreatedArn = createdArn;
+ final String finalCreatedArn2 = createdArn2;
+ Awaitility.await().pollInterval(5, TimeUnit.SECONDS).atMost(1,
TimeUnit.MINUTES).untilAsserted(
+ () -> {
+ Map<String, Boolean> secrets = listSecrets();
+ // contains both created secrets
+ assertTrue(secrets.containsKey(finalCreatedArn));
+ assertTrue(secrets.containsKey(finalCreatedArn2));
+ });
+
+ String secret = RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.getSecret)
+ .then()
+ .statusCode(201)
+ .extract().asString();
+
+ assertEquals(secretToCreate, secret);
+
+ Map description = RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.describeSecret)
+ .then()
+ .statusCode(201)
+ .extract().as(Map.class);
+
+ assertEquals(2, description.size());
+ assertEquals(true, description.get("sdkHttpSuccessful"));
+ assertEquals(nameToCreate, description.get("name"));
+
+ RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn2))
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.deleteSecret)
+ .then()
+ .statusCode(201)
+ .body(is("true"));
+
+ Awaitility.await().pollInterval(5, TimeUnit.SECONDS).atMost(1,
TimeUnit.MINUTES).untilAsserted(
+ () -> {
+ Map<String, Boolean> secrets = listSecrets();
+ // by default secrets marked for deletion are not
listed (can be enabled with
https://sdk.amazonaws.com/java/api/latest/software/amazon/awssdk/services/secretsmanager/model/ListSecretsRequest.Builder.html#includePlannedDeletion(java.lang.Boolean))
+ // but on localstack they are present (with non-null
deletedDate field) - see https://github.com/localstack/localstack/issues/11635
+ assertTrue(secrets.containsKey(finalCreatedArn));
+ if (!MockBackendUtils.startMockBackend(false)) {
+ assertFalse(secrets.containsKey(finalCreatedArn2));
+ } else {
+ assertFalse(secrets.get(finalCreatedArn));
+ assertTrue(secrets.get(finalCreatedArn2));
+ }
+ });
+
+ // operation rotateSecret fails on local stack with 500 when
upgraded to 2.2.0
+ // it needs lambda function ARN to work
+ // TODO:See https://github.com/apache/camel-quarkus/issues/5300
+
+ // RestAssured.given()
+ // .contentType(ContentType.JSON)
+ //
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
+ // .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.rotateSecret)
+ // .then()
+ // .statusCode(201)
+ // .body(is("true"));
+
+ updateSecret(createdArn, secretToUpdate);
+
+ String updatedSecret = RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn))
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.getSecret)
+ .then()
+ .statusCode(201)
+ .extract().asString();
+
+ assertEquals(secretToUpdate, updatedSecret);
+
+ RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, createdArn2))
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.restoreSecret)
+ .then()
+ .statusCode(201)
+ .body(is("true"));
+
+ Awaitility.await().pollInterval(5, TimeUnit.SECONDS).atMost(1,
TimeUnit.MINUTES).untilAsserted(
+ () -> {
+ Map<String, Boolean> secrets = listSecrets();
+
+ //none of them is deleted, because they were restored
+ assertTrue(secrets.containsKey(finalCreatedArn));
+ assertTrue(secrets.containsKey(finalCreatedArn2));
+ });
+
+ // operation replicateSecretToRegions fails on local stack with 500
+ // There is no possibility to delete secret in different region
via camel
+
+ // find different region then the actually used
+ // String anotherRegion = regions().stream().filter(region ->
!region.equals(region())).findFirst().get();
+ // RestAssured.given()
+ // .contentType(ContentType.JSON)
+ // .body(CollectionHelper.mapOf(SecretsManagerConstants.SECRET_ID,
createdArn2,
+ // SecretsManagerConstants.SECRET_REPLICATION_REGIONS,
anotherRegion))
+ // .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.replicateSecretToRegions)
+ // .then()
+ // .statusCode(201)
+ // .body(is("true"));
+ } finally {
+ if (!MockBackendUtils.startMockBackend(false)) {
+ // we must clean created secrets
+ // skip cleaning on localstack
+ deleteSecretImmediately(createdArn);
+ deleteSecretImmediately(createdArn2);
+ }
+ }
}
@Test
@@ -193,4 +193,36 @@ class AwsSecretsManagerTest {
.statusCode(200)
.body(is("true"));
}
+
+ @Test
+ // https://issues.apache.org/jira/browse/CAMEL-21330
+ @EnabledIf(MockBackendDisabled.class)
+ public void testPropertyFunction() {
+ String createdArn = null;
+ final String secretToCreate = "loadFirst";
+ final String secretToUpdate = "loadSecond";
+ try {
+ final String nameToCreate = "CQTestSecretPropFunction" +
System.currentTimeMillis();
+ createdArn = createSecret(nameToCreate, secretToCreate);
+ assertNotNull(createdArn);
+
+ RestAssured.get("/aws-secrets-manager/propertyFunction/" +
nameToCreate)
+ .then()
+ .statusCode(200)
+ .body(is(AwsSecretsManagerRouteBuilder.MSG_FIRST));
+
+ updateSecret(createdArn, secretToUpdate);
+
+ RestAssured.get("/aws-secrets-manager/propertyFunction/" +
nameToCreate)
+ .then()
+ .statusCode(200)
+ .body(is(AwsSecretsManagerRouteBuilder.MSG_SECOND));
+ } finally {
+ if (!MockBackendUtils.startMockBackend(false)) {
+ // we must clean created secrets
+ // skip cleaning on localstack
+ deleteSecretImmediately(createdArn);
+ }
+ }
+ }
}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTestEnvCustomizer.java
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTestEnvCustomizer.java
index 973dacb4eb..c98631eb00 100644
---
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTestEnvCustomizer.java
+++
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/AwsSecretsManagerTestEnvCustomizer.java
@@ -19,6 +19,7 @@ package
org.apache.camel.quarkus.component.aws.secrets.manager.it;
import java.util.Map;
import java.util.stream.Collectors;
+import org.apache.camel.quarkus.test.mock.backend.MockBackendUtils;
import org.apache.camel.quarkus.test.support.aws2.Aws2TestEnvContext;
import org.apache.camel.quarkus.test.support.aws2.Aws2TestEnvCustomizer;
import org.testcontainers.containers.localstack.LocalStackContainer.Service;
@@ -45,5 +46,17 @@ public class AwsSecretsManagerTestEnvCustomizer implements
Aws2TestEnvCustomizer
for (Map.Entry<String, String> e : p2.entrySet()) {
envContext.property(e.getKey(), e.getValue());
}
+
+ if (MockBackendUtils.startMockBackend(false)) {
+ envContext.property("camel.vault.aws.accessKey",
+ p2.get("camel.component.aws-secrets-manager.access-key"));
+ envContext.property("camel.vault.aws.secretKey",
+ p2.get("camel.component.aws-secrets-manager.secret-key"));
+ envContext.property("camel.vault.aws.region",
p2.get("camel.component.aws-secrets-manager.region"));
+ } else {
+ envContext.property("camel.vault.aws.accessKey",
System.getenv("AWS_ACCESS_KEY"));
+ envContext.property("camel.vault.aws.secretKey",
System.getenv("AWS_SECRET_KEY"));
+ envContext.property("camel.vault.aws.region",
System.getenv("AWS_REGION"));
+ }
}
}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/CamelContextRefreshOnSecretRefreshTest.java
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/CamelContextRefreshOnSecretRefreshTest.java
new file mode 100644
index 0000000000..0a7d18f6a3
--- /dev/null
+++
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/CamelContextRefreshOnSecretRefreshTest.java
@@ -0,0 +1,72 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.quarkus.component.aws.secrets.manager.it;
+
+import java.util.Collections;
+import java.util.concurrent.TimeUnit;
+
+import io.quarkus.test.common.QuarkusTestResource;
+import io.quarkus.test.junit.QuarkusTest;
+import io.quarkus.test.junit.TestProfile;
+import io.restassured.RestAssured;
+import io.restassured.http.ContentType;
+import org.apache.camel.component.aws.secretsmanager.SecretsManagerConstants;
+import org.apache.camel.component.aws.secretsmanager.SecretsManagerOperations;
+import org.apache.camel.quarkus.test.EnabledIf;
+import org.apache.camel.quarkus.test.mock.backend.MockBackendDisabled;
+import org.apache.camel.quarkus.test.support.aws2.Aws2TestResource;
+import org.eclipse.microprofile.config.ConfigProvider;
+import org.junit.jupiter.api.Disabled;
+import org.junit.jupiter.api.Test;
+import org.testcontainers.shaded.org.awaitility.Awaitility;
+
+import static org.hamcrest.CoreMatchers.is;
+
+@QuarkusTest
+@QuarkusTestResource(Aws2TestResource.class)
+@TestProfile(ContextReloadTestProfile.class)
+// disabled on Localstack due to
https://docs.localstack.cloud/references/coverage/coverage_cloudtrail/#lookupevents
+@EnabledIf(MockBackendDisabled.class)
+@Disabled("https://issues.apache.org/jira/browse/CAMEL-21324")
+public class CamelContextRefreshOnSecretRefreshTest extends
AwsSecretsManagerAbstractTest {
+ @Test
+ public void testCamelContextReloadOnSecretRefresh() {
+ String secretArn = null;
+ try {
+ final String myUniqueSecretValue = "Uniqueee1234";
+ secretArn =
createSecret(ConfigProvider.getConfig().getValue("camel.vault.aws.secrets",
String.class),
+ myUniqueSecretValue);
+ RestAssured.given()
+ .contentType(ContentType.JSON)
+
.body(Collections.singletonMap(SecretsManagerConstants.SECRET_ID, secretArn))
+ .queryParam("body", myUniqueSecretValue + "-diff")
+ .post("/aws-secrets-manager/operation/" +
SecretsManagerOperations.updateSecret)
+ .then()
+ .statusCode(201)
+ .body(is("true"));
+ Awaitility.await().pollInterval(5, TimeUnit.SECONDS).atMost(5,
TimeUnit.MINUTES).untilAsserted(
+ () -> {
+ RestAssured.get("/aws-secrets-manager/context/reload")
+ .then()
+ .statusCode(200)
+ .body(is("true"));
+ });
+ } finally {
+ deleteSecretImmediately(secretArn);
+ }
+ }
+}
diff --git
a/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/ContextReloadTestProfile.java
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/ContextReloadTestProfile.java
new file mode 100644
index 0000000000..b778b37df1
--- /dev/null
+++
b/integration-tests-jvm/aws-secrets-manager/src/test/java/org/apache/camel/quarkus/component/aws/secrets/manager/it/ContextReloadTestProfile.java
@@ -0,0 +1,34 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.quarkus.component.aws.secrets.manager.it;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import io.quarkus.test.junit.QuarkusTestProfile;
+
+public class ContextReloadTestProfile implements QuarkusTestProfile {
+ @Override
+ public Map<String, String> getConfigOverrides() {
+ Map<String, String> props = new HashMap<>();
+ props.put("camel.vault.aws.refreshEnabled", "true");
+ props.put("camel.vault.aws.refreshPeriod", "5000");
+ props.put("camel.vault.aws.secrets", "CQTestSecretContextReload" +
System.currentTimeMillis());
+ props.put("camel.main.context-reload-enabled", "true");
+ return props;
+ }
+}