From: Kai Moritz Date: Sun, 14 Mar 2021 13:38:33 +0000 (+0100) Subject: WIP X-Git-Url: https://juplo.de/gitweb/?p=demos%2Fpact;a=commitdiff_plain;h=7df01dd4a110b02cf438b8e24d0e8f7b9c025d00 WIP --- diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/in/WebController.java b/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/in/WebController.java index 2d6b089..00f2510 100644 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/in/WebController.java +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/in/WebController.java @@ -1,7 +1,7 @@ package de.juplo.demos.pwreset.adapters.in; -import de.juplo.demos.pwreset.domain.ports.in.ResetRequestProgress; -import de.juplo.demos.pwreset.domain.ports.in.PasswordResetService; +import de.juplo.demos.pwreset.domain.ports.in.PasswordResetRequestProgressDTO; +import de.juplo.demos.pwreset.domain.ports.in.PasswordResetPort; import lombok.RequiredArgsConstructor; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.*; @@ -16,7 +16,7 @@ import java.util.UUID; @RequiredArgsConstructor public class WebController { - private final PasswordResetService passwordResetService; + private final PasswordResetPort passwordResetPort; @GetMapping("/") @@ -32,14 +32,14 @@ public class WebController throws IOException { - ResetRequestProgress progress = passwordResetService.request(email); + PasswordResetRequestProgressDTO progress = passwordResetPort.createRequest(email); httpServletResponse.sendRedirect(progress.getRequestId().toString()); } @GetMapping("/{id}") public ModelAndView getResetRequest(@PathVariable UUID id) { - ResetRequestProgress progress = passwordResetService.get(id); + PasswordResetRequestProgressDTO progress = passwordResetPort.getRequest(id); return createModelAndView(progress); } @@ -49,8 +49,8 @@ public class WebController @RequestParam String code, @RequestParam String password) { - ResetRequestProgress progress = - passwordResetService.confirm( + PasswordResetRequestProgressDTO progress = + passwordResetPort.confirmRequest( id, code, password); @@ -63,7 +63,7 @@ public class WebController return mav; } - ModelAndView createModelAndView(ResetRequestProgress progress) + ModelAndView createModelAndView(PasswordResetRequestProgressDTO progress) { ModelAndView mav = new ModelAndView(); mav.addObject("progress", progress); diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumer.java b/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumer.java deleted file mode 100644 index 7a2ac77..0000000 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumer.java +++ /dev/null @@ -1,48 +0,0 @@ -package de.juplo.demos.pwreset.adapters.out; - -import de.juplo.demos.pwreset.domain.ports.out.UsersService; -import lombok.RequiredArgsConstructor; -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.web.client.RestTemplate; - -import java.util.Optional; -import java.util.UUID; - - -@RequiredArgsConstructor -public class RemoteUsersServiceConsumer implements UsersService -{ - private final String uriTemplate; - private final RestTemplate restTemplate; - - - @Override - public Optional getUserByEmail(String email) - { - ResponseEntity response = - restTemplate.getForEntity(uriTemplate, UserDTO.class, email); - - HttpStatus status = response.getStatusCode(); - UserDTO dto = response.getBody(); - - switch (response.getStatusCode()) - { - case OK: - return - Optional.of(dto.id); - - case NOT_FOUND: - return Optional.empty(); - - default: - throw new RuntimeException(status.toString()); - } - } - - @Override - public void setPassword(UUID userId, String password) - { - - } -} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGateway.java b/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGateway.java new file mode 100644 index 0000000..53b9d60 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGateway.java @@ -0,0 +1,48 @@ +package de.juplo.demos.pwreset.adapters.out; + +import de.juplo.demos.pwreset.domain.ports.out.UsersPort; +import lombok.RequiredArgsConstructor; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.client.RestTemplate; + +import java.util.Optional; +import java.util.UUID; + + +@RequiredArgsConstructor +public class UsersServiceGateway implements UsersPort +{ + private final String uriTemplate; + private final RestTemplate restTemplate; + + + @Override + public Optional getUserByEmail(String email) + { + ResponseEntity response = + restTemplate.getForEntity(uriTemplate, UserDTO.class, email); + + HttpStatus status = response.getStatusCode(); + UserDTO dto = response.getBody(); + + switch (response.getStatusCode()) + { + case OK: + return + Optional.of(dto.id); + + case NOT_FOUND: + return Optional.empty(); + + default: + throw new RuntimeException(status.toString()); + } + } + + @Override + public void setPassword(UUID userId, String password) + { + + } +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetProgress.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetProgress.java new file mode 100644 index 0000000..757f692 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetProgress.java @@ -0,0 +1,18 @@ +package de.juplo.demos.pwreset.domain.internal; + +import lombok.Value; + + +@Value +public class PasswordResetProgress +{ + public enum Status + { + CONFIRMATION_DENIED, + CONFIMED, + ACCOMPLISHED + } + + private final Status status; + private final String message; +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetService.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetService.java new file mode 100644 index 0000000..5d4b346 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/internal/PasswordResetService.java @@ -0,0 +1,33 @@ +package de.juplo.demos.pwreset.domain.internal; + +import java.util.Optional; +import java.util.UUID; + + +public class PasswordResetService +{ + public PasswordResetRequest createRequest(String email) + { + return null; + } + + public Optional findRequest(String email) + { + return null; + } + + public PasswordResetRequest getRequest(UUID requestId) + { + return null; + } + + public PasswordResetProgress confirmRequest(PasswordResetRequest request, String code, String password) + { + return null; + } + + public Optional getProgress(UUID requestId) + { + return null; + } +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetPort.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetPort.java new file mode 100644 index 0000000..7f8a3f0 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetPort.java @@ -0,0 +1,35 @@ +package de.juplo.demos.pwreset.domain.ports.in; + +import de.juplo.demos.pwreset.domain.internal.PasswordResetRequest; +import de.juplo.demos.pwreset.domain.internal.PasswordResetService; +import lombok.RequiredArgsConstructor; + +import java.util.Optional; +import java.util.UUID; + + +@RequiredArgsConstructor +public class PasswordResetPort +{ + private final PasswordResetService resetService; + + + public PasswordResetRequestProgressDTO createRequest(String email) + { + Optional result = + resetService.findRequest(email); + PasswordResetRequest request = + result.orElseGet(() -> resetService.createRequest(email)); + return PasswordResetRequestProgressDTO.from(request); + } + + public PasswordResetRequestProgressDTO getRequest(UUID requestId) + { + return PasswordResetRequestProgressDTO.from(resetService.getRequest(requestId)); + } + + public PasswordResetRequestProgressDTO confirmRequest(UUID requestId, String code, String password) + { + return PasswordResetRequestProgressDTO.from(resetService.confirmRequest(requestId, code, password)); + } +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetRequestProgressDTO.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetRequestProgressDTO.java new file mode 100644 index 0000000..beb91fd --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetRequestProgressDTO.java @@ -0,0 +1,44 @@ +package de.juplo.demos.pwreset.domain.ports.in; + +import de.juplo.demos.pwreset.domain.internal.PasswordResetProgress; +import de.juplo.demos.pwreset.domain.internal.PasswordResetRequest; +import de.juplo.demos.pwreset.domain.internal.PasswordResetRequestProgress; +import lombok.RequiredArgsConstructor; +import lombok.Value; + +import java.time.ZonedDateTime; +import java.util.Optional; +import java.util.UUID; + +import static de.juplo.demos.pwreset.domain.internal.PasswordResetProgress.Status.*; + + +@RequiredArgsConstructor +@Value +public class PasswordResetRequestProgressDTO +{ + private final UUID requestId; + private final boolean accepted; + private final String message; + private final Optional created; + private final Optional confirmed; + private final Optional accomplished; + + public static PasswordResetRequestProgressDTO from( + PasswordResetRequest request, + PasswordResetProgress progress) + { + return + new PasswordResetRequestProgressDTO( + request.getId(), + progress.getStatus() != CONFIRMATION_DENIED, + progress.getMessage(), + Optional.of(request.getCreated()), + progress.getStatus() == CONFIRMATION_DENIED + ? Optional.empty() + : Optional.of(request.getConfirmed()), + progress.getStatus() == ACCOMPLISHED + ? Optional.empty() + : Optional.of(request.getAccomplihed())); + } +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetService.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetService.java deleted file mode 100644 index 833edd8..0000000 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/PasswordResetService.java +++ /dev/null @@ -1,11 +0,0 @@ -package de.juplo.demos.pwreset.domain.ports.in; - -import java.util.UUID; - - -public interface PasswordResetService -{ - ResetRequestProgress request(String email); - ResetRequestProgress get(UUID requestId); - ResetRequestProgress confirm(UUID requestId, String code, String password); -} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/ResetRequestProgress.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/ResetRequestProgress.java deleted file mode 100644 index 5e70f5e..0000000 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/in/ResetRequestProgress.java +++ /dev/null @@ -1,23 +0,0 @@ -package de.juplo.demos.pwreset.domain.ports.in; - -import lombok.Builder; -import lombok.Getter; -import lombok.ToString; - -import java.time.ZonedDateTime; -import java.util.Optional; -import java.util.UUID; - - -@Builder -@Getter -@ToString -public class ResetRequestProgress -{ - private final UUID requestId; - private final boolean accepted; - private final String message; - private final Optional created; - private final Optional confirmed; - private final Optional accomplished; -} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingPort.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingPort.java new file mode 100644 index 0000000..f904775 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingPort.java @@ -0,0 +1,9 @@ +package de.juplo.demos.pwreset.domain.ports.out; + +import java.util.UUID; + + +public interface MessagingPort +{ + void sendRestCode(UUID userId, String code); +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingService.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingService.java deleted file mode 100644 index b05411f..0000000 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/MessagingService.java +++ /dev/null @@ -1,9 +0,0 @@ -package de.juplo.demos.pwreset.domain.ports.out; - -import java.util.UUID; - - -public interface MessagingService -{ - void sendRestCode(UUID userId, String code); -} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersPort.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersPort.java new file mode 100644 index 0000000..bca7d82 --- /dev/null +++ b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersPort.java @@ -0,0 +1,11 @@ +package de.juplo.demos.pwreset.domain.ports.out; + +import java.util.Optional; +import java.util.UUID; + + +public interface UsersPort +{ + Optional getUserByEmail(String email); + void setPassword(UUID userId, String password); +} diff --git a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersService.java b/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersService.java deleted file mode 100644 index b314c86..0000000 --- a/pwreset/src/main/java/de/juplo/demos/pwreset/domain/ports/out/UsersService.java +++ /dev/null @@ -1,11 +0,0 @@ -package de.juplo.demos.pwreset.domain.ports.out; - -import java.util.Optional; -import java.util.UUID; - - -public interface UsersService -{ - Optional getUserByEmail(String email); - void setPassword(UUID userId, String password); -} diff --git a/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumerIT.java b/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumerIT.java deleted file mode 100644 index 2f58b21..0000000 --- a/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/RemoteUsersServiceConsumerIT.java +++ /dev/null @@ -1,67 +0,0 @@ -package de.juplo.demos.pwreset.adapters.out; - -import au.com.dius.pact.consumer.MockServer; -import au.com.dius.pact.consumer.dsl.PactDslWithProvider; -import au.com.dius.pact.consumer.junit5.PactConsumerTestExt; -import au.com.dius.pact.consumer.junit5.PactTestFor; -import au.com.dius.pact.core.model.RequestResponsePact; -import au.com.dius.pact.core.model.annotations.Pact; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.api.extension.ExtendWith; -import org.springframework.boot.web.client.RestTemplateBuilder; -import org.springframework.web.client.RestTemplate; - -import java.util.Map; -import java.util.Optional; -import java.util.UUID; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.fail; - - -@ExtendWith(PactConsumerTestExt.class) -@PactTestFor(providerName = "UsersProvider") -public class RemoteUsersServiceConsumerIT -{ - @Pact(consumer="EmailServicesConsumer") - public RequestResponsePact getExistingUserByEmail(PactDslWithProvider builder) - { - return builder - .given("User with email pact@juplo.de exists") - .uponReceiving("Request for user with email pact@juplo.de") - .path("/get") - .query("email=pact@juplo.de") - .method("GET") - .willRespondWith() - .status(200) - .headers(Map.of("Content-Type", "application/json;charset=UTF-8")) - .body("{\"id\": \"123e4567-e89b-12d3-a456-426614174000\"}") - .toPact(); - } - - @Test - @PactTestFor(pactMethod = "getExistingUserByEmail") - public void testGetExistingUserByEmail(MockServer mockServer) - { - RestTemplate restTemplate = - new RestTemplateBuilder() - .rootUri(mockServer.getUrl()) - .build(); - RemoteUsersServiceConsumer usersService = - new RemoteUsersServiceConsumer( - "/get?email={email}", - restTemplate); - try - { - Optional result = - usersService.getUserByEmail("pact@juplo.de"); - - assertThat(result.isPresent()).isTrue(); - assertThat(result.get()).isEqualTo(UUID.fromString("123e4567-e89b-12d3-a456-426614174000")); - } - catch (Exception e) - { - fail("Unexpected exception", e); - } - } -} diff --git a/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGatewayContractTest.java b/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGatewayContractTest.java new file mode 100644 index 0000000..4ab4c85 --- /dev/null +++ b/pwreset/src/test/java/de/juplo/demos/pwreset/adapters/out/UsersServiceGatewayContractTest.java @@ -0,0 +1,67 @@ +package de.juplo.demos.pwreset.adapters.out; + +import au.com.dius.pact.consumer.MockServer; +import au.com.dius.pact.consumer.dsl.PactDslWithProvider; +import au.com.dius.pact.consumer.junit5.PactConsumerTestExt; +import au.com.dius.pact.consumer.junit5.PactTestFor; +import au.com.dius.pact.core.model.RequestResponsePact; +import au.com.dius.pact.core.model.annotations.Pact; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; +import org.springframework.boot.web.client.RestTemplateBuilder; +import org.springframework.web.client.RestTemplate; + +import java.util.Map; +import java.util.Optional; +import java.util.UUID; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.fail; + + +@ExtendWith(PactConsumerTestExt.class) +@PactTestFor(providerName = "UsersProvider") +public class UsersServiceGatewayContractTest +{ + @Pact(consumer="EmailServicesConsumer") + public RequestResponsePact getExistingUserByEmail(PactDslWithProvider builder) + { + return builder + .given("User with email pact@juplo.de exists") + .uponReceiving("Request for user with email pact@juplo.de") + .path("/get") + .query("email=pact@juplo.de") + .method("GET") + .willRespondWith() + .status(200) + .headers(Map.of("Content-Type", "application/json;charset=UTF-8")) + .body("{\"id\": \"123e4567-e89b-12d3-a456-426614174000\"}") + .toPact(); + } + + @Test + @PactTestFor(pactMethod = "getExistingUserByEmail") + public void testGetExistingUserByEmail(MockServer mockServer) + { + RestTemplate restTemplate = + new RestTemplateBuilder() + .rootUri(mockServer.getUrl()) + .build(); + UsersServiceGateway usersService = + new UsersServiceGateway( + "/get?email={email}", + restTemplate); + try + { + Optional result = + usersService.getUserByEmail("pact@juplo.de"); + + assertThat(result.isPresent()).isTrue(); + assertThat(result.get()).isEqualTo(UUID.fromString("123e4567-e89b-12d3-a456-426614174000")); + } + catch (Exception e) + { + fail("Unexpected exception", e); + } + } +}