Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • fit-connect/sdk-java
1 result
Show changes
Commits on Source (23)
Showing
with 371 additions and 98 deletions
......@@ -26,19 +26,19 @@ reuse:
DOCKER_REGISTRY_READ: $DOCKER_PULL_REGISTRY
build:
image: maven:latest
image: eclipse-temurin:11.0.18_10-jdk
stage: build
script:
- ./mvnw $MAVEN_CLI_OPTS clean install -DskipTests --no-transfer-progress -T2
test:
image: maven:latest
image: eclipse-temurin:11.0.18_10-jdk
stage: test
script:
- ./mvnw $MAVEN_CLI_OPTS test --no-transfer-progress -T2
- ./mvnw $MAVEN_CLI_OPTS verify --no-transfer-progress -T2
package:
image: maven:latest
image: eclipse-temurin:11.0.18_10-jdk
stage: package
before_script: &gpg-setup
- apt-get update
......@@ -50,14 +50,15 @@ package:
- ./mvnw $MAVEN_CLI_OPTS package -DskipTests
artifacts:
paths:
- client/target/*.jar
- core/target/*.jar
- api/target/*.jar
- core/target/*.jar
- client/target/*.jar
- integration-tests/target/*.jar
expire_in: 1 day
when: manual
deploy:
image: maven:latest
image: eclipse-temurin:11.0.18_10-jdk
stage: deploy
before_script: *gpg-setup
script:
......
Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/
Files: api/src/* client/src/* core/src/*
Files: api/src/* client/src/* core/src/* integration-tests/src/*
api/README.md client/README.md core/README.md
README.md CHANGELOG.md SECURITY.md
Copyright: 2022 FIT-Connect contributors
......@@ -10,7 +10,7 @@ Files: .mvn/wrapper/* mvnw mvnw.cmd
Copyright: 2013-2022 The Apache Software Foundation
License: Apache-2.0
Files: pom.xml api/pom.xml core/pom.xml client/pom.xml open-api/pom.xml
Files: pom.xml api/pom.xml core/pom.xml client/pom.xml integration-tests/pom.xml
.gitlab-ci.yml .gitignore .m2/release.xml
renovate.json checkstyle.xml checkstyle-suppressions.xml config.yml
Copyright: 2022 FIT-Connect contributors
......
......@@ -106,11 +106,18 @@ _The following steps show how to get the SDK running_
- add reference to private signature key (JWK) to *SUBSCRIBER* section
6. Provide config via environment variable ``FIT_CONNECT_CONFIG`` or load the config with
6. Load a configuration via:
````java
final var config = ApplicationConfigLoader.loadConfig("absolute/path/to/config.yml");
final var senderClient = ClientFactory.senderClient(config);
final ApplicationConfig config = ApplicationConfigLoader.loadConfigFromPath(Path.of("path/to/config.yml"));
````
7. Afterwards the config is used to initialize clients with the `ClientFactory` that offer clients for sender, subscriber and routing:
````java
final SenderClient senderClient = ClientFactory.getSenderClient(config);
//
final SubscriberClient subscriberClient = ClientFactory.getSubscriberClient(config);
//
final RoutingClient routingClient = ClientFactory.getRoutingClient(config);
````
<p align="right">(<a href="#top">back to top</a>)</p>
......@@ -126,7 +133,7 @@ A typical workflow using the `RoutingClient` and `SenderClient` would be:
Areas can be searched with one or more search criteria:
```java
final RoutingClient routingClient = ClientFactory.routingClient(config);
final RoutingClient routingClient = ClientFactory.getRoutingClient(config);
final var citySearchCriterion = "Leip*";
final var zipCodeSearchCriterion = "04229";
......@@ -156,7 +163,7 @@ __Note:__ Both, the `leikaKey` service-identifier and the region keys `ars/ags`c
#### Find destination by service identifier and *areaId*
```java
final RoutingClient routingClient = ClientFactory.routingClient(config);
final RoutingClient routingClient = ClientFactory.getRoutingClient(config);
final DestinationSearch search = DestinationSearch.Builder()
.withLeikaKey("99123456760610")
......@@ -178,7 +185,7 @@ for (final Route route : routes){
Besides the areaId another search criterion for the area/region can be used as well:
```java
final RoutingClient routingClient = ClientFactory.routingClient(config);
final RoutingClient routingClient = ClientFactory.getRoutingClient(config);
final DestinationSearch search = DestinationSearch.Builder()
.withLeikaKey("99123456760610")
......@@ -212,12 +219,12 @@ If all data, metadata and attachments are encrypted outside the SDK the sender c
```java
final var destinationId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final Optional<String> publicJwk = ClientFactory.senderClient(config).getPublicKey(destinationId);
final String publicJwkAsJsonString = ClientFactory.getSenderClient(config).getPublicKey(destinationId);
```
#### 2. Send encrypted data
To send an encrypted submission the builder `EncryptedSubmissionBuilder` is needed to construct an `EncryptedSubmissionPayload` object.
To send an encrypted submission the builder `EncryptedSubmissionBuilder` is needed to construct an `SendableEncryptedSubmission` object.
The payload can be submitted as shown below via the `ClientFactory`.
If optional attachments are added, the UUID needs to be provided for each attachment to be able to announce them before the submission is actually sent.
......@@ -225,17 +232,17 @@ This is necessary because the SDK does not have access to the already encrypted
```java
// The constructed client can be reused to send multiple submissions
final SenderClient senderClient = ClientFactory.senderClient(config);
final EncryptedSubmissionPayload frontendEncryptedPayload = EncryptedSubmissionBuilder.Builder()
.withEncryptedAttachment(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"), "$encrpyt€ed @tt@chment") // optional
.withEncryptedData("{$encrpyt€ed json}")
.withEncryptedMetadata("$encrpyt€ed metadata")
.withDestination(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"))
.withServiceType("Führerscheinummeldung", "urn:de:fim:leika:leistung:99400048079000")
final SenderClient senderClient = ClientFactory.getSenderClient(config);
final SendableEncryptedSubmission encryptedSubmission = SendableEncryptedSubmission.Builder()
.setDestination(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"))
.setServiceType("urn:de:fim:leika:leistung:99400048079000", "Führerscheinummeldung")
.setEncryptedMetadata("$encrpyt€ed metadata")
.setEncryptedData("{$encrpyt€ed json}")
.addEncryptedAttachment(new EncryptedAttachment(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"), "$encrpyt€ed @tt@chment")) // optional
.build();
final SentSubmission sentSubmission = senderClient.submit(frontendEncryptedPayload);
final SentSubmission sentSubmission = senderClient.send(encryptedSubmission);
```
| **Important** |
......@@ -249,21 +256,23 @@ If all data, metadata and attachments are encrypted in the sender using the SDK,
Be aware that this example is not end-2-end encrypted, see [FIT-Connect documentation](https://docs.fitko.de/fit-connect/docs/getting-started/encryption) for details.
To send a submission the builder `SubmissionBuilder` is needed to construct a `SubmissionPayload` object.
To send a submission the builder `SubmissionBuilder` is needed to construct a `SendableSubmission` object.
The payload can be submitted as shown below via the `ClientFactory`.
```java
// The constructed client can be reused to send multiple submissions
final SenderClient senderClient = ClientFactory.senderClient(config);
final SubmissionPayload submissionPayload = SubmissionBuilder.Builder()
.withAttachment(Path.of("path/to/attachment.txt").toFile()) // optional
.withJsonData("{ \"foo\" : \"bar\"}")
.withDestination(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"))
.withServiceType("Führerscheinummeldung", "urn:de:fim:leika:leistung:99400048079000")
final SenderClient senderClient = ClientFactory.getSenderClient(config);
final SendableSubmission sendableSubmission = SendableSubmission.Builder()
.setDestination(UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14"))
.setServiceType("urn:de:fim:leika:leistung:99400048079000", "Führerscheinummeldung")
.setJsonData("{ \"foo\" : \"bar\"}")
// optional properties
.addAttachment(Attachment.fromPath(Path.of("path/to/attachment.txt"), "text/plain"))
.setReplyChannel(ReplyChannel.fromEmail("test@mail.org"))
.build();
final SentSubmission sentSubmission = senderClient.submit(submissionPayload);
final SentSubmission sentSubmission = senderClient.send(sendableSubmission);
```
......@@ -273,7 +282,7 @@ To read the event-log, destinationId and caseId are needed.
final var caseId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final var destinationId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final List<EventLogEntry> eventLog = ClientFactory.senderClient(config).getEventLog(caseId, destinationId);
final List<EventLogEntry> eventLog = ClientFactory.getSenderClient(config).getEventLog(caseId, destinationId);
for(EventLogEntry logEntry: eventLog) {
LOGGER.info("Event: {}", logEntry.getEvent());
......@@ -303,9 +312,9 @@ Instead of the entire log, the latest status for a submission can be retrieved a
```java
final SentSubmission sentSubmission = ... // persisted sent submission by sender client
final EventStatus eventStatus = ClientFactory.senderClient(config).getStatusForSubmission(sentSubmission);
final EventStatus submissionStatus = ClientFactory.getSenderClient(config).getStatusForSubmission(sentSubmission);
LOGGER.info("Current status for submission {} => {}", sentSubmission.getSubmissionId(), eventStatus.getStatus());
LOGGER.info("Current status for submission {} => {}", sentSubmission.getSubmissionId(), submissionStatus.getStatus());
```
The example output shows the current state of the submission after being created, following the transitions in the diagram below:
......@@ -326,7 +335,7 @@ More details on how this method works can be found here:
The Java SDK provides a convenient method for validating callbacks, its usage could look like this:
```java
final SenderClient senderClient = ClientFactory.senderClient(config);
final SenderClient senderClient = ClientFactory.getSenderClient(config);
final ValidationResult validationResult = senderClient.validateCallback("hmac", 0L, "body", "secret");
......@@ -342,45 +351,62 @@ Submissions can be fetched by id or as a list of submissions for a specific case
#### List with pagination
Limit and offset parameters allow to page through the result.
```java
final var subscriberClient = ClientFactory.getSubscriberClient(config);
final int offset = 0;
final int limit = 100;
final var destinationId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final Set<SubmissionForPickup> firstOneHundredSubmissions = ClientFactory.subscriberClient(config).getAvailableSubmissions(destinationId), limit, offset);
final Set<SubmissionForPickup> firstOneHundredSubmissions = subscriberClient.getAvailableSubmissionsforDestination(destinationId), limit, offset);
```
#### List without pagination
Listing available submissions without pagination pulls the first 500 entries.
```java
final var subscriberClient = ClientFactory.getSubscriberClient(config);
final var destinationId= UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final Set<SubmissionForPickup> submissions = ClientFactory.subscriberClient(config).getAvailableSubmissions(destinationId);
final Set<SubmissionForPickup> submissions = subscriberClient.getAvailableSubmissionsForDestination(destinationId);
```
#### Receive single submission
#### Receive single submission
```java
final submissionId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final ReceivedSubmission receivedSubmission = ClientFactory.subscriberClient(config).requestSubmission(submissionId);
// by id
final var submissionId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final ReceivedSubmission receivedSubmission = ClientFactory.getSubscriberClient(config).requestSubmission(submissionId);
```
```java
// by object
final SubmissionForPickup submissionForPickup = // code for sending submission;
final ReceivedSubmission receivedSubmission = ClientFactory.getSubscriberClient(config).requestSubmission(submissionForPickup);
```
Now, the received submission allows access to the decrypted data, attachments, metadata and ids
```java
// access data
final String data = receivedData.getData();
final URI dataSchemaUri = receivedData.getDataSchemaUri();
final MimeType mimeType = receivedData.getDataMimeType();
final String data = receivedSubmission.getDataAsString();
final URI dataSchemaUri = receivedSubmission.getDataSchemaUri();
final String mimeType = receivedSubmission.getDataMimeType();
// access metadata
final Metadata = receivedData.getSubmissionMetdata();
final Metadata metadata = receivedSubmission.getSubmissionMetdata();
// access reply channel
final ReplyChannel replyChannel = metadata.getReplyChannel();
// access attachments
for(final ReceivedAttachment attachment : receivedSubmission.getAttachments()){
final byte[] attachmentRawData = attachment.getData();
for(final Attachment attachment : receivedSubmission.getAttachments()){
final String originalFilename = attachment.getFilename();
final UUID attachmentId = attachment.getAttachmentId();
final String attachmentMimeType = attachment.getMimeType();
// different formats to retrieve the attachment content
final byte[] attachmentDataAsBytes = attachment.getDataAsBytes();
final String attachmentDataAsString = attachment.getDataAString(StandardCharsets.UTF_8);
}
// access further ids of submission
final UUID caseId = receivedData.getCaseId();
final UUID submissionId = receivedData.getSubmissionId();
final UUID destinationId = receivedData.getDestinationId();
final UUID caseId = receivedSubmission.getCaseId();
final UUID submissionId = receivedSubmission.getSubmissionId();
final UUID destinationId = receivedSubmission.getDestinationId();
```
### Sending events to the event-log
......@@ -389,13 +415,20 @@ In order to accept or reject a submission, the subscriber client can send events
For more details please see the documentation on [events](https://docs.fitko.de/fit-connect/docs/getting-started/event-log/overview) and the creation of [set-events](https://docs.fitko.de/fit-connect/docs/getting-started/event-log/set-creation).
#### Accepting a submission
If the functional review by the subscriber was positive, the submission can be accepted with an `accept-submission` event.
If the functional review by the subscriber was positive, the submission can be accepted with an `accept-submission` event.
For this event a list of optional problems can be sent, the submission is still accepted but with remarks.
```java
final var submissionId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
ClientFactory.subscriberClient(config)
.requestSubmission(submissionId)
ClientFactory.getSubscriberClient(config)
.requestSubmission(submissionId);
.acceptSubmission();
// OR accept with an optional list of problems
ClientFactory.getSubscriberClient(config)
.requestSubmission(submissionId);
.acceptSubmission(List.of(new MyCustomProblem()));
```
After the accept event was sent the submission transitions into the state `deleted` and is removed.
#### Rejecting a submission
......@@ -405,11 +438,9 @@ See the Fit-Connect documentation for more details on [available (technical) pro
```java
final var submissionId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final var rejectionProblems = List.of(new DataSchemaViolation());
ClientFactory.subscriberClient(config)
.requestSubmission(submissionId)
.rejectSubmission(rejectionProblems);
ClientFactory.getSubscriberClient(config)
.requestSubmission(submissionId);
.rejectSubmission(List.of(new DataSchemaViolation()));
```
After the rejection event was sent the submission transitions into the state `deleted` and is removed.
......@@ -419,7 +450,7 @@ To read the event-log, destinationId and caseId are needed.
final var caseId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final var destinationId = UUID.fromString("d2d43892-9d9c-4630-980a-5af341179b14");
final List<EventLogEntry> eventLog = ClientFactory.subscriberClient(config).getEventLog(caseId, destinationId);
final List<EventLogEntry> eventLog = ClientFactory.getSubscriberClient(config).getEventLog(caseId, destinationId);
for(EventLogEntry logEntry: eventLog) {
LOGGER.info("Event: {}", logEntry.getEvent());
......@@ -450,7 +481,7 @@ For more details please see the [event-log documentation](https://docs.fitko.de/
The validation of callbacks works similar to the sender side (see [Sender Callback Validation](#validating-callbacks)), but instead of the `SenderClient`, we use the `SubscriberClient`:
```java
final SubscriberClient subscriberClient = ClientFactory.subscriberClient(config);
final SubscriberClient subscriberClient = ClientFactory.getSubscriberClient(config);
final ValidationResult validationResult = subscriberClient.validateCallback("hmac", 0L, "body", "secret");
......@@ -461,8 +492,8 @@ if(validationResult.hasError()){
## Integration Tests
Integration tests in `dev.fitko.fitconnect.client.ClientIntegrationTest` run only on the CI-Server and are ignored by default locally.
To run them on a local machine the following environment variables have to be set in the run-configuration of the IDE:
Integration tests do not run per default with `mvn test`, but they can be executed with the maven profile `IntegrationTests` via `mvn -PIntegrationTests test`.
They expect the following environment variables to be set in the rn configuration of the IDE or on the local terminal:
* SENDER_CLIENT_ID
* SENDER_CLIENT_SECRET
......@@ -483,7 +514,7 @@ var submissionBaseUrl = "https://submission-api-testing.fit-connect.fitko.dev";
## Roadmap
- [ ] Add auto-reject on technical errors
- [ ] Maven central release of 1.0.0
- [ ] Maven central release of 1.0.0-beta
See the [open issues](https://git.fitko.de/fit-connect/planning/-/boards/44?search=SDK) for a full list of proposed features (and known issues).
......@@ -506,6 +537,6 @@ Hierfür kann das SDK in die anzubindenden Software integriert werden.
Erfolgt die Integration des SDK in unveränderter Form, liegt keine Bearbeitung im Sinne der EUPL bzw. des deutschen Urheberrechts vor.
Die Art und Weise der Verlinkung des SDK führt insbesondere nicht zur Schaffung eines abgeleiteten Werkes.
Die unveränderte Übernahme des SDK in eine anzubindende Software führt damit nicht dazu, dass die anzubindende Software unter den Bedingungen der EUPL zu lizenzieren ist.
Für die Weitergabe des SDK selbst - in unveränderter oder bearbeiteter Form, als Quellcode oder ausführbares Programm - gelten die Lizenzbedingungen der EUPL in unverände*rter Weise.
Für die Weitergabe des SDK selbst - in unveränderter oder bearbeiteter Form, als Quellcode oder ausführbares Programm - gelten die Lizenzbedingungen der EUPL in unveränderter Weise.*
<p align="right">(<a href="#top">back to top</a>)</p>
......@@ -5,6 +5,8 @@ import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@Builder
@AllArgsConstructor
......@@ -12,6 +14,6 @@ import lombok.NoArgsConstructor;
public class SubscriberConfig {
private String clientId;
private String clientSecret;
private String privateDecryptionKeyPath;
private List<String> privateDecryptionKeyPaths;
private String privateSigningKeyPath;
}
......@@ -2,6 +2,7 @@ package dev.fitko.fitconnect.api.domain.model.destination;
import com.fasterxml.jackson.annotation.JsonProperty;
import dev.fitko.fitconnect.api.domain.model.replychannel.ReplyChannel;
import dev.fitko.fitconnect.api.domain.model.submission.Callback;
import lombok.Data;
import lombok.NoArgsConstructor;
......
package dev.fitko.fitconnect.api.domain.model.destination;
import com.fasterxml.jackson.annotation.JsonProperty;
import dev.fitko.fitconnect.api.domain.model.replychannel.ReplyChannel;
import lombok.Data;
import lombok.NoArgsConstructor;
......
......@@ -100,12 +100,12 @@ public enum Event {
@Override
public SubmissionState getState() {
return SubmissionState.SUBMITTED;
return SubmissionState.NOTIFIED;
}
@Override
public Set<Event> allowedNextEvents() {
return Set.of(SUBMIT);
return Set.of(ACCEPT, REJECT, FORWARD);
}
},
......
......@@ -2,43 +2,72 @@ package dev.fitko.fitconnect.api.domain.model.event;
import dev.fitko.fitconnect.api.domain.model.event.problems.Problem;
import dev.fitko.fitconnect.api.domain.model.submission.Submission;
import dev.fitko.fitconnect.api.domain.model.submission.SubmissionForPickup;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.UUID;
@Data
@Builder
@AllArgsConstructor
public class EventPayload {
private UUID submissionId;
private UUID destinationId;
private UUID caseId;
// used for auth-tag validation
private String encryptedMetadata;
private String encryptedData;
private Map<UUID, String> encryptedAttachments;
private List<Problem> problems;
public EventPayload(final Submission submission, final Map<UUID, String> encryptedAttachments, final List<Problem> problems) {
submissionId = submission.getSubmissionId();
destinationId = submission.getDestinationId();
caseId = submission.getCaseId();
encryptedData = submission.getEncryptedData();
encryptedMetadata = submission.getEncryptedMetadata();
this.encryptedAttachments = encryptedAttachments;
this.problems = problems;
public static EventPayload forRejectEvent(final SubmissionForPickup submission, final List<Problem> problems){
return EventPayload.builder()
.submissionId(submission.getSubmissionId())
.destinationId(submission.getDestinationId())
.caseId(submission.getCaseId())
.problems(problems)
.build();
}
public EventPayload(final Submission submission, final Map<UUID, String> encryptedAttachments) {
this(submission, encryptedAttachments, Collections.emptyList());
public static EventPayload forRejectEvent(final Submission submission, final List<Problem> problems){
return EventPayload.builder()
.submissionId(submission.getSubmissionId())
.destinationId(submission.getDestinationId())
.caseId(submission.getCaseId())
.problems(problems)
.build();
}
public EventPayload(final Submission submission, final List<Problem> problems) {
this(submission, Collections.emptyMap(), problems);
public static EventPayload forAcceptEvent(final Submission submission, final Problem... problems){
return EventPayload.builder()
.submissionId(submission.getSubmissionId())
.destinationId(submission.getDestinationId())
.caseId(submission.getCaseId())
.encryptedData(submission.getEncryptedData())
.encryptedMetadata(submission.getEncryptedMetadata())
.encryptedAttachments(Collections.emptyMap())
.problems(Arrays.asList(problems))
.build();
}
public EventPayload(final Submission submission) {
this(submission, Collections.emptyMap(), Collections.emptyList());
public static EventPayload forAcceptEventWithAttachments(final Submission submission, final Map<UUID, String> encryptedAttachments, final Problem... problems){
return EventPayload.builder()
.submissionId(submission.getSubmissionId())
.destinationId(submission.getDestinationId())
.caseId(submission.getCaseId())
.encryptedData(submission.getEncryptedData())
.encryptedMetadata(submission.getEncryptedMetadata())
.encryptedAttachments(encryptedAttachments)
.problems(Arrays.asList(problems))
.build();
}
}
......@@ -7,7 +7,8 @@ public enum SubmissionState {
ACCEPTED("accepted"),
REJECTED("rejected"),
DELETED("deleted"),
FORWARDED("forwarded");
FORWARDED("forwarded"),
NOTIFIED("notified");
private final String name;
......
......@@ -10,7 +10,7 @@ import java.util.List;
@Getter
@AllArgsConstructor
@NoArgsConstructor
public class EventStatus {
public class SubmissionStatus {
SubmissionState status;
List<Problem> problems;
}
......@@ -2,9 +2,13 @@ package dev.fitko.fitconnect.api.domain.model.metadata;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
@AllArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class AdditionalReferenceInfo {
......@@ -13,6 +17,29 @@ public class AdditionalReferenceInfo {
@JsonProperty("applicationDate")
private String applicationDate;
public static Builder builder() {
return new Builder();
}
public static class Builder {
private String senderReference;
private String applicationDate;
public Builder withSenderReference(final String senderReference) {
this.senderReference = senderReference;
return this;
}
public Builder withApplicationDate(final String applicationDate) {
this.applicationDate = applicationDate;
return this;
}
public AdditionalReferenceInfo build() {
return new AdditionalReferenceInfo(senderReference, applicationDate);
}
}
}
package dev.fitko.fitconnect.api.domain.model.metadata;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
@AllArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class AuthenticationInformation {
@JsonProperty("type")
......@@ -16,4 +18,32 @@ public class AuthenticationInformation {
@JsonProperty("content")
private String content;
public static Builder builder() {
return new Builder();
}
public static class Builder {
private String type;
private String version;
private String content;
public Builder withType(final String type) {
this.type = type;
return this;
}
public Builder withVersion(final String version) {
this.version = version;
return this;
}
public Builder withContent(final String content) {
this.content = content;
return this;
}
public AuthenticationInformation build() {
return new AuthenticationInformation(type, version, content);
}
}
}
......@@ -2,7 +2,7 @@ package dev.fitko.fitconnect.api.domain.model.metadata;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import dev.fitko.fitconnect.api.domain.model.metadata.attachment.Attachment;
import dev.fitko.fitconnect.api.domain.model.metadata.attachment.ApiAttachment;
import dev.fitko.fitconnect.api.domain.model.metadata.data.Data;
import lombok.NoArgsConstructor;
......@@ -17,5 +17,5 @@ public class ContentStructure {
private Data data;
@JsonProperty("attachments")
private List<Attachment> attachments;
private List<ApiAttachment> attachments;
}
......@@ -2,28 +2,41 @@ package dev.fitko.fitconnect.api.domain.model.metadata;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
import dev.fitko.fitconnect.api.domain.model.metadata.payment.PaymentInformation;
import dev.fitko.fitconnect.api.domain.model.replychannel.ReplyChannel;
import lombok.AllArgsConstructor;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import java.util.List;
@Data
@Setter
@EqualsAndHashCode
@AllArgsConstructor
@NoArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class Metadata {
@Getter
@JsonProperty("$schema")
private String schema;
@JsonProperty("contentStructure")
@Getter
private ContentStructure contentStructure;
@JsonProperty("publicServiceType")
private PublicServiceType publicServiceType;
@JsonProperty("authenticationInformation")
@Getter
private List<AuthenticationInformation> authenticationInformation;
@JsonProperty("additionalReferenceInfo")
@Getter
private PaymentInformation paymentInformation;
@Getter
private ReplyChannel replyChannel;
@Getter
private AdditionalReferenceInfo additionalReferenceInfo;
}
......@@ -12,7 +12,7 @@ import java.util.UUID;
@Data
@NoArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class Attachment {
public class ApiAttachment {
@JsonProperty("hash")
private Hash hash;
......
package dev.fitko.fitconnect.api.domain.model.metadata.payment;
import com.fasterxml.jackson.annotation.JsonInclude;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.NonNull;
import java.net.URI;
import java.util.Date;
@Data
@NoArgsConstructor
@AllArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class PaymentInformation {
private URI transactionUrl;
private String transactionId;
private String transactionReference;
private Date transactionTimestamp;
private PaymentMethod paymentMethod;
private String paymentMethodDetail;
private PaymentStatus status;
private double grossAmount;
public static Builder builder() {
return new Builder();
}
public static class Builder {
private URI transactionUrl;
private @NonNull String transactionId;
private @NonNull String transactionReference;
private @NonNull Date transactionTimestamp;
private @NonNull PaymentMethod paymentMethod;
private String paymentMethodDetail;
private @NonNull PaymentStatus status;
private double grossAmount;
public Builder withTransactionUrl(final URI transactionUrl) {
this.transactionUrl = transactionUrl;
return this;
}
public Builder withTransactionId(final String transactionId) {
this.transactionId = transactionId;
return this;
}
public Builder withTransactionReference(final String transactionReference) {
this.transactionReference = transactionReference;
return this;
}
public Builder withTransactionTimestamp(final Date transactionTimestamp) {
this.transactionTimestamp = transactionTimestamp;
return this;
}
public Builder withPaymentMethod(final PaymentMethod paymentMethod) {
this.paymentMethod = paymentMethod;
return this;
}
public Builder withPaymentMethodDetail(final String paymentMethodDetail) {
this.paymentMethodDetail = paymentMethodDetail;
return this;
}
public Builder withStatus(final PaymentStatus status) {
this.status = status;
return this;
}
public Builder withGrossAmount(final double grossAmount) {
this.grossAmount = grossAmount;
return this;
}
public PaymentInformation build() {
return new PaymentInformation(transactionUrl, transactionId, transactionReference, transactionTimestamp, paymentMethod, paymentMethodDetail, status, grossAmount);
}
}
}
package dev.fitko.fitconnect.api.domain.model.metadata.payment;
public enum PaymentMethod {
GIROPAY, PAYDIRECT, CREDITCARD, PAYPAL, INVOICE, OTHER
}
package dev.fitko.fitconnect.api.domain.model.metadata.payment;
public enum PaymentStatus {
INITIAL, BOOKED, FAILED, CANCELED
}
package dev.fitko.fitconnect.api.domain.model.destination;
package dev.fitko.fitconnect.api.domain.model.replychannel;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
public class ReplyChannel {
@AllArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class DeMail {
@JsonProperty("deMail")
private Object deMail;
@JsonProperty("elster")
private Object elster;
@JsonProperty("eMail")
private ReplyChannelEMail eMail;
@JsonProperty("fink")
private Object fink;
@JsonProperty("address")
private String address;
}
package dev.fitko.fitconnect.api.domain.model.replychannel;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
@AllArgsConstructor
@JsonInclude(JsonInclude.Include.NON_NULL)
public class Elster {
@JsonProperty("accountId")
private String accountId;
@JsonProperty("lieferTicket")
private String deliveryTicket;
@JsonProperty("geschaeftszeichen")
private String reference;
}