From 619bd1017a47890bbd839059cfb0922f680325e4 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 27 Feb 2026 08:08:44 +0000 Subject: [PATCH 01/10] Initial plan From 7e034011ac1cdc11e2ef84227e51944476bb1973 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 27 Feb 2026 08:40:10 +0000 Subject: [PATCH 02/10] Upgrade Spring Boot from 3.5.11 to 4.0.3 and update compatible dependencies Co-authored-by: commjoen <1457214+commjoen@users.noreply.github.com> --- pom.xml | 28 +++++++++++-------- .../wrongsecrets/SecretsErrorController.java | 2 +- .../challenges/ChallengesCtfController.java | 21 ++++++++------ .../wrongsecrets/AboutControllerTests.java | 2 +- .../ChallengeAPiControllerTest.java | 2 +- .../ChallengesControllerTest.java | 2 +- .../SecretLeakageControllerTest.java | 2 +- .../SecretsErrorControllerTest.java | 2 +- .../wrongsecrets/SecurityConfigTest.java | 2 +- .../org/owasp/wrongsecrets/SpringDocTest.java | 2 +- .../wrongsecrets/StatsControllerTests.java | 2 +- .../canaries/CanaryCallbackTest.java | 2 +- ...esControllerWithPresetCloudValuesTest.java | 2 +- ...trollerWithPresetKubernetesValuesTest.java | 2 +- ...ChallengesControllerCTFClientModeTest.java | 2 +- .../ChallengesControllerCTFModeTest.java | 2 +- ...ollerCTFModeWithPresetCloudValuesTest.java | 2 +- ...TFModeWithPresetK8sAndVaultValuesTest.java | 2 +- ...CTFModeWithPresetK8sNoVaultValuesTest.java | 2 +- .../oauth/TokenControllerTest.java | 2 +- 20 files changed, 48 insertions(+), 37 deletions(-) diff --git a/pom.xml b/pom.xml index ee09bff9a..5c38850dc 100644 --- a/pom.xml +++ b/pom.xml @@ -5,7 +5,7 @@ org.springframework.boot spring-boot-starter-parent - 3.5.11 + 4.0.3 @@ -51,7 +51,7 @@ 5.3.8 3.6.0 13.2.0 - 6.0.0 + 7.0.0 2.9.1 12.1.0 2.3.7 @@ -61,9 +61,9 @@ 1.15.4 4.21.0 3.14.9 - 7.4.5 + 26.76.0 2.14.1 - 4.1.123.Final + 4.2.10.Final 25 3.7.1 10.0.3.0 @@ -77,12 +77,12 @@ 4.9.8.2 4.9.8 3.2.1 - 3.5.11 - 3.2.0 - 2025.0.0 - 6.5.8 + 4.0.3 + 4.0.1 + 2025.1.1 + 7.0.3 1.5 - 2.8.15 + 3.0.1 2.1.8 1.10.0 1.21.4 @@ -108,8 +108,8 @@ com.google.cloud - spring-cloud-gcp-dependencies - ${gcp.sdk.version} + libraries-bom + ${google.cloud.libraries-bom.version} pom import @@ -297,6 +297,12 @@ test + + org.springframework.boot + spring-boot-starter-webmvc-test + test + + uk.org.webcompere system-stubs-jupiter diff --git a/src/main/java/org/owasp/wrongsecrets/SecretsErrorController.java b/src/main/java/org/owasp/wrongsecrets/SecretsErrorController.java index c12b516f5..4d03bad15 100644 --- a/src/main/java/org/owasp/wrongsecrets/SecretsErrorController.java +++ b/src/main/java/org/owasp/wrongsecrets/SecretsErrorController.java @@ -1,7 +1,7 @@ package org.owasp.wrongsecrets; import io.swagger.v3.oas.annotations.Operation; -import org.springframework.boot.web.servlet.error.ErrorController; +import org.springframework.boot.webmvc.error.ErrorController; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.GetMapping; diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java b/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java index 8dc0de5ff..de2b7802d 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java @@ -3,8 +3,8 @@ import io.swagger.v3.oas.annotations.Operation; import java.util.List; import lombok.extern.slf4j.Slf4j; -import net.minidev.json.JSONArray; -import net.minidev.json.JSONObject; +import com.fasterxml.jackson.databind.node.ArrayNode; +import com.fasterxml.jackson.databind.node.JsonNodeFactory; import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.RuntimeEnvironment; import org.owasp.wrongsecrets.ScoreCard; @@ -45,11 +45,11 @@ public ChallengesCtfController( summary = "Gives all challenges back in a jsonArray, to be used with the Juiceshop CTF cli") public String getChallenges() { List definitions = challenges.getDefinitions().challenges(); - JSONObject json = new JSONObject(); - JSONArray jsonArray = new JSONArray(); + var json = JsonNodeFactory.instance.objectNode(); + ArrayNode jsonArray = JsonNodeFactory.instance.arrayNode(); for (int i = 0; i < definitions.size(); i++) { ChallengeDefinition definition = definitions.get(i); - JSONObject jsonChallenge = new JSONObject(); + var jsonChallenge = JsonNodeFactory.instance.objectNode(); jsonChallenge.put("id", i + 1); jsonChallenge.put("name", definition.name().name()); jsonChallenge.put("key", definition.name().shortName()); @@ -68,13 +68,18 @@ public String getChallenges() { .map(s -> s.hint().contents().get()) .orElse(disabledChallenge)); jsonChallenge.put("solved", scoreCard.getChallengeCompleted(definition)); - jsonChallenge.put("disabledEnv", getDisabledEnv(definition)); + String disabledEnv = getDisabledEnv(definition); + if (disabledEnv != null) { + jsonChallenge.put("disabledEnv", disabledEnv); + } else { + jsonChallenge.putNull("disabledEnv"); + } jsonChallenge.put("difficulty", getDificulty(definition.difficulty())); jsonArray.add(jsonChallenge); } json.put("status", "success"); - json.put("data", jsonArray); - String result = json.toJSONString(); + json.set("data", jsonArray); + String result = json.toString(); log.trace("returning {}", result); return result; } diff --git a/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java b/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java index 9f29e786d..83f61ceaf 100644 --- a/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java +++ b/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java @@ -7,7 +7,7 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java b/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java index ec09aaf9c..7a2f8b6ad 100644 --- a/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java @@ -7,7 +7,7 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java b/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java index b5c4fd031..2d05de499 100644 --- a/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java @@ -9,7 +9,7 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.challenges.Spoiler; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java b/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java index 1bf3b9b37..eb56509e7 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java @@ -8,7 +8,7 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.challenges.docker.WrongSecretsConstants; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; import org.springframework.test.web.servlet.request.MockMvcRequestBuilders; diff --git a/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java b/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java index a469aeba5..721103e74 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java @@ -7,7 +7,7 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java b/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java index 9664a94b0..1cc8f4430 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java @@ -8,7 +8,7 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.context.annotation.Import; import org.springframework.http.MediaType; diff --git a/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java b/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java index fe96cc0aa..b17d4f6f3 100644 --- a/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java @@ -17,7 +17,7 @@ import org.assertj.core.api.Assertions; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java b/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java index 06b0a75e7..6a708782a 100644 --- a/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java +++ b/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java @@ -7,7 +7,7 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java b/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java index ceedf3911..188b54a4a 100644 --- a/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java +++ b/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java @@ -6,7 +6,7 @@ import com.fasterxml.jackson.databind.ObjectMapper; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java b/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java index 2cc74c07f..ae33b4785 100644 --- a/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java @@ -10,7 +10,7 @@ import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java b/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java index 322151411..4eb347fac 100644 --- a/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java @@ -10,7 +10,7 @@ import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java index b672ddace..7dea8bb61 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java @@ -13,7 +13,7 @@ import org.owasp.wrongsecrets.WrongSecretsApplication; import org.owasp.wrongsecrets.challenges.docker.Challenge1; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java index ea42dd987..53bfc8eb6 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java @@ -12,7 +12,7 @@ import org.owasp.wrongsecrets.WrongSecretsApplication; import org.owasp.wrongsecrets.challenges.docker.Challenge1; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java index 7ca677902..f795d03a8 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java @@ -14,7 +14,7 @@ import org.owasp.wrongsecrets.challenges.cloud.Challenge10; import org.owasp.wrongsecrets.challenges.cloud.challenge11.Challenge11Aws; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java index f9a1ea16f..9effd3740 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java @@ -14,7 +14,7 @@ import org.owasp.wrongsecrets.challenges.kubernetes.Challenge6; import org.owasp.wrongsecrets.challenges.kubernetes.Challenge7; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java index 3c756a93a..9bab3f21e 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java @@ -14,7 +14,7 @@ import org.owasp.wrongsecrets.challenges.kubernetes.Challenge6; import org.owasp.wrongsecrets.challenges.kubernetes.Challenge7; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java b/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java index 3cc87606b..cbbdb7204 100644 --- a/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java @@ -8,7 +8,7 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; From 5ecae29cc76045976274873a44e6e52dba6b8ac2 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 27 Feb 2026 09:01:06 +0000 Subject: [PATCH 03/10] Pin Groovy to 4.0.25 for thymeleaf-layout-dialect compatibility with Spring Boot 4.0 Co-authored-by: commjoen <1457214+commjoen@users.noreply.github.com> --- pom.xml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/pom.xml b/pom.xml index 5c38850dc..560be680d 100644 --- a/pom.xml +++ b/pom.xml @@ -89,6 +89,8 @@ 3.1.3.RELEASE 3.4.0 1.4.0 + + 4.0.25 From 0a9a3ec9b787886a48992aa0afd40e1816bff37f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 27 Feb 2026 11:06:36 +0000 Subject: [PATCH 04/10] Fix Spotless import ordering violations after AutoConfigureMockMvc package change Co-authored-by: commjoen <1457214+commjoen@users.noreply.github.com> --- pom.xml | 6 +++--- .../wrongsecrets/challenges/ChallengesCtfController.java | 4 ++-- .../java/org/owasp/wrongsecrets/AboutControllerTests.java | 2 +- .../org/owasp/wrongsecrets/ChallengeAPiControllerTest.java | 2 +- .../org/owasp/wrongsecrets/ChallengesControllerTest.java | 2 +- .../org/owasp/wrongsecrets/SecretLeakageControllerTest.java | 2 +- .../org/owasp/wrongsecrets/SecretsErrorControllerTest.java | 2 +- .../java/org/owasp/wrongsecrets/SecurityConfigTest.java | 2 +- src/test/java/org/owasp/wrongsecrets/SpringDocTest.java | 2 +- .../java/org/owasp/wrongsecrets/StatsControllerTests.java | 2 +- .../org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java | 2 +- .../ChallengesControllerWithPresetCloudValuesTest.java | 2 +- .../ChallengesControllerWithPresetKubernetesValuesTest.java | 2 +- .../ctftests/ChallengesControllerCTFClientModeTest.java | 2 +- .../ctftests/ChallengesControllerCTFModeTest.java | 2 +- ...hallengesControllerCTFModeWithPresetCloudValuesTest.java | 2 +- ...gesControllerCTFModeWithPresetK8sAndVaultValuesTest.java | 2 +- ...ngesControllerCTFModeWithPresetK8sNoVaultValuesTest.java | 2 +- .../org/owasp/wrongsecrets/oauth/TokenControllerTest.java | 2 +- 19 files changed, 22 insertions(+), 22 deletions(-) diff --git a/pom.xml b/pom.xml index 560be680d..6895217de 100644 --- a/pom.xml +++ b/pom.xml @@ -61,8 +61,10 @@ 1.15.4 4.21.0 3.14.9 - 26.76.0 2.14.1 + 26.76.0 + + 4.0.25 4.2.10.Final 25 3.7.1 @@ -89,8 +91,6 @@ 3.1.3.RELEASE 3.4.0 1.4.0 - - 4.0.25 diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java b/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java index de2b7802d..a79555731 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/ChallengesCtfController.java @@ -1,10 +1,10 @@ package org.owasp.wrongsecrets.challenges; +import com.fasterxml.jackson.databind.node.ArrayNode; +import com.fasterxml.jackson.databind.node.JsonNodeFactory; import io.swagger.v3.oas.annotations.Operation; import java.util.List; import lombok.extern.slf4j.Slf4j; -import com.fasterxml.jackson.databind.node.ArrayNode; -import com.fasterxml.jackson.databind.node.JsonNodeFactory; import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.RuntimeEnvironment; import org.owasp.wrongsecrets.ScoreCard; diff --git a/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java b/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java index 83f61ceaf..51ff944c4 100644 --- a/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java +++ b/src/test/java/org/owasp/wrongsecrets/AboutControllerTests.java @@ -7,8 +7,8 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest diff --git a/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java b/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java index 7a2f8b6ad..52969d3e0 100644 --- a/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ChallengeAPiControllerTest.java @@ -7,8 +7,8 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest diff --git a/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java b/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java index 2d05de499..00386a675 100644 --- a/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ChallengesControllerTest.java @@ -9,8 +9,8 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.challenges.Spoiler; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest( diff --git a/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java b/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java index eb56509e7..ac5d25b69 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecretLeakageControllerTest.java @@ -8,8 +8,8 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.challenges.docker.WrongSecretsConstants; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; import org.springframework.test.web.servlet.request.MockMvcRequestBuilders; diff --git a/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java b/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java index 721103e74..4a0cae350 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecretsErrorControllerTest.java @@ -7,8 +7,8 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest diff --git a/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java b/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java index 1cc8f4430..b0d4c70bc 100644 --- a/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SecurityConfigTest.java @@ -8,8 +8,8 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.context.annotation.Import; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java b/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java index b17d4f6f3..d36ae1841 100644 --- a/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java +++ b/src/test/java/org/owasp/wrongsecrets/SpringDocTest.java @@ -17,8 +17,8 @@ import org.assertj.core.api.Assertions; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping; diff --git a/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java b/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java index 6a708782a..fef7f84f8 100644 --- a/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java +++ b/src/test/java/org/owasp/wrongsecrets/StatsControllerTests.java @@ -7,8 +7,8 @@ import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest diff --git a/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java b/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java index 188b54a4a..594df772e 100644 --- a/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java +++ b/src/test/java/org/owasp/wrongsecrets/canaries/CanaryCallbackTest.java @@ -6,8 +6,8 @@ import com.fasterxml.jackson.databind.ObjectMapper; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest diff --git a/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java b/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java index ae33b4785..a1149933a 100644 --- a/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/challenges/cloud/ChallengesControllerWithPresetCloudValuesTest.java @@ -10,8 +10,8 @@ import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest( diff --git a/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java b/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java index 4eb347fac..6aa06a78b 100644 --- a/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/challenges/kubernetes/ChallengesControllerWithPresetKubernetesValuesTest.java @@ -10,8 +10,8 @@ import org.owasp.wrongsecrets.Challenges; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.test.web.servlet.MockMvc; @SpringBootTest( diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java index 7dea8bb61..f8175fc4b 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFClientModeTest.java @@ -13,8 +13,8 @@ import org.owasp.wrongsecrets.WrongSecretsApplication; import org.owasp.wrongsecrets.challenges.docker.Challenge1; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java index 53bfc8eb6..1d5d82703 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeTest.java @@ -12,8 +12,8 @@ import org.owasp.wrongsecrets.WrongSecretsApplication; import org.owasp.wrongsecrets.challenges.docker.Challenge1; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java index f795d03a8..d8a5f48b6 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetCloudValuesTest.java @@ -14,8 +14,8 @@ import org.owasp.wrongsecrets.challenges.cloud.Challenge10; import org.owasp.wrongsecrets.challenges.cloud.challenge11.Challenge11Aws; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java index 9effd3740..89f68111e 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sAndVaultValuesTest.java @@ -14,8 +14,8 @@ import org.owasp.wrongsecrets.challenges.kubernetes.Challenge6; import org.owasp.wrongsecrets.challenges.kubernetes.Challenge7; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java index 9bab3f21e..c1799dec5 100644 --- a/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java +++ b/src/test/java/org/owasp/wrongsecrets/ctftests/ChallengesControllerCTFModeWithPresetK8sNoVaultValuesTest.java @@ -14,8 +14,8 @@ import org.owasp.wrongsecrets.challenges.kubernetes.Challenge6; import org.owasp.wrongsecrets.challenges.kubernetes.Challenge7; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; diff --git a/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java b/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java index cbbdb7204..22d0ae368 100644 --- a/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java +++ b/src/test/java/org/owasp/wrongsecrets/oauth/TokenControllerTest.java @@ -8,8 +8,8 @@ import org.junit.jupiter.api.Test; import org.owasp.wrongsecrets.WrongSecretsApplication; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.webmvc.test.autoconfigure.AutoConfigureMockMvc; import org.springframework.http.MediaType; import org.springframework.test.web.servlet.MockMvc; From f5d55ba467eb74760f177a90576e4867e6a46c78 Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 05:18:26 +0100 Subject: [PATCH 05/10] Fix netty operationsa nd issues --- Dockerfile | 4 ++-- pom.xml | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Dockerfile b/Dockerfile index 3865ddfdc..87c46ddcc 100644 --- a/Dockerfile +++ b/Dockerfile @@ -58,7 +58,7 @@ RUN mkdir -p /var/run/secrets/kubernetes.io/serviceaccount && \ chmod 600 /var/run/secrets/kubernetes.io/serviceaccount/token # Create a dynamic archive -RUN java -XX:ArchiveClassesAtExit=application.jsa -Dspring.context.exit=onRefresh -jar application.jar +RUN java --add-modules=jdk.unsupported -XX:ArchiveClassesAtExit=application.jsa -Dspring.context.exit=onRefresh -jar application.jar # Clean up the mocked token RUN rm -rf /var/run/secrets/kubernetes.io @@ -70,4 +70,4 @@ RUN rm -rf /var/run/secrets/kubernetes.io RUN adduser -u 2000 -D wrongsecrets USER wrongsecrets -CMD java -jar -XX:SharedArchiveFile=application.jsa -Dspring.profiles.active=$(echo ${SPRING_PROFILES_ACTIVE}) -Dspringdoc.swagger-ui.enabled=${SPRINGDOC_UI} -Dspringdoc.api-docs.enabled=${SPRINGDOC_DOC} -D application.jar +CMD java --add-modules=jdk.unsupported -jar -XX:SharedArchiveFile=application.jsa -Dspring.profiles.active=$(echo ${SPRING_PROFILES_ACTIVE}) -Dspringdoc.swagger-ui.enabled=${SPRINGDOC_UI} -Dspringdoc.api-docs.enabled=${SPRINGDOC_DOC} -D application.jar diff --git a/pom.xml b/pom.xml index 6895217de..490272771 100644 --- a/pom.xml +++ b/pom.xml @@ -65,7 +65,7 @@ 26.76.0 4.0.25 - 4.2.10.Final + 4.1.130.Final 25 3.7.1 10.0.3.0 From 37cb64e78279bcc52bccebd122f2227c9e873b31 Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 05:40:06 +0100 Subject: [PATCH 06/10] update gatling and others --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 490272771..5cccac961 100644 --- a/pom.xml +++ b/pom.xml @@ -47,7 +47,7 @@ 1.4.1 3.2.0 3.0.1 - 2.40.9 + 2.42.4 5.3.8 3.6.0 13.2.0 @@ -60,7 +60,7 @@ 1.14.0 1.15.4 4.21.0 - 3.14.9 + 3.15.0 2.14.1 26.76.0 From 780ba58245f83b7ea9a6c1c5c064cdf2a2bf10a4 Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 05:56:13 +0100 Subject: [PATCH 07/10] fixed some small code issues: challenge 59 slack clalback is nwo a record, and reason in challnege56 is now propperly formatted --- .../challenges/docker/Challenge59.java | 3 ++ .../docker/SlackNotificationService.java | 16 ++-------- .../explanations/challenge56_reason.adoc | 2 +- .../docker/SlackNotificationServiceTest.java | 30 +++++++------------ 4 files changed, 17 insertions(+), 34 deletions(-) diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge59.java b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge59.java index 11af3249f..f782e8c61 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge59.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge59.java @@ -3,6 +3,7 @@ import static java.nio.charset.StandardCharsets.UTF_8; import java.util.Base64; +import lombok.extern.slf4j.Slf4j; import org.owasp.wrongsecrets.challenges.FixedAnswerChallenge; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; @@ -12,6 +13,7 @@ * variables. Shows how an ex-employee could misuse the webhook if it's not rotated when they leave. */ @Component +@Slf4j public class Challenge59 extends FixedAnswerChallenge { private final String obfuscatedSlackWebhookUrl; @@ -37,6 +39,7 @@ private String deobfuscateSlackWebhookUrl(String obfuscatedUrl) { byte[] secondDecode = Base64.getDecoder().decode(firstDecode); return new String(secondDecode, UTF_8); } catch (Exception e) { + log.warn("Webhook URL not properly set for Slack in {}", this); // Return a default value if the environment variable is not properly set return "https://hooks.slack.com/services/T00000000/B00000000/XXXXXXXXXXXXXXXXXXXXXXXX"; } diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java b/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java index 024166fbe..9345b1f4f 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java @@ -1,7 +1,6 @@ package org.owasp.wrongsecrets.challenges.docker; import com.fasterxml.jackson.annotation.JsonProperty; -import com.fasterxml.jackson.databind.ObjectMapper; import java.util.Optional; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -19,15 +18,11 @@ public class SlackNotificationService { private static final Logger logger = LoggerFactory.getLogger(SlackNotificationService.class); private final RestTemplate restTemplate; - private final ObjectMapper objectMapper; private final Optional challenge59; public SlackNotificationService( - RestTemplate restTemplate, - ObjectMapper objectMapper, - @Autowired(required = false) Challenge59 challenge59) { + RestTemplate restTemplate, @Autowired(required = false) Challenge59 challenge59) { this.restTemplate = restTemplate; - this.objectMapper = objectMapper; this.challenge59 = Optional.ofNullable(challenge59); } @@ -94,16 +89,9 @@ private String buildCompletionMessage(String challengeName, String userName, Str } /** Simple record for Slack message payload. */ - public static class SlackMessage { - @JsonProperty("text") - private final String text; - + public record SlackMessage(@JsonProperty("text") String text) { public SlackMessage(String text) { this.text = text; } - - public String getText() { - return text; - } } } diff --git a/src/main/resources/explanations/challenge56_reason.adoc b/src/main/resources/explanations/challenge56_reason.adoc index 319fe2360..3a3096e86 100644 --- a/src/main/resources/explanations/challenge56_reason.adoc +++ b/src/main/resources/explanations/challenge56_reason.adoc @@ -5,7 +5,6 @@ Sometimes, secrets or sensitive information are added as examples or instruction This challenge highlights the importance of reviewing all project files—including documentation—for secrets and sensitive data. ---- - In a real project, you should always include explicit security requirements in your project specification or agentic plan. This means: - Listing how secrets should be managed, stored, and rotated. - Defining who has access to sensitive files and how access is controlled. @@ -13,6 +12,7 @@ In a real project, you should always include explicit security requirements in y - Requiring regular reviews of both code and documentation for accidental secret leakage. Adding these requirements helps ensure that security is considered from the start and reduces the risk of sensitive data exposure through overlooked files or bad practices. +---- [NOTE] ==== diff --git a/src/test/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationServiceTest.java b/src/test/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationServiceTest.java index 3ea174fc6..0d8719215 100644 --- a/src/test/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationServiceTest.java +++ b/src/test/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationServiceTest.java @@ -38,8 +38,7 @@ void shouldSendNotificationWithUserAgentWhenSlackIsConfigured() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenReturn(ResponseEntity.ok("ok")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser", userAgent); @@ -58,8 +57,7 @@ void shouldIncludeUserAgentInMessageWhenProvided() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenReturn(ResponseEntity.ok("ok")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser", userAgent); @@ -72,7 +70,7 @@ void shouldIncludeUserAgentInMessageWhenProvided() { HttpEntity capturedEntity = entityCaptor.getValue(); SlackNotificationService.SlackMessage slackMessage = (SlackNotificationService.SlackMessage) capturedEntity.getBody(); - assertTrue(slackMessage.getText().contains("(User-Agent: " + userAgent + ")")); + assertTrue(slackMessage.text().contains("(User-Agent: " + userAgent + ")")); } @Test @@ -83,8 +81,7 @@ void shouldNotIncludeUserAgentInMessageWhenNotProvided() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenReturn(ResponseEntity.ok("ok")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser", null); @@ -97,7 +94,7 @@ void shouldNotIncludeUserAgentInMessageWhenNotProvided() { HttpEntity capturedEntity = entityCaptor.getValue(); SlackNotificationService.SlackMessage slackMessage = (SlackNotificationService.SlackMessage) capturedEntity.getBody(); - assertFalse(slackMessage.getText().contains("User-Agent")); + assertFalse(slackMessage.text().contains("User-Agent")); } @Test @@ -108,8 +105,7 @@ void shouldSendNotificationWhenSlackIsConfigured() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenReturn(ResponseEntity.ok("ok")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser"); @@ -122,7 +118,7 @@ void shouldSendNotificationWhenSlackIsConfigured() { @Test void shouldNotSendNotificationWhenSlackNotConfigured() { // Given - slackNotificationService = new SlackNotificationService(restTemplate, objectMapper, null); + slackNotificationService = new SlackNotificationService(restTemplate, null); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser"); @@ -135,8 +131,7 @@ void shouldNotSendNotificationWhenSlackNotConfigured() { void shouldNotSendNotificationWhenWebhookUrlNotSet() { // Given when(challenge59.getSlackWebhookUrl()).thenReturn("not_set"); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser"); @@ -149,8 +144,7 @@ void shouldNotSendNotificationWhenWebhookUrlNotSet() { void shouldNotSendNotificationWhenWebhookUrlIsInvalid() { // Given when(challenge59.getSlackWebhookUrl()).thenReturn("https://example.com/invalid"); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", "testuser"); @@ -167,8 +161,7 @@ void shouldHandleRestTemplateException() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenThrow(new RuntimeException("Network error")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When & Then - should not throw exception assertDoesNotThrow( @@ -183,8 +176,7 @@ void shouldSendNotificationWithNullUsername() { when(restTemplate.postForEntity(anyString(), any(HttpEntity.class), eq(String.class))) .thenReturn(ResponseEntity.ok("ok")); - slackNotificationService = - new SlackNotificationService(restTemplate, objectMapper, challenge59); + slackNotificationService = new SlackNotificationService(restTemplate, challenge59); // When slackNotificationService.notifyChallengeCompletion("challenge-1", null); From 122e5dda02fccf64857dc94535819030e1333cff Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 06:04:18 +0100 Subject: [PATCH 08/10] replaced deprecated nullable class --- .../wrongsecrets/challenges/kubernetes/MetaDataChallenge.java | 2 +- .../challenges/kubernetes/VaultSubKeyChallenge.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/MetaDataChallenge.java b/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/MetaDataChallenge.java index 7df8b9297..eea149432 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/MetaDataChallenge.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/MetaDataChallenge.java @@ -3,10 +3,10 @@ import com.google.common.base.Strings; import java.util.Map; import lombok.extern.slf4j.Slf4j; +import org.jspecify.annotations.Nullable; import org.owasp.wrongsecrets.challenges.FixedAnswerChallenge; import org.springframework.beans.factory.annotation.Value; import org.springframework.cloud.vault.config.VaultProperties; -import org.springframework.lang.Nullable; import org.springframework.stereotype.Component; import org.springframework.vault.core.*; import org.springframework.vault.support.Versioned; diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/VaultSubKeyChallenge.java b/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/VaultSubKeyChallenge.java index 72b1b5fd1..14479f22c 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/VaultSubKeyChallenge.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/kubernetes/VaultSubKeyChallenge.java @@ -3,10 +3,10 @@ import java.util.Map; import java.util.Optional; import lombok.extern.slf4j.Slf4j; +import org.jspecify.annotations.Nullable; import org.owasp.wrongsecrets.challenges.FixedAnswerChallenge; import org.springframework.beans.factory.annotation.Value; import org.springframework.cloud.vault.config.VaultProperties; -import org.springframework.lang.Nullable; import org.springframework.stereotype.Component; import org.springframework.vault.core.VaultTemplate; import org.springframework.vault.core.VaultVersionedKeyValueOperations; From df9a9a75b121fc59c2e595924daa18a551a4d694 Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 06:19:52 +0100 Subject: [PATCH 09/10] Fix for slackmessage not being sent : significantly reducing log output, and having mockito as an agent, preventing future deprecation --- pom.xml | 14 +++++++++++++- .../challenges/docker/Challenge49.java | 2 +- .../challenges/docker/Challenge52.java | 5 ++++- .../docker/SlackNotificationService.java | 5 ++++- 4 files changed, 22 insertions(+), 4 deletions(-) diff --git a/pom.xml b/pom.xml index 5cccac961..074490bbf 100644 --- a/pom.xml +++ b/pom.xml @@ -666,12 +666,24 @@ gatling-maven-plugin ${gatling-maven-plugin.version} + + org.apache.maven.plugins + maven-dependency-plugin + 3.8.1 + + + + properties + + + + org.apache.maven.plugins maven-surefire-plugin ${maven-surefire-plugin.version} - -Dspring.profiles.active=test,maven-test + -Dspring.profiles.active=test,maven-test -javaagent:${org.mockito:mockito-core:jar} diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge49.java b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge49.java index 54184106b..51e816be6 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge49.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge49.java @@ -46,7 +46,7 @@ public boolean answerCorrect(String answer) { return false; } } catch (Exception e) { - log.warn("given answer is not an integer", e); + log.warn("given answer is not an integer. Exception: {}", e.getMessage()); return false; } diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge52.java b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge52.java index 5f7ce06fc..8a5ea184a 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge52.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/docker/Challenge52.java @@ -33,7 +33,10 @@ private String getActualSecret() { try { return Files.readString(Paths.get(dockerMountsecret, "secret.txt"), StandardCharsets.UTF_8); } catch (Exception e) { - log.warn("Exception during file reading, defaulting to default without cloud environment", e); + log.warn( + "Exception during file reading, defaulting to default without cloud environment." + + " Exception message: {}", + e.getMessage()); return Challenges.ErrorResponses.OUTSIDE_DOCKER; } } diff --git a/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java b/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java index 9345b1f4f..3c47a1e23 100644 --- a/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java +++ b/src/main/java/org/owasp/wrongsecrets/challenges/docker/SlackNotificationService.java @@ -54,7 +54,10 @@ public void notifyChallengeCompletion(String challengeName, String userName, Str "Successfully sent Slack notification for challenge completion: {}", challengeName); } catch (Exception e) { - logger.warn("Failed to send Slack notification for challenge: {}", challengeName, e); + logger.warn( + "Failed to send Slack notification for challenge: {}. Message: {}", + challengeName, + e.getMessage()); } } From b514c356b40af83b50dc4e7a81c31fffbc6d84e0 Mon Sep 17 00:00:00 2001 From: Jeroen Willemsen Date: Sat, 28 Feb 2026 06:29:57 +0100 Subject: [PATCH 10/10] Spring boot 4 adotpion list added --- README.md | 1 + docs/DEVELOPMENT_PATTERNS.md | 4 + docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md | 146 +++++++++++++++++++++++ 3 files changed, 151 insertions(+) create mode 100644 docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md diff --git a/README.md b/README.md index 7f1e3609b..599d1cac7 100644 --- a/README.md +++ b/README.md @@ -96,6 +96,7 @@ This repository contains **intentionally vulnerable code and configuration files ### 👨‍💻 Development & Contribution - [Notes on development](#notes-on-development) + - [Spring Boot 4 adoption checklist](docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md) - [Dependency management](#dependency-management) - [Get the project started in IntelliJ IDEA](#get-the-project-started-in-intellij-idea) - [Automatic reload during development](#automatic-reload-during-development) diff --git a/docs/DEVELOPMENT_PATTERNS.md b/docs/DEVELOPMENT_PATTERNS.md index 002e49e24..2849e7026 100644 --- a/docs/DEVELOPMENT_PATTERNS.md +++ b/docs/DEVELOPMENT_PATTERNS.md @@ -2,6 +2,10 @@ This document outlines common code patterns, conventions, and best practices used throughout the WrongSecrets project. +## Related documentation + +- [Spring Boot 4 Adoption Checklist](SPRING_BOOT_4_ADOPTION_CHECKLIST.md) + ## Challenge Structure Patterns ### Challenge Interface vs FixedAnswerChallenge diff --git a/docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md b/docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md new file mode 100644 index 000000000..b052551fc --- /dev/null +++ b/docs/SPRING_BOOT_4_ADOPTION_CHECKLIST.md @@ -0,0 +1,146 @@ +# Spring Boot 4 Adoption Checklist (WrongSecrets) + +This checklist is tailored to the current `wrongsecrets` codebase (Spring Boot `4.0.3`, Java `25`). + +## How to use this document + +- Keep this as a living checklist in PRs. +- Mark items complete when merged. +- Prefer small, focused migrations (one concern per PR). + +## Current baseline (already in place) + +- [x] Spring Boot `4.0.3` is configured in `pom.xml`. +- [x] Spring Cloud line is aligned (`2025.1.1`). +- [x] `@ConfigurationProperties` is already used in multiple places. +- [x] Mockito inline-mock-maker warning addressed by passing Mockito as Java agent in Surefire. + +--- + +## Priority 0 — Safety and consistency (start here) + +### 1) Standardize HTTP error responses with `ProblemDetail` + +- [ ] Add a global `@RestControllerAdvice` for API endpoints that returns `ProblemDetail`. +- [ ] Keep MVC HTML error handling as-is for Thymeleaf pages; only modernize JSON API errors. +- [ ] Add tests that assert RFC 9457-style payload fields (`type`, `title`, `status`, `detail`, `instance`). + +**Why now:** Reduces custom exception payload drift and improves API consistency. + +### 2) Replace new `RestTemplate` usage with `RestClient` + +- [ ] Stop introducing any new `RestTemplate` usage. +- [ ] Migrate existing bean in `WrongSecretsApplication` from `RestTemplate` to `RestClient.Builder`. +- [ ] Migrate call sites incrementally (start with `SlackNotificationService`). +- [ ] Add timeout and retry policy explicitly for outbound calls. + +**Current state:** `RestTemplate` bean and usage exist and can be migrated safely in phases. + +### 3) Add/verify deprecation gate in CI + +- [ ] Run compile with deprecation warnings enabled in CI (`-Xlint:deprecation`). +- [ ] Fail build on newly introduced deprecations (can be soft-fail initially). +- [ ] Track remaining suppressions/deprecations as explicit TODOs. + +**Why now:** Boot 4/Spring 7 deprecations will accumulate quickly otherwise. + +--- + +## Priority 1 — Observability and operability + +### 4) Enable tracing + log correlation end-to-end + +- [ ] Ensure tracing is enabled in all non-local profiles. +- [ ] Ensure logs include trace/span correlation IDs. +- [ ] Add dashboard/alerts for key challenge-flow operations. + +### 5) Harden Actuator for production profiles + +- [ ] Verify readiness/liveness probes are exposed and used by deployment manifests. +- [ ] Restrict sensitive actuator endpoints by profile. +- [ ] Add health contributors for external dependencies used in runtime profiles. + +### 6) Structured logging profile + +- [ ] Use JSON logs for cloud/container profiles. +- [ ] Keep developer-friendly text logs for local profile. +- [ ] Document expected log fields for incident response. + +--- + +## Priority 2 — Runtime and performance + +### 7) Evaluate virtual threads for I/O-heavy flows + +- [ ] Add profile-based toggle (`spring.threads.virtual.enabled=true`) for evaluation. +- [ ] Run load comparison (latency, throughput, memory) before default-enabling. +- [ ] Keep a rollback toggle in case of third-party incompatibilities. + +### 8) Validate graceful shutdown behavior + +- [ ] Verify request drain behavior on shutdown in containerized environments. +- [ ] Confirm no challenge state corruption occurs during rolling updates. + +### 9) AOT/native readiness checks + +- [ ] Add optional CI job for AOT/native compatibility (not necessarily release artifact yet). +- [ ] Record blockers (reflection/dynamic proxies/resources) in this document. + +--- + +## Priority 3 — Security and configuration posture + +### 10) Expand typed config, reduce scattered `@Value` + +- [ ] Introduce/extend `@ConfigurationProperties` classes for grouped settings. +- [ ] Limit direct `@Value` usage to simple one-off values. +- [ ] Validate config with bean validation annotations. + +### 11) TLS/SSL bundles standardization + +- [ ] Use SSL bundle config for outbound TLS trust/key material where applicable. +- [ ] Remove ad-hoc SSL setup code if present. + +### 12) Secret handling consistency by profile + +- [ ] Document expected secret source per profile (`docker`, `k8s`, `aws`, `gcp`, `azure`). +- [ ] Ensure no fallback path accidentally logs sensitive values. + +--- + +## Priority 4 — Testing modernization + +### 13) Keep Mockito java-agent setup stable + +- [x] Surefire passes Mockito as `-javaagent`. +- [ ] Mirror same setup in Failsafe if/when integration tests use inline mocking. + +### 14) Strengthen integration testing with Testcontainers service connection patterns + +- [ ] Prefer service-connection style wiring for test dependencies. +- [ ] Reduce custom bootstrapping code in integration tests where possible. + +### 15) Add contract tests for outbound HTTP clients + +- [ ] Add tests for success, timeout, retry, and non-2xx mapping behavior. +- [ ] Ensure migrated `RestClient` paths are fully covered. + +--- + +## Concrete first 5 PRs + +1. **PR 1:** Add API `ProblemDetail` advice + tests. +2. **PR 2:** Introduce `RestClient` bean and migrate `SlackNotificationService`. +3. **PR 3:** Add deprecation checks to CI and document policy. +4. **PR 4:** Add tracing/log-correlation defaults for non-local profiles. +5. **PR 5:** Virtual thread evaluation profile + benchmark notes. + +--- + +## Definition of done for Boot 4 adoption + +- [ ] No new `RestTemplate` code introduced. +- [ ] API errors are standardized on `ProblemDetail`. +- [ ] Deprecation warnings are tracked and controlled in CI. +- [ ] Observability baseline (metrics, traces, log correlation) is active in non-local profiles. +- [ ] Migration choices and rollout decisions are documented in `docs/`.