diff --git a/pom.xml b/pom.xml
index 2a78b18..90d2913 100644
--- a/pom.xml
+++ b/pom.xml
@@ -32,7 +32,8 @@
5.4.6
1.18.20
4.3.3
- 0.2.2-SNAPSHOT
+ 1.0.1
+ 1.5.10
1.5.7
5.7.1
1.4.2.Final
@@ -77,7 +78,7 @@
ehd-github
- https://maven.pkg.github.com/ehn-digital-green-development/*
+ https://maven.pkg.github.com/ehn-dcc-development/*
@@ -235,18 +236,28 @@
ehn.techiop.hcert
- hcert-kotlin
+ hcert-kotlin-jvm
${hcert-kotlin.version}
- com.augustcellars.cose
- cose-java
- 1.1.0
+ org.jetbrains.kotlinx
+ kotlinx-serialization-json
+ 1.2.1
org.jetbrains.kotlin
kotlin-stdlib-jdk8
- 1.4.31
+ ${kotlin.version}
+
+
+ org.jetbrains.kotlinx
+ kotlinx-datetime-jvm
+ 0.2.1
+
+
+ com.augustcellars.cose
+ cose-java
+ 1.1.0
com.fasterxml.jackson.dataformat
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/config/HcertLibConfig.java b/src/main/java/eu/europa/ec/dgc/issuance/config/HcertLibConfig.java
index 81ee537..5230271 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/config/HcertLibConfig.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/config/HcertLibConfig.java
@@ -1,13 +1,17 @@
package eu.europa.ec.dgc.issuance.config;
import ehn.techiop.hcert.kotlin.chain.Base45Service;
+import ehn.techiop.hcert.kotlin.chain.CborService;
import ehn.techiop.hcert.kotlin.chain.CompressorService;
import ehn.techiop.hcert.kotlin.chain.ContextIdentifierService;
import ehn.techiop.hcert.kotlin.chain.CoseService;
+import ehn.techiop.hcert.kotlin.chain.SchemaValidationService;
import ehn.techiop.hcert.kotlin.chain.impl.DefaultBase45Service;
+import ehn.techiop.hcert.kotlin.chain.impl.DefaultCborService;
import ehn.techiop.hcert.kotlin.chain.impl.DefaultCompressorService;
import ehn.techiop.hcert.kotlin.chain.impl.DefaultContextIdentifierService;
import ehn.techiop.hcert.kotlin.chain.impl.DefaultCoseService;
+import ehn.techiop.hcert.kotlin.chain.impl.DefaultSchemaValidationService;
import eu.europa.ec.dgc.issuance.service.EhdCryptoService;
import lombok.RequiredArgsConstructor;
import org.springframework.context.annotation.Bean;
@@ -38,4 +42,14 @@ Base45Service base45Service() {
return new DefaultBase45Service();
}
+ @Bean
+ CborService cborService() {
+ return new DefaultCborService();
+ }
+
+ @Bean
+ SchemaValidationService schemaValidationService() {
+ return new DefaultSchemaValidationService();
+ }
+
}
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciBackendController.java b/src/main/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciBackendController.java
index faad8f7..467e35c 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciBackendController.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciBackendController.java
@@ -1,12 +1,10 @@
package eu.europa.ec.dgc.issuance.restapi.controller;
-import ehn.techiop.hcert.data.Eudgc;
import eu.europa.ec.dgc.issuance.restapi.dto.EgdcCodeData;
import eu.europa.ec.dgc.issuance.service.DgciService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.responses.ApiResponse;
import io.swagger.v3.oas.annotations.responses.ApiResponses;
-import javax.validation.Valid;
import lombok.AllArgsConstructor;
import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
import org.springframework.http.MediaType;
@@ -17,7 +15,7 @@
import org.springframework.web.bind.annotation.RestController;
@RestController
-@RequestMapping("/context")
+@RequestMapping("/dgci")
@AllArgsConstructor
@ConditionalOnExpression("${issuance.endpoints.backendIssuing:false}")
public class DgciBackendController {
@@ -31,7 +29,7 @@ public class DgciBackendController {
@ApiResponse(responseCode = "200", description = "signed edgc qr code created"),
@ApiResponse(responseCode = "400", description = "wrong issue data")})
@PutMapping(value = "/issue", consumes = MediaType.APPLICATION_JSON_VALUE)
- public ResponseEntity createEdgc(@Valid @RequestBody Eudgc eudgc) {
+ public ResponseEntity createEdgc(@RequestBody String eudgc) {
EgdcCodeData egdcCodeData = dgciService.createEdgc(eudgc);
return ResponseEntity.ok(egdcCodeData);
}
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/restapi/dto/EgdcCodeData.java b/src/main/java/eu/europa/ec/dgc/issuance/restapi/dto/EgdcCodeData.java
index 06484f1..370023e 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/restapi/dto/EgdcCodeData.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/restapi/dto/EgdcCodeData.java
@@ -5,6 +5,6 @@
@Data
public class EgdcCodeData {
String dgci;
- String qrcCode;
+ String qrCode;
String tan;
}
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCborService.java b/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCborService.java
deleted file mode 100644
index ffc30e2..0000000
--- a/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCborService.java
+++ /dev/null
@@ -1,49 +0,0 @@
-package eu.europa.ec.dgc.issuance.service;
-
-import com.fasterxml.jackson.core.JsonProcessingException;
-import com.fasterxml.jackson.dataformat.cbor.databind.CBORMapper;
-import com.upokecenter.cbor.CBORObject;
-import ehn.techiop.hcert.data.Eudgc;
-import ehn.techiop.hcert.kotlin.chain.impl.DefaultCborService;
-import eu.europa.ec.dgc.issuance.config.IssuanceConfigProperties;
-import lombok.RequiredArgsConstructor;
-import org.jetbrains.annotations.NotNull;
-import org.springframework.stereotype.Service;
-
-/**
- * own cbor service.
- * The default one inject fixed country code and expiration period
- *
- */
-@Service
-@RequiredArgsConstructor
-public class ConfigurableCborService extends DefaultCborService {
- public static final int ISSUER = 1;
- public static final int ISSUED_AT = 6;
- public static final int EXPIRATION = 4;
- public static final int HCERT = -260;
- public static final int HCERT_VERSION = 1;
-
- private final ExpirationService expirationService;
- private final IssuanceConfigProperties issuanceConfigProperties;
-
- @Override
- public byte[] encode(@NotNull Eudgc input) {
- byte[] cbor;
- try {
- cbor = new CBORMapper().writeValueAsBytes(input);
- } catch (JsonProcessingException e) {
- throw new IllegalArgumentException(e);
- }
- ExpirationService.CwtTimeFields cwtTimes = expirationService.calculateCwtExpiration(input);
- CBORObject coseContainer = CBORObject.NewMap();
- coseContainer.set(CBORObject.FromObject(ISSUER),
- CBORObject.FromObject(issuanceConfigProperties.getCountryCode()));
- coseContainer.set(CBORObject.FromObject(ISSUED_AT),CBORObject.FromObject(cwtTimes.getIssuedAt()));
- coseContainer.set(CBORObject.FromObject(EXPIRATION),CBORObject.FromObject(cwtTimes.getExpiration()));
- CBORObject hcert = CBORObject.NewMap();
- hcert.set(CBORObject.FromObject(HCERT_VERSION),CBORObject.DecodeFromBytes(cbor));
- coseContainer.set(CBORObject.FromObject(HCERT),hcert);
- return coseContainer.EncodeToBytes();
- }
-}
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCwtService.java b/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCwtService.java
new file mode 100644
index 0000000..524855e
--- /dev/null
+++ b/src/main/java/eu/europa/ec/dgc/issuance/service/ConfigurableCwtService.java
@@ -0,0 +1,43 @@
+package eu.europa.ec.dgc.issuance.service;
+
+import com.upokecenter.cbor.CBORObject;
+import ehn.techiop.hcert.kotlin.chain.CwtService;
+import ehn.techiop.hcert.kotlin.chain.VerificationResult;
+import ehn.techiop.hcert.kotlin.crypto.CwtHeaderKeys;
+import ehn.techiop.hcert.kotlin.data.GreenCertificate;
+import eu.europa.ec.dgc.issuance.config.IssuanceConfigProperties;
+import kotlinx.serialization.json.Json;
+import lombok.RequiredArgsConstructor;
+import org.jetbrains.annotations.NotNull;
+import org.springframework.stereotype.Service;
+
+@Service
+@RequiredArgsConstructor
+public class ConfigurableCwtService implements CwtService {
+ private final ExpirationService expirationService;
+ private final IssuanceConfigProperties issuanceConfigProperties;
+
+ @NotNull
+ @Override
+ public byte[] decode(@NotNull byte[] bytes, @NotNull VerificationResult verificationResult) {
+ throw new UnsupportedOperationException("decoding not supported");
+ }
+
+ @NotNull
+ @Override
+ public byte[] encode(@NotNull byte[] bytes) {
+ CBORObject cwtMap = CBORObject.NewMap();
+ cwtMap.Add(CwtHeaderKeys.ISSUER.getIntVal(), issuanceConfigProperties.getCountryCode());
+ CBORObject dcc = CBORObject.DecodeFromBytes(bytes);
+ GreenCertificate greenCertificate = Json.Default.decodeFromString(GreenCertificate.Companion.serializer(),
+ dcc.ToJSONString());
+ ExpirationService.CwtTimeFields cwtTimes = expirationService.calculateCwtExpiration(greenCertificate);
+
+ cwtMap.Add(CwtHeaderKeys.ISSUED_AT.getIntVal(), cwtTimes.issuedAt);
+ cwtMap.Add(CwtHeaderKeys.EXPIRATION.getIntVal(), cwtTimes.expiration);
+ CBORObject hcertMap = CBORObject.NewMap();
+ hcertMap.Add(CwtHeaderKeys.EUDGC_IN_HCERT.getIntVal(),dcc);
+ cwtMap.Add(CwtHeaderKeys.HCERT.getIntVal(), hcertMap);
+ return cwtMap.EncodeToBytes();
+ }
+}
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/service/DgciService.java b/src/main/java/eu/europa/ec/dgc/issuance/service/DgciService.java
index 2db57d9..0f7d0ee 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/service/DgciService.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/service/DgciService.java
@@ -23,13 +23,13 @@
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.ObjectNode;
import com.nimbusds.jose.jwk.Curve;
import com.nimbusds.jose.jwk.ECKey;
import com.nimbusds.jose.jwk.RSAKey;
import com.nimbusds.jose.util.Base64URL;
import com.upokecenter.cbor.CBORObject;
import com.upokecenter.cbor.CBORType;
-import ehn.techiop.hcert.data.Eudgc;
import ehn.techiop.hcert.kotlin.chain.Base45Service;
import ehn.techiop.hcert.kotlin.chain.CborService;
import ehn.techiop.hcert.kotlin.chain.Chain;
@@ -37,6 +37,9 @@
import ehn.techiop.hcert.kotlin.chain.CompressorService;
import ehn.techiop.hcert.kotlin.chain.ContextIdentifierService;
import ehn.techiop.hcert.kotlin.chain.CoseService;
+import ehn.techiop.hcert.kotlin.chain.CwtService;
+import ehn.techiop.hcert.kotlin.chain.SchemaValidationService;
+import ehn.techiop.hcert.kotlin.data.GreenCertificate;
import eu.europa.ec.dgc.issuance.config.IssuanceConfigProperties;
import eu.europa.ec.dgc.issuance.entity.DgciEntity;
import eu.europa.ec.dgc.issuance.entity.GreenCertificateType;
@@ -71,6 +74,8 @@
import java.util.Base64;
import java.util.List;
import java.util.Optional;
+import kotlinx.serialization.SerializationException;
+import kotlinx.serialization.json.Json;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import lombok.val;
@@ -93,9 +98,11 @@ public enum DgciStatus {
private final DgciGenerator dgciGenerator;
private final CborService cborService;
private final CoseService coseService;
+ private final CwtService cwtService;
private final ContextIdentifierService contextIdentifierService;
private final CompressorService compressorService;
private final Base45Service base45Service;
+ private final SchemaValidationService schemaValidationService;
private final ExpirationService expirationService;
private static final int MAX_CLAIM_RETRY_TAN = 3;
@@ -363,37 +370,42 @@ private boolean verifySignature(ClaimRequest claimRequest) {
/**
* Create edgc in backend.
*
- * @param eudgc certificate
+ * @param dccJson certificate
* @return edgc qr code and tan
*/
- public EgdcCodeData createEdgc(Eudgc eudgc) {
+ public EgdcCodeData createEdgc(String dccJson) {
String dgci = dgciGenerator.newDgci();
+ dccJson = updateCI(dccJson, dgci);
+
+ GreenCertificate eudgc;
+ try {
+ eudgc = Json.Default.decodeFromString(GreenCertificate.Companion.serializer(), dccJson);
+ } catch (SerializationException se) {
+ throw new WrongRequest(se.getMessage());
+ }
GreenCertificateType greenCertificateType = GreenCertificateType.Vaccination;
- if (eudgc.getR() != null) {
- for (val v : eudgc.getR()) {
- v.setCi(dgci);
+ if (eudgc.getRecoveryStatements() != null) {
+ for (val v : eudgc.getRecoveryStatements()) {
greenCertificateType = GreenCertificateType.Recovery;
}
}
- if (eudgc.getT() != null) {
- for (val v : eudgc.getT()) {
- v.setCi(dgci);
+ if (eudgc.getTests() != null) {
+ for (val v : eudgc.getTests()) {
greenCertificateType = GreenCertificateType.Test;
}
}
- if (eudgc.getV() != null) {
- for (val v : eudgc.getV()) {
- v.setCi(dgci);
+ if (eudgc.getVaccinations() != null) {
+ for (val v : eudgc.getVaccinations()) {
greenCertificateType = GreenCertificateType.Vaccination;
}
}
Chain cborProcessingChain =
- new Chain(cborService, coseService,
- contextIdentifierService, compressorService, base45Service);
+ new Chain(cborService, cwtService, coseService,
+ contextIdentifierService, compressorService, base45Service, schemaValidationService);
ChainResult chainResult = cborProcessingChain.encode(eudgc);
EgdcCodeData egdcCodeData = new EgdcCodeData();
- egdcCodeData.setQrcCode(chainResult.getStep5Prefixed());
+ egdcCodeData.setQrCode(chainResult.getStep5Prefixed());
egdcCodeData.setDgci(dgci);
Tan ta = Tan.create();
egdcCodeData.setTan(ta.getRawTan());
@@ -411,6 +423,34 @@ public EgdcCodeData createEdgc(Eudgc eudgc) {
return egdcCodeData;
}
+ private String updateCI(String dccJson, String dgci) {
+ // The fields can be not modified on GreenCertificate object so we need to set ci on json level
+ ObjectMapper mapper = new ObjectMapper();
+ try {
+ JsonNode dccTree = mapper.readTree(dccJson);
+ updateCI(dccTree, dgci);
+ return mapper.writeValueAsString(dccTree);
+ } catch (JsonProcessingException e) {
+ throw new WrongRequest(e.getMessage());
+ }
+ }
+
+ private void updateCI(JsonNode jsonNode, String dgci) {
+ if (jsonNode.isObject()) {
+ if (jsonNode.has("ci")) {
+ ((ObjectNode)jsonNode).put("ci",dgci);
+ } else {
+ for (JsonNode value : jsonNode) {
+ updateCI(value, dgci);
+ }
+ }
+ } else if (jsonNode.isArray()) {
+ for (JsonNode item : jsonNode) {
+ updateCI(item, dgci);
+ }
+ }
+ }
+
/**
* Check if dgci exists.
*
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/service/EhdCryptoService.java b/src/main/java/eu/europa/ec/dgc/issuance/service/EhdCryptoService.java
index 3075740..9750418 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/service/EhdCryptoService.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/service/EhdCryptoService.java
@@ -21,12 +21,15 @@
package eu.europa.ec.dgc.issuance.service;
import COSE.AlgorithmID;
-import COSE.CoseException;
-import COSE.HeaderKeys;
-import COSE.OneKey;
import com.upokecenter.cbor.CBORObject;
import ehn.techiop.hcert.kotlin.chain.CryptoService;
import ehn.techiop.hcert.kotlin.chain.VerificationResult;
+import ehn.techiop.hcert.kotlin.crypto.CertificateAdapter;
+import ehn.techiop.hcert.kotlin.crypto.CoseHeaderKeys;
+import ehn.techiop.hcert.kotlin.crypto.JvmPrivKey;
+import ehn.techiop.hcert.kotlin.crypto.JvmPubKey;
+import ehn.techiop.hcert.kotlin.crypto.PrivKey;
+import ehn.techiop.hcert.kotlin.crypto.PubKey;
import java.security.PrivateKey;
import java.security.cert.X509Certificate;
import java.security.interfaces.RSAPrivateCrtKey;
@@ -39,7 +42,7 @@
public class EhdCryptoService implements CryptoService {
private final X509Certificate cert;
private final byte[] kid;
- private final List> headers;
+ private final List> headers;
private final PrivateKey privateKey;
/**
@@ -52,48 +55,37 @@ public EhdCryptoService(CertificateService certificateService) {
this.privateKey = certificateService.getPrivateKey();
kid = certificateService.getKid();
if (this.privateKey instanceof RSAPrivateCrtKey) {
- headers = Arrays.asList(new Pair<>(HeaderKeys.Algorithm, AlgorithmID.RSA_PSS_256.AsCBOR()),
- new Pair<>(HeaderKeys.KID, CBORObject.FromObject(kid)));
+ headers = Arrays.asList(new Pair<>(CoseHeaderKeys.ALGORITHM, AlgorithmID.RSA_PSS_256.AsCBOR()),
+ new Pair<>(CoseHeaderKeys.KID, CBORObject.FromObject(kid)));
} else {
- headers = Arrays.asList(new Pair<>(HeaderKeys.Algorithm, AlgorithmID.ECDSA_256.AsCBOR()),
- new Pair<>(HeaderKeys.KID, CBORObject.FromObject(kid)));
+ headers = Arrays.asList(new Pair<>(CoseHeaderKeys.ALGORITHM, AlgorithmID.ECDSA_256.AsCBOR()),
+ new Pair<>(CoseHeaderKeys.KID, CBORObject.FromObject(kid)));
}
}
+
@Override
- public List> getCborHeaders() {
+ public List> getCborHeaders() {
return headers;
}
@Override
- public COSE.OneKey getCborSigningKey() {
- try {
- return new OneKey(cert.getPublicKey(), privateKey);
- } catch (CoseException e) {
- throw new RuntimeException(e);
- }
+ public PrivKey getCborSigningKey() {
+ return new JvmPrivKey(privateKey);
}
@Override
- public COSE.OneKey getCborVerificationKey(byte[] bytes, VerificationResult verificationResult) {
+ public PubKey getCborVerificationKey(byte[] bytes, VerificationResult verificationResult) {
if (Arrays.compare(this.kid, kid) == 0) {
- try {
- return new OneKey(cert.getPublicKey(), privateKey);
- } catch (CoseException e) {
- throw new RuntimeException(e);
- }
+ return new JvmPubKey(cert.getPublicKey());
} else {
throw new IllegalArgumentException("unknown kid");
}
}
@Override
- public X509Certificate getCertificate() {
- if (Arrays.compare(this.kid, kid) == 0) {
- return cert;
- } else {
- throw new IllegalArgumentException("unknown kid");
- }
+ public CertificateAdapter getCertificate() {
+ return new CertificateAdapter(cert);
}
@Override
diff --git a/src/main/java/eu/europa/ec/dgc/issuance/service/ExpirationService.java b/src/main/java/eu/europa/ec/dgc/issuance/service/ExpirationService.java
index 72cb468..f646af5 100644
--- a/src/main/java/eu/europa/ec/dgc/issuance/service/ExpirationService.java
+++ b/src/main/java/eu/europa/ec/dgc/issuance/service/ExpirationService.java
@@ -1,14 +1,12 @@
package eu.europa.ec.dgc.issuance.service;
-import ehn.techiop.hcert.data.Eudgc;
+import ehn.techiop.hcert.kotlin.data.GreenCertificate;
import eu.europa.ec.dgc.issuance.config.IssuanceConfigProperties;
import eu.europa.ec.dgc.issuance.entity.GreenCertificateType;
import java.time.Duration;
import java.time.Instant;
-import java.time.LocalDate;
import java.time.ZoneOffset;
import java.time.temporal.ChronoUnit;
-import java.util.Date;
import lombok.Data;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Component;
@@ -55,27 +53,27 @@ public Duration expirationForType(GreenCertificateType greenCertificateType) {
* @param eudgc json data of dgc
* @return the times
*/
- public CwtTimeFields calculateCwtExpiration(Eudgc eudgc) {
+ public CwtTimeFields calculateCwtExpiration(GreenCertificate eudgc) {
CwtTimeFields result = new CwtTimeFields();
GreenCertificateType greenCertificateType;
long expirationTime;
long issueTime = Instant.now().getEpochSecond();
long expirationStartTime = issueTime;
- if (eudgc.getT() != null && !eudgc.getT().isEmpty()) {
+ if (eudgc.getTests() != null && !eudgc.getTests().isEmpty()) {
greenCertificateType = GreenCertificateType.Test;
- expirationStartTime = extractTimesSec(eudgc.getT().get(0).getSc(),expirationStartTime);
+ expirationStartTime = extractTimesSec(eudgc.getTests().get(0).getDateTimeSample(),expirationStartTime);
expirationTime = expirationStartTime + expirationForType(greenCertificateType).get(ChronoUnit.SECONDS);
- } else if (eudgc.getR() != null && !eudgc.getR().isEmpty()) {
+ } else if (eudgc.getRecoveryStatements() != null && !eudgc.getRecoveryStatements().isEmpty()) {
greenCertificateType = GreenCertificateType.Recovery;
expirationTime = expirationStartTime + expirationForType(greenCertificateType).get(ChronoUnit.SECONDS);
- expirationTime = extractTimesSec(eudgc.getR().get(0).getDu(),expirationTime);
- } else if (eudgc.getV() != null && !eudgc.getV().isEmpty()) {
+ expirationTime = extractTimesSec(eudgc.getRecoveryStatements().get(0).getCertificateValidUntil(),
+ expirationTime);
+ } else if (eudgc.getVaccinations() != null && !eudgc.getVaccinations().isEmpty()) {
greenCertificateType = GreenCertificateType.Vaccination;
- expirationStartTime = extractTimesSec(eudgc.getV().get(0).getDt(),expirationStartTime);
+ expirationStartTime = extractTimesSec(eudgc.getVaccinations().get(0).getDate(),expirationStartTime);
expirationTime = expirationStartTime + expirationForType(greenCertificateType).get(ChronoUnit.SECONDS);
} else {
- // fallback
greenCertificateType = GreenCertificateType.Vaccination;
expirationTime = expirationStartTime + expirationForType(greenCertificateType).get(ChronoUnit.SECONDS);
}
@@ -84,20 +82,20 @@ public CwtTimeFields calculateCwtExpiration(Eudgc eudgc) {
return result;
}
- private long extractTimesSec(Date date, long defaultTimeSec) {
+ private long extractTimesSec(kotlinx.datetime.Instant date, long defaultTimeSec) {
long timeSec;
if (date != null) {
- timeSec = date.toInstant().getEpochSecond();
+ timeSec = date.getEpochSeconds();
} else {
timeSec = defaultTimeSec;
}
return timeSec;
}
- private long extractTimesSec(String dateAsString, long defaultTimeSec) {
+ private long extractTimesSec(kotlinx.datetime.LocalDate localDate, long defaultTimeSec) {
long timeSec;
- if (dateAsString != null && dateAsString.length() > 0) {
- timeSec = LocalDate.parse(dateAsString).atStartOfDay().toInstant(ZoneOffset.UTC).getEpochSecond();
+ if (localDate != null) {
+ timeSec = localDate.getValue$kotlinx_datetime().atStartOfDay().toEpochSecond(ZoneOffset.UTC);
} else {
timeSec = defaultTimeSec;
}
diff --git a/src/test/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciControllerTest.java b/src/test/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciControllerTest.java
index ed89974..fbca81b 100644
--- a/src/test/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciControllerTest.java
+++ b/src/test/java/eu/europa/ec/dgc/issuance/restapi/controller/DgciControllerTest.java
@@ -1,7 +1,5 @@
package eu.europa.ec.dgc.issuance.restapi.controller;
-import com.fasterxml.jackson.databind.ObjectMapper;
-import ehn.techiop.hcert.data.Eudgc;
import eu.europa.ec.dgc.issuance.restapi.dto.EgdcCodeData;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
@@ -17,12 +15,10 @@ public class DgciControllerTest {
@Test
void checkBackendIssuing() throws Exception {
- ObjectMapper mapper = new ObjectMapper();
- Eudgc edgc = mapper.readValue("{\"ver\":\"1.0.0\",\"nam\":{\"fn\":\"Garcia\",\"fnt\":\"GARCIA\"," +
+ String edgc = "{\"ver\":\"1.0.0\",\"nam\":{\"fn\":\"Garcia\",\"fnt\":\"GARCIA\"," +
"\"gn\":\"Francisco\",\"gnt\":\"FRANCISCO\"},\"dob\":\"1991-01-01\",\"v\":[{\"tg\":\"840539006\"," +
"\"vp\":\"1119305005\",\"mp\":\"EU/1/20/1507\",\"ma\":\"ORG-100001699\",\"dn\":1,\"sd\":2,\"dt\":" +
- "\"2021-05-14\",\"co\":\"CY\",\"is\":\"Neha\",\"ci\":\"dgci:V1:CY:HIP4OKCIS8CXKQMJSSTOJXAMP:03\"}]}"
- ,Eudgc.class);
+ "\"2021-05-14\",\"co\":\"CY\",\"is\":\"Neha\",\"ci\":\"dgci:V1:CY:HIP4OKCIS8CXKQMJSSTOJXAMP:03\"}]}";
ResponseEntity responseEntity = dgciController.createEdgc(edgc);
assertNotNull(responseEntity.getBody());
}
diff --git a/src/test/java/eu/europa/ec/dgc/issuance/service/DGCGenTest.java b/src/test/java/eu/europa/ec/dgc/issuance/service/DGCGenTest.java
index 432cb23..9eb5e69 100644
--- a/src/test/java/eu/europa/ec/dgc/issuance/service/DGCGenTest.java
+++ b/src/test/java/eu/europa/ec/dgc/issuance/service/DGCGenTest.java
@@ -2,7 +2,8 @@
import com.upokecenter.cbor.CBORObject;
import com.upokecenter.cbor.CBORType;
-import ehn.techiop.hcert.kotlin.chain.common.Base45Encoder;
+import ehn.techiop.hcert.kotlin.chain.Base45Service;
+import ehn.techiop.hcert.kotlin.chain.impl.DefaultBase45Service;
import eu.europa.ec.dgc.issuance.entity.GreenCertificateType;
import eu.europa.ec.dgc.issuance.restapi.dto.DgciIdentifier;
import eu.europa.ec.dgc.issuance.restapi.dto.DgciInit;
@@ -114,8 +115,8 @@ private String coseToQRCode(byte[] cose) throws IOException {
ByteArrayInputStream bis = new ByteArrayInputStream(cose);
DeflaterInputStream compessedInput = new DeflaterInputStream(bis, new Deflater(9));
byte[] coseCompressed = compessedInput.readAllBytes();
- Base45Encoder base45Encoder = new Base45Encoder();
- String coded = base45Encoder.encode(coseCompressed);
+ Base45Service base45Service = new DefaultBase45Service();
+ String coded = base45Service.encode(coseCompressed);
return "HC1:"+coded;
}
}
diff --git a/src/test/java/eu/europa/ec/dgc/issuance/service/DgciServiceTest.java b/src/test/java/eu/europa/ec/dgc/issuance/service/DgciServiceTest.java
index cedd7d5..4d0bd6f 100644
--- a/src/test/java/eu/europa/ec/dgc/issuance/service/DgciServiceTest.java
+++ b/src/test/java/eu/europa/ec/dgc/issuance/service/DgciServiceTest.java
@@ -4,7 +4,6 @@
import COSE.CoseException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
-import ehn.techiop.hcert.data.Eudgc;
import ehn.techiop.hcert.kotlin.chain.SampleData;
import eu.europa.ec.dgc.issuance.config.IssuanceConfigProperties;
import eu.europa.ec.dgc.issuance.entity.DgciEntity;
@@ -99,11 +98,9 @@ void testDGCISign() throws Exception {
@Test
void testCreateEdgcBackend() throws Exception {
String vacDataJson = SampleData.Companion.getVaccination();
- ObjectMapper objectMapper = new ObjectMapper();
- Eudgc eudgc = objectMapper.readValue(vacDataJson,Eudgc.class);
- EgdcCodeData egdcCodeData = dgciService.createEdgc(eudgc);
+ EgdcCodeData egdcCodeData = dgciService.createEdgc(vacDataJson);
assertNotNull(egdcCodeData);
- assertNotNull(egdcCodeData.getQrcCode());
+ assertNotNull(egdcCodeData.getQrCode());
Optional dgciEnitiyOpt = dgciRepository.findByDgci(egdcCodeData.getDgci());
assertTrue(dgciEnitiyOpt.isPresent());
assertEquals(GreenCertificateType.Vaccination,dgciEnitiyOpt.get().getGreenCertificateType());
@@ -112,7 +109,7 @@ void testCreateEdgcBackend() throws Exception {
assertNotNull(dgciEnitiyOpt.get().getHashedTan());
assertNotNull(dgciEnitiyOpt.get().getExpiresAt());
- EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrcCode());
+ EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrCode());
assertTrue(decodeResult.isValidated());
assertNull(decodeResult.getErrorMessage());
JsonNode cborJson = decodeResult.getCborJson();
@@ -128,11 +125,9 @@ void testCreateEdgcBackend() throws Exception {
@Test
void testWalletClaim() throws Exception {
String vacDataJson = SampleData.Companion.getVaccination();
- ObjectMapper objectMapper = new ObjectMapper();
- Eudgc eudgc = objectMapper.readValue(vacDataJson,Eudgc.class);
- EgdcCodeData egdcCodeData = dgciService.createEdgc(eudgc);
+ EgdcCodeData egdcCodeData = dgciService.createEdgc(vacDataJson);
assertNotNull(egdcCodeData);
- assertNotNull(egdcCodeData.getQrcCode());
+ assertNotNull(egdcCodeData.getQrCode());
Optional dgciEnitiyOpt = dgciRepository.findByDgci(egdcCodeData.getDgci());
assertTrue(dgciEnitiyOpt.isPresent());
assertFalse(dgciEnitiyOpt.get().isClaimed());
@@ -140,7 +135,7 @@ void testWalletClaim() throws Exception {
String certHash = dgciEnitiyOpt.get().getCertHash();
assertEquals(GreenCertificateType.Vaccination,dgciEnitiyOpt.get().getGreenCertificateType());
- EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrcCode());
+ EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrCode());
assertTrue(decodeResult.isValidated());
assertNull(decodeResult.getErrorMessage());
@@ -166,6 +161,7 @@ void testWalletClaim() throws Exception {
assertNotNull(didDocument);
assertNotNull(didDocument.getAuthentication());
assertFalse(didDocument.getAuthentication().isEmpty());
+ ObjectMapper objectMapper = new ObjectMapper();
System.out.println(objectMapper.writeValueAsString(didDocument.getAuthentication().get(0).getPublicKeyJsw()));
}
@@ -179,11 +175,9 @@ private String sha256(String toHash) throws NoSuchAlgorithmException {
@Test
void testWalletClaimEC() throws Exception {
String vacDataJson = SampleData.Companion.getVaccination();
- ObjectMapper objectMapper = new ObjectMapper();
- Eudgc eudgc = objectMapper.readValue(vacDataJson,Eudgc.class);
- EgdcCodeData egdcCodeData = dgciService.createEdgc(eudgc);
+ EgdcCodeData egdcCodeData = dgciService.createEdgc(vacDataJson);
assertNotNull(egdcCodeData);
- assertNotNull(egdcCodeData.getQrcCode());
+ assertNotNull(egdcCodeData.getQrCode());
Optional dgciEnitiyOpt = dgciRepository.findByDgci(egdcCodeData.getDgci());
assertTrue(dgciEnitiyOpt.isPresent());
assertFalse(dgciEnitiyOpt.get().isClaimed());
@@ -191,7 +185,7 @@ void testWalletClaimEC() throws Exception {
String certHash = dgciEnitiyOpt.get().getCertHash();
assertEquals(GreenCertificateType.Vaccination,dgciEnitiyOpt.get().getGreenCertificateType());
- EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrcCode());
+ EgcDecodeResult decodeResult = edgcValidator.decodeEdgc(egdcCodeData.getQrCode());
assertTrue(decodeResult.isValidated());
assertNull(decodeResult.getErrorMessage());
@@ -209,6 +203,7 @@ void testWalletClaimEC() throws Exception {
assertNotNull(didDocument);
assertNotNull(didDocument.getAuthentication());
assertFalse(didDocument.getAuthentication().isEmpty());
+ ObjectMapper objectMapper = new ObjectMapper();
System.out.println(objectMapper.writeValueAsString(didDocument.getAuthentication().get(0).getPublicKeyJsw()));
}
diff --git a/src/test/java/eu/europa/ec/dgc/issuance/service/ExpirationServiceTest.java b/src/test/java/eu/europa/ec/dgc/issuance/service/ExpirationServiceTest.java
index 9c09809..5420220 100644
--- a/src/test/java/eu/europa/ec/dgc/issuance/service/ExpirationServiceTest.java
+++ b/src/test/java/eu/europa/ec/dgc/issuance/service/ExpirationServiceTest.java
@@ -1,10 +1,11 @@
package eu.europa.ec.dgc.issuance.service;
import com.fasterxml.jackson.databind.ObjectMapper;
-import ehn.techiop.hcert.data.Eudgc;
import ehn.techiop.hcert.kotlin.chain.SampleData;
+import ehn.techiop.hcert.kotlin.data.GreenCertificate;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
+import kotlinx.serialization.json.Json;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
@@ -20,21 +21,21 @@ class ExpirationServiceTest {
@Test
void testExpriationCalculation() throws Exception {
String vacDataJson = SampleData.Companion.getVaccination();
- Eudgc eudgc = testCalculation("vactination",vacDataJson);
- System.out.println(eudgc.getV().get(0).getDt());
+ GreenCertificate eudgc = testCalculation("vactination",vacDataJson);
+ System.out.println(eudgc.getVaccinations().get(0).getDate());
String recoveryDataJson = SampleData.Companion.getRecovery();
eudgc = testCalculation("recovery",recoveryDataJson);
- System.out.println(eudgc.getR().get(0).getDu());
+ System.out.println(eudgc.getRecoveryStatements().get(0).getCertificateValidUntil());
String testDataJson = SampleData.Companion.getTestNaa();
eudgc = testCalculation("test",testDataJson);
- System.out.println(eudgc.getT().get(0).getSc().toInstant().atOffset(ZoneOffset.UTC));
+ System.out.println(eudgc.getTests().get(0).getDateTimeSample());
assertNotNull(eudgc);
}
- private Eudgc testCalculation(String description, String vacDataJson) throws com.fasterxml.jackson.core.JsonProcessingException {
+ private GreenCertificate testCalculation(String description, String vacDataJson) throws com.fasterxml.jackson.core.JsonProcessingException {
System.out.println("testing: "+description);
- Eudgc eudgc = objectMapper.readValue(vacDataJson,Eudgc.class);
+ GreenCertificate eudgc = Json.Default.decodeFromString(GreenCertificate.Companion.serializer(), vacDataJson);
ExpirationService.CwtTimeFields expTime = expirationService.calculateCwtExpiration(eudgc);
LocalDateTime issuedAt = LocalDateTime.ofEpochSecond(expTime.getIssuedAt(), 0, ZoneOffset.UTC);
assertNotNull(issuedAt);