From 95dfd22c08dbd44e20271d8c88755b60dc6fd699 Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Mon, 10 Feb 2025 16:33:54 +0000 Subject: [PATCH 01/10] plugins --- build.gradle | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/build.gradle b/build.gradle index 008d4ddbea..3e42fe379b 100644 --- a/build.gradle +++ b/build.gradle @@ -1,3 +1,5 @@ +import uk.gov.hmcts.rse.AuthMode + plugins { id 'application' id 'jacoco' @@ -6,6 +8,8 @@ plugins { id 'com.github.ben-manes.versions' version '0.52.0' id 'org.sonarqube' version '6.0.1.5171' id 'net.serenity-bdd.serenity-gradle-plugin' version '4.2.16' + id 'hmcts.ccd.sdk' + id 'com.github.hmcts.rse-cft-lib' /* Applies analysis tools including checkstyle and OWASP Dependency checker. See https://github.com/hmcts/gradle-java-plugin @@ -250,10 +254,12 @@ bootJar { } // Gradle 7.x issue, workaround from: https://github.com/gradle/gradle/issues/17236#issuecomment-894768083 -rootProject.tasks.named("processSmokeTestResources") { +project.tasks.named("processSmokeTestResources") { duplicatesStrategy = 'include' } -wrapper { - distributionType = Wrapper.DistributionType.ALL +bootWithCCD { + group = 'ccd tasks' + authMode = AuthMode.Local } + From 3b604466d98e3cbb980aa89742567d5cd8050c0c Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 12 Feb 2025 16:07:06 +0000 Subject: [PATCH 02/10] config generator & cftlib demo --- build.gradle | 5 +- settings.gradle | 8 +++ .../uk/gov/hmcts/reform/pcs/CftlibConfig.java | 46 +++++++++++++++++ .../uk/gov/hmcts/reform/pcs/Application.java | 7 ++- .../uk/gov/hmcts/reform/pcs/ccd/CaseType.java | 36 +++++++++++++ .../pcs/ccd/domain/DefaultStateAccess.java | 19 +++++++ .../hmcts/reform/pcs/ccd/domain/PCSCase.java | 10 ++++ .../hmcts/reform/pcs/ccd/domain/State.java | 17 +++++++ .../hmcts/reform/pcs/ccd/domain/UserRole.java | 17 +++++++ .../reform/pcs/ccd/event/CreateTestCase.java | 50 +++++++++++++++++++ src/main/resources/application.yaml | 2 +- 11 files changed, 213 insertions(+), 4 deletions(-) create mode 100644 settings.gradle create mode 100644 src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java diff --git a/build.gradle b/build.gradle index 3e42fe379b..30dc9c8359 100644 --- a/build.gradle +++ b/build.gradle @@ -8,8 +8,9 @@ plugins { id 'com.github.ben-manes.versions' version '0.52.0' id 'org.sonarqube' version '6.0.1.5171' id 'net.serenity-bdd.serenity-gradle-plugin' version '4.2.16' - id 'hmcts.ccd.sdk' - id 'com.github.hmcts.rse-cft-lib' + id 'hmcts.ccd.sdk' version '5.5.16' + id 'com.github.hmcts.rse-cft-lib' version '0.19.1573' + id 'io.freefair.lombok' version '8.12.1' /* Applies analysis tools including checkstyle and OWASP Dependency checker. See https://github.com/hmcts/gradle-java-plugin diff --git a/settings.gradle b/settings.gradle new file mode 100644 index 0000000000..c49ebda762 --- /dev/null +++ b/settings.gradle @@ -0,0 +1,8 @@ +pluginManagement { + repositories { + gradlePluginPortal() + maven { + url "https://jitpack.io" + } + } +} diff --git a/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java new file mode 100644 index 0000000000..0053e67741 --- /dev/null +++ b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java @@ -0,0 +1,46 @@ +package uk.gov.hmcts.reform.pcs; + +import org.apache.commons.io.FileUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Lazy; +import org.springframework.stereotype.Component; +import uk.gov.hmcts.ccd.sdk.CCDDefinitionGenerator; +import uk.gov.hmcts.reform.pcs.ccd.domain.State; +import uk.gov.hmcts.rse.ccd.lib.ControlPlane; +import uk.gov.hmcts.rse.ccd.lib.Database; +import uk.gov.hmcts.rse.ccd.lib.api.CFTLib; +import uk.gov.hmcts.rse.ccd.lib.api.CFTLibConfigurer; + +import java.io.File; +import java.io.IOException; +import java.util.List; +import java.util.Map; + +@Component +public class CftlibConfig implements CFTLibConfigurer { + @Autowired + @Lazy + CCDDefinitionGenerator configWriter; + + @Override + public void configure(CFTLib lib) throws Exception { + var users = Map.of( + "caseworker@pcs.com", List.of("caseworker", "caseworker-civil")); + + for (var entry : users.entrySet()) { + lib.createIdamUser(entry.getKey(), entry.getValue().toArray(new String[0])); + lib.createProfile(entry.getKey(), "CIVIL", "PCS", State.Open.name()); + } + + lib.createRoles( + "caseworker", + "caseworker-civil" + ); + + // Generate CCD definitions + configWriter.generateAllCaseTypesToJSON(new File("build/definitions")); + + // Import CCD definitions + lib.importJsonDefinition(new File("build/definitions/PCS")); + } +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/Application.java b/src/main/java/uk/gov/hmcts/reform/pcs/Application.java index 99b52127ec..ae39ae2347 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/Application.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/Application.java @@ -3,7 +3,12 @@ import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; -@SpringBootApplication +@SpringBootApplication( + scanBasePackages = { + "uk.gov.hmcts.reform.pcs", + "uk.gov.hmcts.ccd.sdk" + } +) @SuppressWarnings("HideUtilityClassConstructor") // Spring needs a constructor, its not a utility class public class Application { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java new file mode 100644 index 0000000000..4cd26fa254 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java @@ -0,0 +1,36 @@ +package uk.gov.hmcts.reform.pcs.ccd; + +import org.springframework.stereotype.Component; +import uk.gov.hmcts.ccd.sdk.api.CCDConfig; +import uk.gov.hmcts.ccd.sdk.api.ConfigBuilder; +import uk.gov.hmcts.reform.pcs.ccd.domain.PCSCase; +import uk.gov.hmcts.reform.pcs.ccd.domain.State; +import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; + +@Component +public class CaseType implements CCDConfig { + + @Override + public void configure(final ConfigBuilder builder) { + builder.setCallbackHost("http://localhost:3206"); + + builder.caseType("PCS", "Civil Possessions", "Possessions"); + builder.jurisdiction("CIVIL", "Civil Possessions", "The new one"); + + var label = "Applicant Forename"; + builder.searchInputFields() + .field(PCSCase::getApplicantForename, label); + builder.searchCasesFields() + .field(PCSCase::getApplicantForename, label); + + builder.searchResultFields() + .field(PCSCase::getApplicantForename, label); + builder.workBasketInputFields() + .field(PCSCase::getApplicantForename, label); + builder.workBasketResultFields() + .field(PCSCase::getApplicantForename, label); + + builder.tab("Example", "Example Tab") + .field(PCSCase::getApplicantForename); + } +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java new file mode 100644 index 0000000000..4931187ced --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java @@ -0,0 +1,19 @@ +package uk.gov.hmcts.reform.pcs.ccd.domain; + +import com.google.common.collect.HashMultimap; +import com.google.common.collect.SetMultimap; +import uk.gov.hmcts.ccd.sdk.api.HasAccessControl; +import uk.gov.hmcts.ccd.sdk.api.HasRole; +import uk.gov.hmcts.ccd.sdk.api.Permission; + +import static uk.gov.hmcts.reform.pcs.ccd.domain.UserRole.CASE_WORKER; + + +public class DefaultStateAccess implements HasAccessControl { + @Override + public SetMultimap getGrants() { + SetMultimap grants = HashMultimap.create(); + grants.putAll(CASE_WORKER, Permission.CRU); + return grants; + } +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java new file mode 100644 index 0000000000..bbb52d9fa1 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java @@ -0,0 +1,10 @@ +package uk.gov.hmcts.reform.pcs.ccd.domain; + +import lombok.Data; +import uk.gov.hmcts.ccd.sdk.api.CCD; + +@Data +public class PCSCase { + @CCD(label = "A field") + private String applicantForename; +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java new file mode 100644 index 0000000000..e5fa868e72 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java @@ -0,0 +1,17 @@ +package uk.gov.hmcts.reform.pcs.ccd.domain; + +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import uk.gov.hmcts.ccd.sdk.api.CCD; + +@RequiredArgsConstructor +@Getter +public enum State { + + @CCD( + label = "Open", + access = {DefaultStateAccess.class} + ) + Open; +} + diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java new file mode 100644 index 0000000000..447a709639 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java @@ -0,0 +1,17 @@ +package uk.gov.hmcts.reform.pcs.ccd.domain; + +import com.fasterxml.jackson.annotation.JsonValue; +import lombok.AllArgsConstructor; +import lombok.Getter; +import uk.gov.hmcts.ccd.sdk.api.HasRole; + +@AllArgsConstructor +@Getter +public enum UserRole implements HasRole { + + CASE_WORKER("caseworker-civil", "CRU"); + + @JsonValue + private final String role; + private final String caseTypePermissions; +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java new file mode 100644 index 0000000000..f9ee59e32f --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java @@ -0,0 +1,50 @@ +package uk.gov.hmcts.reform.pcs.ccd.event; + +import lombok.SneakyThrows; +import org.springframework.stereotype.Component; +import uk.gov.hmcts.ccd.sdk.api.CCDConfig; +import uk.gov.hmcts.ccd.sdk.api.CaseDetails; +import uk.gov.hmcts.ccd.sdk.api.ConfigBuilder; +import uk.gov.hmcts.ccd.sdk.api.Permission; +import uk.gov.hmcts.ccd.sdk.api.callback.AboutToStartOrSubmitResponse; +import uk.gov.hmcts.reform.pcs.ccd.domain.PCSCase; +import uk.gov.hmcts.reform.pcs.ccd.domain.State; +import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; + +@Component +public class CreateTestCase implements CCDConfig { + @Override + public void configure(ConfigBuilder configBuilder) { + + configBuilder + .event("createTestApplication") + .initialState(State.Open) + .name("Create test case") + .aboutToStartCallback(this::start) + .aboutToSubmitCallback(this::aboutToSubmit) + .grant(Permission.CRUD, UserRole.CASE_WORKER) + .fields() + .page("Create test case") + .mandatory(PCSCase::getApplicantForename) + .done(); + } + + private AboutToStartOrSubmitResponse start(CaseDetails caseDetails) { + var data = caseDetails.getData(); + data.setApplicantForename("Preset value"); + + return AboutToStartOrSubmitResponse.builder() + .data(caseDetails.getData()) + .build(); + } + + @SneakyThrows + public AboutToStartOrSubmitResponse aboutToSubmit(CaseDetails details, + CaseDetails beforeDetails) { + + + return AboutToStartOrSubmitResponse.builder() + .data(details.getData()) + .build(); + } +} diff --git a/src/main/resources/application.yaml b/src/main/resources/application.yaml index 5652d9f719..9b343099b4 100644 --- a/src/main/resources/application.yaml +++ b/src/main/resources/application.yaml @@ -60,7 +60,7 @@ idam: totp_secret: ${PCS_API_S2S_SECRET:AAAAAAAAAAAAAAAA} microservice: ${S2S_SERVICE_NAME:pcs_api} s2s-authorised: - services: ${S2S_NAMES_WHITELIST:pcs_api,pcs_frontend} + services: ${S2S_NAMES_WHITELIST:pcs_api,pcs_frontend,ccd_data} azure: application-insights: From 0e22b44ab2f73dfd6b4de3012a598fa10dad7545 Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 19 Feb 2025 12:27:28 +0000 Subject: [PATCH 03/10] Example integration of the cftlib + config generator --- .github/workflows/cftlibTest.yaml | 25 ++++++++++ build.gradle | 3 ++ .../uk/gov/hmcts/reform/pcs/TestWithCCD.java | 19 ++++++++ .../uk/gov/hmcts/reform/pcs/ccd/CaseType.java | 3 +- .../hmcts/reform/pcs/ccd/domain/PCSCase.java | 7 ++- .../hmcts/reform/pcs/ccd/domain/Party.java | 12 +++++ .../reform/pcs/ccd/event/CreateTestCase.java | 6 ++- .../reform/pcs/ccd/event/EditParties.java | 46 +++++++++++++++++++ 8 files changed, 117 insertions(+), 4 deletions(-) create mode 100644 .github/workflows/cftlibTest.yaml create mode 100644 src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java diff --git a/.github/workflows/cftlibTest.yaml b/.github/workflows/cftlibTest.yaml new file mode 100644 index 0000000000..dd17028831 --- /dev/null +++ b/.github/workflows/cftlibTest.yaml @@ -0,0 +1,25 @@ +name: Cftlib Tests + +on: + pull_request: + branches: + - master + push: + branches: + - master + +jobs: + gradle: + runs-on: ubuntu-latest + strategy: + fail-fast: false + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-java@v4 + with: + distribution: corretto + java-version: 21 + cache: 'gradle' + - name: Run task + run: ./gradlew -is cftlibTest + diff --git a/build.gradle b/build.gradle index 30dc9c8359..340f4888c2 100644 --- a/build.gradle +++ b/build.gradle @@ -65,6 +65,9 @@ configurations { smokeTestImplementation.extendsFrom testImplementation smokeTestRuntimeOnly.extendsFrom runtimeOnly + + cftlibTestImplementation.extendsFrom testImplementation + cftlibTestRuntime.extendsFrom testRuntime } tasks.withType(JavaCompile) { diff --git a/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java b/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java new file mode 100644 index 0000000000..2404a7b44b --- /dev/null +++ b/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java @@ -0,0 +1,19 @@ +package uk.gov.hmcts.reform.pcs; + + +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.TestInstance; +import org.springframework.boot.test.context.SpringBootTest; +import uk.gov.hmcts.rse.ccd.lib.test.CftlibTest; + +@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT) +@TestInstance(TestInstance.Lifecycle.PER_CLASS) +public class TestWithCCD extends CftlibTest { + + @Test + public void bootsWithCCD() { + // Env fully booted with definitions imported + // Even this empty test is useful, checking that your definitions are valid and import successfully. + // You can add more tests here to use CCD's APIs, XUI with playwright, etc. + } +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java index 4cd26fa254..953f183906 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java @@ -31,6 +31,7 @@ public void configure(final ConfigBuilder builder) { .field(PCSCase::getApplicantForename, label); builder.tab("Example", "Example Tab") - .field(PCSCase::getApplicantForename); + .field(PCSCase::getApplicantForename) + .field(PCSCase::getParties); } } diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java index bbb52d9fa1..89821b1456 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java @@ -2,9 +2,14 @@ import lombok.Data; import uk.gov.hmcts.ccd.sdk.api.CCD; +import uk.gov.hmcts.ccd.sdk.type.ListValue; + +import java.util.List; @Data public class PCSCase { - @CCD(label = "A field") + @CCD(label = "Applicant's first name") private String applicantForename; + + private List> parties; } diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java new file mode 100644 index 0000000000..a19054f9e3 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java @@ -0,0 +1,12 @@ +package uk.gov.hmcts.reform.pcs.ccd.domain; + +import lombok.Data; +import uk.gov.hmcts.ccd.sdk.api.CCD; + +@Data +public class Party { + @CCD(label = "Party's forename") + private String forename; + @CCD(label = "Party's surname") + private String surname; +} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java index f9ee59e32f..ad17b15908 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java @@ -13,9 +13,11 @@ @Component public class CreateTestCase implements CCDConfig { + + + @Override public void configure(ConfigBuilder configBuilder) { - configBuilder .event("createTestApplication") .initialState(State.Open) @@ -30,7 +32,7 @@ public void configure(ConfigBuilder configBuilder) { } private AboutToStartOrSubmitResponse start(CaseDetails caseDetails) { - var data = caseDetails.getData(); + PCSCase data = caseDetails.getData(); data.setApplicantForename("Preset value"); return AboutToStartOrSubmitResponse.builder() diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java new file mode 100644 index 0000000000..065725c8d5 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java @@ -0,0 +1,46 @@ +package uk.gov.hmcts.reform.pcs.ccd.event; + +import lombok.SneakyThrows; +import org.springframework.security.access.method.P; +import org.springframework.stereotype.Component; +import uk.gov.hmcts.ccd.sdk.api.CCDConfig; +import uk.gov.hmcts.ccd.sdk.api.CaseDetails; +import uk.gov.hmcts.ccd.sdk.api.ConfigBuilder; +import uk.gov.hmcts.ccd.sdk.api.Permission; +import uk.gov.hmcts.ccd.sdk.api.callback.AboutToStartOrSubmitResponse; +import uk.gov.hmcts.reform.pcs.ccd.domain.PCSCase; +import uk.gov.hmcts.reform.pcs.ccd.domain.State; +import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; + +import java.util.List; + +@Component +public class EditParties implements CCDConfig { + @Override + public void configure(ConfigBuilder configBuilder) { + + configBuilder + .event("editParties") + .forAllStates() + .name("Edit parties") + .grant(Permission.CRUD, UserRole.CASE_WORKER) + .fields() + .page("Edit parties", this::validateParties) + .mandatory(PCSCase::getParties) + .done(); + } + + // Example mid event callback handler + private AboutToStartOrSubmitResponse validateParties(CaseDetails details, CaseDetails detailsBefore) { + PCSCase result = details.getData(); + var errors = List.of(); + // Example validation + if (result.getParties().stream().anyMatch(x -> x.getValue().getForename().contains("Bob"))) { + errors = List.of("Bob is not allowed!"); + } + return AboutToStartOrSubmitResponse.builder() + .data(result) + .errors(errors) + .build(); + } +} From 1f13daab2e87d4daedc2660e670be8cce23b6ffb Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 19 Feb 2025 15:29:09 +0000 Subject: [PATCH 04/10] tidy --- src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java | 4 ---- .../java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java | 5 ++--- 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java index 0053e67741..edf30f7284 100644 --- a/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java +++ b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java @@ -1,18 +1,14 @@ package uk.gov.hmcts.reform.pcs; -import org.apache.commons.io.FileUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Component; import uk.gov.hmcts.ccd.sdk.CCDDefinitionGenerator; import uk.gov.hmcts.reform.pcs.ccd.domain.State; -import uk.gov.hmcts.rse.ccd.lib.ControlPlane; -import uk.gov.hmcts.rse.ccd.lib.Database; import uk.gov.hmcts.rse.ccd.lib.api.CFTLib; import uk.gov.hmcts.rse.ccd.lib.api.CFTLibConfigurer; import java.io.File; -import java.io.IOException; import java.util.List; import java.util.Map; diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java index 065725c8d5..a196aa4c84 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java @@ -1,7 +1,5 @@ package uk.gov.hmcts.reform.pcs.ccd.event; -import lombok.SneakyThrows; -import org.springframework.security.access.method.P; import org.springframework.stereotype.Component; import uk.gov.hmcts.ccd.sdk.api.CCDConfig; import uk.gov.hmcts.ccd.sdk.api.CaseDetails; @@ -31,7 +29,8 @@ public void configure(ConfigBuilder configBuilder) { } // Example mid event callback handler - private AboutToStartOrSubmitResponse validateParties(CaseDetails details, CaseDetails detailsBefore) { + private AboutToStartOrSubmitResponse validateParties(CaseDetails details, + CaseDetails detailsBefore) { PCSCase result = details.getData(); var errors = List.of(); // Example validation From cb2909e6174f5f5020e4e4f58cee06f6b938f61a Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 19 Feb 2025 15:45:46 +0000 Subject: [PATCH 05/10] comments --- .github/workflows/cftlibTest.yaml | 1 + build.gradle | 7 +++++-- src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java | 5 +++++ src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java | 3 +++ .../hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java | 3 +++ .../java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java | 3 +++ .../java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java | 4 ++++ .../java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java | 3 +++ .../uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java | 8 +++----- .../uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java | 1 - 10 files changed, 30 insertions(+), 8 deletions(-) diff --git a/.github/workflows/cftlibTest.yaml b/.github/workflows/cftlibTest.yaml index dd17028831..8f79adf9b6 100644 --- a/.github/workflows/cftlibTest.yaml +++ b/.github/workflows/cftlibTest.yaml @@ -1,3 +1,4 @@ +# This should be a required branch protection check for master. name: Cftlib Tests on: diff --git a/build.gradle b/build.gradle index 243dddb07f..be60ab414a 100644 --- a/build.gradle +++ b/build.gradle @@ -1,4 +1,5 @@ import uk.gov.hmcts.rse.AuthMode +import uk.gov.hmcts.rse.CftlibExec plugins { id 'application' @@ -255,6 +256,8 @@ dependencies { exclude group: 'junit', module: 'junit' exclude group: 'org.junit.vintage', module: 'junit-vintage-engine' } + // Allow fast reloading during dev; recompile a class to trigger fast reload + definition reimport. + cftlibImplementation 'org.springframework.boot:spring-boot-devtools' } mainClassName = 'uk.gov.hmcts.reform.pcs.Application' @@ -272,12 +275,12 @@ project.tasks.named("processSmokeTestResources") { duplicatesStrategy = 'include' } -bootWithCCD { +tasks.withType(CftlibExec).configureEach { group = 'ccd tasks' authMode = AuthMode.Local + environment 'SPRING_PROFILES_ACTIVE', 'dev' } wrapper { distributionType = Wrapper.DistributionType.ALL } - diff --git a/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java index edf30f7284..e893a10c69 100644 --- a/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java +++ b/src/cftlib/java/uk/gov/hmcts/reform/pcs/CftlibConfig.java @@ -12,6 +12,10 @@ import java.util.List; import java.util.Map; +/** + * Configures the CFTLib with the required users, roles and CCD definitions. + * The Cftlib will find and execute this configuration class once all services are ready. + */ @Component public class CftlibConfig implements CFTLibConfigurer { @Autowired @@ -23,6 +27,7 @@ public void configure(CFTLib lib) throws Exception { var users = Map.of( "caseworker@pcs.com", List.of("caseworker", "caseworker-civil")); + // Create users and roles including in idam simulator for (var entry : users.entrySet()) { lib.createIdamUser(entry.getKey(), entry.getValue().toArray(new String[0])); lib.createProfile(entry.getKey(), "CIVIL", "PCS", State.Open.name()); diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java index 953f183906..7bc0b3b397 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java @@ -7,6 +7,9 @@ import uk.gov.hmcts.reform.pcs.ccd.domain.State; import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; +/** + * Setup some common possessions case type configuration. + */ @Component public class CaseType implements CCDConfig { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java index 4931187ced..15a7e2acb6 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/DefaultStateAccess.java @@ -9,6 +9,9 @@ import static uk.gov.hmcts.reform.pcs.ccd.domain.UserRole.CASE_WORKER; +/** + * Placeholder access control configuration granting caseworker CRU. + */ public class DefaultStateAccess implements HasAccessControl { @Override public SetMultimap getGrants() { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java index 89821b1456..c9e6596832 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java @@ -6,6 +6,9 @@ import java.util.List; +/** + * The main domain model representing a possessions case. + */ @Data public class PCSCase { @CCD(label = "Applicant's first name") diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java index e5fa868e72..8127010ea3 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/State.java @@ -4,6 +4,10 @@ import lombok.RequiredArgsConstructor; import uk.gov.hmcts.ccd.sdk.api.CCD; +/** + * All possible PCS case states. + * Converted into CCD states. + */ @RequiredArgsConstructor @Getter public enum State { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java index 447a709639..6f0bd998cf 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java @@ -5,6 +5,9 @@ import lombok.Getter; import uk.gov.hmcts.ccd.sdk.api.HasRole; +/** + * All the different roles for a PCS case. + */ @AllArgsConstructor @Getter public enum UserRole implements HasRole { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java index ad17b15908..6a40fb52af 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java @@ -1,6 +1,7 @@ package uk.gov.hmcts.reform.pcs.ccd.event; import lombok.SneakyThrows; +import org.springframework.context.annotation.Profile; import org.springframework.stereotype.Component; import uk.gov.hmcts.ccd.sdk.api.CCDConfig; import uk.gov.hmcts.ccd.sdk.api.CaseDetails; @@ -11,11 +12,9 @@ import uk.gov.hmcts.reform.pcs.ccd.domain.State; import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; +@Profile("dev") // Non-prod event @Component public class CreateTestCase implements CCDConfig { - - - @Override public void configure(ConfigBuilder configBuilder) { configBuilder @@ -43,8 +42,7 @@ private AboutToStartOrSubmitResponse start(CaseDetails aboutToSubmit(CaseDetails details, CaseDetails beforeDetails) { - - + // TODO: Whatever you need. return AboutToStartOrSubmitResponse.builder() .data(details.getData()) .build(); diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java index a196aa4c84..34dfb863eb 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java @@ -16,7 +16,6 @@ public class EditParties implements CCDConfig { @Override public void configure(ConfigBuilder configBuilder) { - configBuilder .event("editParties") .forAllStates() From a4fa744c45b04815c25c8a1bcb4f1b7f72279af2 Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 19 Feb 2025 16:19:41 +0000 Subject: [PATCH 06/10] cover cftlib with ci tests --- .github/workflows/cftlibTest.yaml | 26 -------------------------- build.gradle | 3 +++ 2 files changed, 3 insertions(+), 26 deletions(-) delete mode 100644 .github/workflows/cftlibTest.yaml diff --git a/.github/workflows/cftlibTest.yaml b/.github/workflows/cftlibTest.yaml deleted file mode 100644 index 8f79adf9b6..0000000000 --- a/.github/workflows/cftlibTest.yaml +++ /dev/null @@ -1,26 +0,0 @@ -# This should be a required branch protection check for master. -name: Cftlib Tests - -on: - pull_request: - branches: - - master - push: - branches: - - master - -jobs: - gradle: - runs-on: ubuntu-latest - strategy: - fail-fast: false - steps: - - uses: actions/checkout@v4 - - uses: actions/setup-java@v4 - with: - distribution: corretto - java-version: 21 - cache: 'gradle' - - name: Run task - run: ./gradlew -is cftlibTest - diff --git a/build.gradle b/build.gradle index be60ab414a..dd73502f66 100644 --- a/build.gradle +++ b/build.gradle @@ -281,6 +281,9 @@ tasks.withType(CftlibExec).configureEach { environment 'SPRING_PROFILES_ACTIVE', 'dev' } +// Ensure we cover Cftlib dev & test with our CI checks +check.dependsOn cftlibTest + wrapper { distributionType = Wrapper.DistributionType.ALL } From b1a1ba2d67220297f0ce5793b3f87fdc9f7ae8fd Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 26 Feb 2025 14:12:28 +0000 Subject: [PATCH 07/10] Take coverage info from cftlibTests + add create test case test --- build.gradle | 7 ++- .../uk/gov/hmcts/reform/pcs/TestWithCCD.java | 45 +++++++++++++++++-- .../uk/gov/hmcts/reform/pcs/Application.java | 4 +- .../uk/gov/hmcts/reform/pcs/ccd/CaseType.java | 2 +- .../hmcts/reform/pcs/ccd/domain/PCSCase.java | 8 ++-- .../hmcts/reform/pcs/ccd/domain/Party.java | 2 + .../reform/pcs/ccd/event/CreateTestCase.java | 2 - .../reform/pcs/ccd/event/EditParties.java | 44 ------------------ .../pcs/config/JacksonConfiguration.java | 41 +++++++++++++++++ src/main/resources/application.yaml | 6 +++ 10 files changed, 103 insertions(+), 58 deletions(-) delete mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java create mode 100644 src/main/java/uk/gov/hmcts/reform/pcs/config/JacksonConfiguration.java diff --git a/build.gradle b/build.gradle index 0cf739245a..17840b1625 100644 --- a/build.gradle +++ b/build.gradle @@ -10,7 +10,7 @@ plugins { id 'org.sonarqube' version '6.0.1.5171' id 'net.serenity-bdd.serenity-gradle-plugin' version '4.2.16' id 'hmcts.ccd.sdk' version '5.5.16' - id 'com.github.hmcts.rse-cft-lib' version '0.19.1573' + id 'com.github.hmcts.rse-cft-lib' version '0.19.1597' id 'io.freefair.lombok' version '8.12.1' /* Applies analysis tools including checkstyle and OWASP Dependency checker. @@ -166,7 +166,7 @@ task runE2eFirefoxTests(type: Exec) { } jacocoTestReport { - executionData(test, integration) + executionData(test, integration, cftlibTest) reports { xml.required = true csv.required = false @@ -229,9 +229,12 @@ dependencies { implementation group: 'org.springframework.boot', name: 'spring-boot-starter-jdbc' implementation group: 'org.springframework.boot', name: 'spring-boot-starter-web' implementation group: 'org.springframework.boot', name: 'spring-boot-starter-security' + implementation group: 'org.springdoc', name: 'springdoc-openapi-starter-webmvc-ui', version: '2.8.5' implementation group: 'com.github.hmcts.java-logging', name: 'logging', version: '6.1.8' + implementation group: 'com.github.hmcts', name: 'ccd-client', version: '5.0.3' + implementation group: 'com.github.hmcts', name: 'idam-java-client', version: '3.0.3' implementation group: 'org.apache.logging.log4j', name: 'log4j-api', version: log4JVersion implementation group: 'org.apache.logging.log4j', name: 'log4j-to-slf4j', version: log4JVersion diff --git a/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java b/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java index 2404a7b44b..71ea2e00ca 100644 --- a/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java +++ b/src/cftlibTest/java/uk/gov/hmcts/reform/pcs/TestWithCCD.java @@ -1,19 +1,56 @@ package uk.gov.hmcts.reform.pcs; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.Order; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.TestInstance; +import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; +import uk.gov.hmcts.reform.ccd.client.CoreCaseDataApi; +import uk.gov.hmcts.reform.ccd.client.model.CaseDataContent; +import uk.gov.hmcts.reform.ccd.client.model.CaseDetails; +import uk.gov.hmcts.reform.ccd.client.model.Event; +import uk.gov.hmcts.reform.idam.client.IdamClient; +import uk.gov.hmcts.reform.pcs.ccd.domain.PCSCase; import uk.gov.hmcts.rse.ccd.lib.test.CftlibTest; +import static org.assertj.core.api.Assertions.assertThat; + + @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT) @TestInstance(TestInstance.Lifecycle.PER_CLASS) public class TestWithCCD extends CftlibTest { + @Autowired + private CoreCaseDataApi ccdApi; + + @Autowired + private IdamClient idamClient; + + CaseDetails caseDetails; + String idamToken; + String s2sToken; + String userId; + + @BeforeAll + public void setup() { + idamToken = idamClient.getAccessToken("caseworker@pcs.com", "password"); + s2sToken = generateDummyS2SToken("ccd_gw"); + userId = idamClient.getUserInfo(idamToken).getUid(); + } + + @Order(1) @Test - public void bootsWithCCD() { - // Env fully booted with definitions imported - // Even this empty test is useful, checking that your definitions are valid and import successfully. - // You can add more tests here to use CCD's APIs, XUI with playwright, etc. + public void createsTestCase() { + var r = ccdApi.startCase(idamToken, s2sToken, "PCS", "createTestApplication"); + var content = CaseDataContent.builder() + .data(PCSCase.builder().applicantForename("Foo").build()) + .event(Event.builder().id("createTestApplication").build()) + .eventToken(r.getToken()) + .build(); + caseDetails = ccdApi.submitForCaseworker(idamToken, s2sToken, userId, + "CIVIL", "PCS", false, content); + assertThat(caseDetails.getId()).isNotNull(); } } diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/Application.java b/src/main/java/uk/gov/hmcts/reform/pcs/Application.java index 5f025bcad7..713049303d 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/Application.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/Application.java @@ -3,6 +3,7 @@ import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.openfeign.EnableFeignClients; +import uk.gov.hmcts.reform.idam.client.IdamApi; import uk.gov.hmcts.reform.pcs.hearings.service.api.HmcHearingApi; @SpringBootApplication( @@ -14,7 +15,8 @@ @SuppressWarnings("HideUtilityClassConstructor") // Spring needs a constructor, its not a utility class @EnableFeignClients( clients = { - HmcHearingApi.class + HmcHearingApi.class, + IdamApi.class } ) public class Application { diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java index 7bc0b3b397..51e163101b 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/CaseType.java @@ -35,6 +35,6 @@ public void configure(final ConfigBuilder builder) { builder.tab("Example", "Example Tab") .field(PCSCase::getApplicantForename) - .field(PCSCase::getParties); + .field(PCSCase::getPartyA); } } diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java index c9e6596832..e4dfdabf1c 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/PCSCase.java @@ -1,18 +1,18 @@ package uk.gov.hmcts.reform.pcs.ccd.domain; +import lombok.Builder; import lombok.Data; import uk.gov.hmcts.ccd.sdk.api.CCD; -import uk.gov.hmcts.ccd.sdk.type.ListValue; - -import java.util.List; /** * The main domain model representing a possessions case. */ +@Builder @Data public class PCSCase { @CCD(label = "Applicant's first name") private String applicantForename; - private List> parties; + @CCD(label = "Party A") + private Party partyA; } diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java index a19054f9e3..75ba1ed016 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/Party.java @@ -1,8 +1,10 @@ package uk.gov.hmcts.reform.pcs.ccd.domain; +import lombok.Builder; import lombok.Data; import uk.gov.hmcts.ccd.sdk.api.CCD; +@Builder @Data public class Party { @CCD(label = "Party's forename") diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java index 6a40fb52af..e2ef2bfc61 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/CreateTestCase.java @@ -1,6 +1,5 @@ package uk.gov.hmcts.reform.pcs.ccd.event; -import lombok.SneakyThrows; import org.springframework.context.annotation.Profile; import org.springframework.stereotype.Component; import uk.gov.hmcts.ccd.sdk.api.CCDConfig; @@ -39,7 +38,6 @@ private AboutToStartOrSubmitResponse start(CaseDetails aboutToSubmit(CaseDetails details, CaseDetails beforeDetails) { // TODO: Whatever you need. diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java deleted file mode 100644 index 34dfb863eb..0000000000 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/event/EditParties.java +++ /dev/null @@ -1,44 +0,0 @@ -package uk.gov.hmcts.reform.pcs.ccd.event; - -import org.springframework.stereotype.Component; -import uk.gov.hmcts.ccd.sdk.api.CCDConfig; -import uk.gov.hmcts.ccd.sdk.api.CaseDetails; -import uk.gov.hmcts.ccd.sdk.api.ConfigBuilder; -import uk.gov.hmcts.ccd.sdk.api.Permission; -import uk.gov.hmcts.ccd.sdk.api.callback.AboutToStartOrSubmitResponse; -import uk.gov.hmcts.reform.pcs.ccd.domain.PCSCase; -import uk.gov.hmcts.reform.pcs.ccd.domain.State; -import uk.gov.hmcts.reform.pcs.ccd.domain.UserRole; - -import java.util.List; - -@Component -public class EditParties implements CCDConfig { - @Override - public void configure(ConfigBuilder configBuilder) { - configBuilder - .event("editParties") - .forAllStates() - .name("Edit parties") - .grant(Permission.CRUD, UserRole.CASE_WORKER) - .fields() - .page("Edit parties", this::validateParties) - .mandatory(PCSCase::getParties) - .done(); - } - - // Example mid event callback handler - private AboutToStartOrSubmitResponse validateParties(CaseDetails details, - CaseDetails detailsBefore) { - PCSCase result = details.getData(); - var errors = List.of(); - // Example validation - if (result.getParties().stream().anyMatch(x -> x.getValue().getForename().contains("Bob"))) { - errors = List.of("Bob is not allowed!"); - } - return AboutToStartOrSubmitResponse.builder() - .data(result) - .errors(errors) - .build(); - } -} diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/config/JacksonConfiguration.java b/src/main/java/uk/gov/hmcts/reform/pcs/config/JacksonConfiguration.java new file mode 100644 index 0000000000..d2f15b7b75 --- /dev/null +++ b/src/main/java/uk/gov/hmcts/reform/pcs/config/JacksonConfiguration.java @@ -0,0 +1,41 @@ +package uk.gov.hmcts.reform.pcs.config; + +import com.fasterxml.jackson.annotation.JsonInclude; +import com.fasterxml.jackson.databind.DeserializationFeature; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.json.JsonMapper; +import com.fasterxml.jackson.datatype.jdk8.Jdk8Module; +import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; +import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer; +import com.fasterxml.jackson.module.paramnames.ParameterNamesModule; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.context.annotation.Primary; + +import static com.fasterxml.jackson.databind.MapperFeature.ACCEPT_CASE_INSENSITIVE_ENUMS; +import static com.fasterxml.jackson.databind.MapperFeature.INFER_BUILDER_TYPE_BINDINGS; + +@Configuration +public class JacksonConfiguration { + + @Primary + @Bean + public ObjectMapper getMapper() { + ObjectMapper mapper = JsonMapper.builder() + .configure(ACCEPT_CASE_INSENSITIVE_ENUMS, true) + .enable(INFER_BUILDER_TYPE_BINDINGS) + .serializationInclusion(JsonInclude.Include.NON_NULL) + .build(); + + JavaTimeModule datetime = new JavaTimeModule(); + datetime.addSerializer(LocalDateSerializer.INSTANCE); + mapper.registerModule(datetime); + + mapper.configure(DeserializationFeature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT, true) + .configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false); + + mapper.registerModules(new Jdk8Module(), new JavaTimeModule(), new ParameterNamesModule()); + + return mapper; + } +} diff --git a/src/main/resources/application.yaml b/src/main/resources/application.yaml index ddc02d860f..dad33a7e5e 100644 --- a/src/main/resources/application.yaml +++ b/src/main/resources/application.yaml @@ -57,6 +57,8 @@ spring: # silence the 'wall-of-text' - unnecessary exception throw about blob types non_contextual_creation: true idam: + api: + url: ${IDAM_API_URL:http://localhost:5062} s2s-auth: url: ${IDAM_S2S_AUTH_URL:http://localhost:4502} totp_secret: ${PCS_API_S2S_SECRET:AAAAAAAAAAAAAAAA} @@ -71,3 +73,7 @@ hmc: deployment-id: ${HMC_DEPLOYMENT_ID:} api-url: ${HMC_API_URL:http://localhost:8084} serviceId: ${HMC_SERVICE_ID:AAA3} + +core_case_data: + api: + url: ${CCD_API_URL:http://localhost:4452} From 5aa734607d0e25e7a8dd6499687bdcfa8b01517f Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 26 Feb 2025 16:48:48 +0000 Subject: [PATCH 08/10] fix preview --- build.gradle | 2 +- src/main/resources/application.yaml | 4 ---- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/build.gradle b/build.gradle index fedd2019c9..b35f416bf8 100644 --- a/build.gradle +++ b/build.gradle @@ -10,7 +10,7 @@ plugins { id 'org.sonarqube' version '6.0.1.5171' id 'net.serenity-bdd.serenity-gradle-plugin' version '4.2.16' id 'hmcts.ccd.sdk' version '5.5.16' - id 'com.github.hmcts.rse-cft-lib' version '0.19.1597' + id 'com.github.hmcts.rse-cft-lib' version '0.19.1600' id 'io.freefair.lombok' version '8.12.1' id 'au.com.dius.pact' version '4.6.17' /* diff --git a/src/main/resources/application.yaml b/src/main/resources/application.yaml index dad33a7e5e..f4d129dde6 100644 --- a/src/main/resources/application.yaml +++ b/src/main/resources/application.yaml @@ -73,7 +73,3 @@ hmc: deployment-id: ${HMC_DEPLOYMENT_ID:} api-url: ${HMC_API_URL:http://localhost:8084} serviceId: ${HMC_SERVICE_ID:AAA3} - -core_case_data: - api: - url: ${CCD_API_URL:http://localhost:4452} From 3f2f291032c90fd2bd9b3610266dead3f99b5c8a Mon Sep 17 00:00:00 2001 From: isha2040 <58481974+isha2040@users.noreply.github.com> Date: Wed, 12 Mar 2025 16:30:21 +0000 Subject: [PATCH 09/10] Updating read me --- README.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/README.md b/README.md index 0b1bc35a92..e8e02c4ed9 100644 --- a/README.md +++ b/README.md @@ -134,6 +134,16 @@ There are also several custom test scripts available: - `test:chrome` - runs the full E2E suite in Chrome - `test:firefox` - runs the full E2E suite in Firefox +### Running pcs-api with local CCD + +```bash +./gradlew bootWithCCD +``` +Above command starts PCS API + CCD & all dependencies + +Once successfully loaded open XUI at http://localhost:3000 +See CftlibConfig.java for users and login details. + ## License This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details From 2fb18ed14e843acff8bee434508a151266dc6921 Mon Sep 17 00:00:00 2001 From: Alex McAusland Date: Wed, 12 Mar 2025 18:10:20 +0000 Subject: [PATCH 10/10] use Set for userrole permissions --- .../uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java index 6f0bd998cf..4e7efffa16 100644 --- a/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java +++ b/src/main/java/uk/gov/hmcts/reform/pcs/ccd/domain/UserRole.java @@ -4,6 +4,9 @@ import lombok.AllArgsConstructor; import lombok.Getter; import uk.gov.hmcts.ccd.sdk.api.HasRole; +import uk.gov.hmcts.ccd.sdk.api.Permission; + +import java.util.Set; /** * All the different roles for a PCS case. @@ -12,9 +15,13 @@ @Getter public enum UserRole implements HasRole { - CASE_WORKER("caseworker-civil", "CRU"); + CASE_WORKER("caseworker-civil", Permission.CRU); @JsonValue private final String role; - private final String caseTypePermissions; + private final Set caseTypePermissions; + + public String getCaseTypePermissions() { + return Permission.toString(caseTypePermissions); + } }