diff --git a/android/clientmanager/src/main/java/io/mosip/registration/clientmanager/config/AppModule.java b/android/clientmanager/src/main/java/io/mosip/registration/clientmanager/config/AppModule.java index 528d381b6..5e474a6e5 100644 --- a/android/clientmanager/src/main/java/io/mosip/registration/clientmanager/config/AppModule.java +++ b/android/clientmanager/src/main/java/io/mosip/registration/clientmanager/config/AppModule.java @@ -71,8 +71,8 @@ public Context provideApplicationContext() { @Singleton @Provides - public ClientCryptoManagerService provideClientCryptoManagerService() { - return new LocalClientCryptoServiceImpl(appContext); + public ClientCryptoManagerService provideClientCryptoManagerService(CertificateManagerService certificateManagerService) { + return new LocalClientCryptoServiceImpl(appContext, certificateManagerService); } @Singleton diff --git a/android/keymanager/build.gradle b/android/keymanager/build.gradle index 8930b2f1e..d43bffeed 100644 --- a/android/keymanager/build.gradle +++ b/android/keymanager/build.gradle @@ -68,9 +68,16 @@ dependencies { implementation group: 'commons-io', name: 'commons-io', version: '2.11.0' implementation 'org.bouncycastle:bcprov-jdk15on:1.59' - // https://mvnrepository.com/artifact/com.madgag.spongycastle/core + implementation 'org.bouncycastle:bcpkix-jdk15on:1.47' + implementation 'com.madgag.spongycastle:core:1.58.0.0' + implementation 'com.fasterxml.jackson.core:jackson-core:2.13.2' + implementation 'com.fasterxml.jackson.core:jackson-databind:2.13.3' + implementation 'com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.13.3' + implementation 'com.fasterxml.jackson.module:jackson-module-afterburner:2.13.3' + implementation 'org.bitbucket.b_c:jose4j:0.6.5' + } sonarqube { diff --git a/android/keymanager/src/main/assets/config.properties b/android/keymanager/src/main/assets/config.properties index 7f922631d..5327ba1b7 100644 --- a/android/keymanager/src/main/assets/config.properties +++ b/android/keymanager/src/main/assets/config.properties @@ -26,3 +26,6 @@ mosip.kernel.crypto.sign-algorithm-padding-scheme=PKCS1 mosip.kernel.certificate.sign.algorithm=SHA256withRSA #CA certificate allowed partner domains mosip.kernel.partner.allowed.domains=DEVICE + +mosip.sign.applicationid=KERNEL +mosip.sign.refid=SIGN diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustRequestDto.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustRequestDto.java new file mode 100644 index 000000000..fc868c9f1 --- /dev/null +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustRequestDto.java @@ -0,0 +1,25 @@ +package io.mosip.registration.keymanager.dto; + +import javax.validation.constraints.NotBlank; + +import lombok.Data; + +/** + * Partner Certificates Verify Trust Request DTO. + */ +@Data +public class CertificateTrustRequestDto { + + /** + * Certificate Data of Partner. + */ + @NotBlank(message = "Invalid Request") + private String certificateData; + + /** + * Partner Type. + */ + @NotBlank(message = "Invalid Request") + private String partnerDomain; + +} diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustResponseDto.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustResponseDto.java new file mode 100644 index 000000000..176b4770d --- /dev/null +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/CertificateTrustResponseDto.java @@ -0,0 +1,16 @@ +package io.mosip.registration.keymanager.dto; + +import lombok.Data; + +/** + * DTO class for certificate verification response. + */ +@Data +public class CertificateTrustResponseDto { + + /** + * Status of certificate verification. + */ + private Boolean status; + +} diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyRequestDto.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyRequestDto.java new file mode 100644 index 000000000..01c49b60a --- /dev/null +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyRequestDto.java @@ -0,0 +1,39 @@ +package io.mosip.registration.keymanager.dto; + +import javax.validation.constraints.NotBlank; + +import lombok.Data; + +@Data +public class JWTSignatureVerifyRequestDto { + + @NotBlank + private String jwtSignatureData; + + private String actualData; + + /** + * Application id of decrypting module + */ + private String applicationId; + + /** + * Refrence Id + */ + private String referenceId; + + /** + * Certificate to be use in JWT Signature verification. + */ + private String certificateData; + + /** + * Flag to validate against trust store. + */ + private Boolean validateTrust; + + /** + * Domain to be considered to validate trust store + */ + private String domain; +} diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyResponseDto.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyResponseDto.java new file mode 100644 index 000000000..418683270 --- /dev/null +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/dto/JWTSignatureVerifyResponseDto.java @@ -0,0 +1,23 @@ +package io.mosip.registration.keymanager.dto; + +import lombok.Data; + +@Data +public class JWTSignatureVerifyResponseDto { + + /** + * The Signature verification status. + */ + private boolean signatureValid; + + /** + * The Signature validation message. + */ + private String message; + + /** + * The Trust validation status. + */ + private String trustValid; + +} diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/CertificateManagerServiceImpl.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/CertificateManagerServiceImpl.java index 2cb00eebd..834556729 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/CertificateManagerServiceImpl.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/CertificateManagerServiceImpl.java @@ -5,6 +5,8 @@ import io.mosip.registration.keymanager.dto.CACertificateRequestDto; import io.mosip.registration.keymanager.dto.CACertificateResponseDto; import io.mosip.registration.keymanager.dto.CertificateRequestDto; +import io.mosip.registration.keymanager.dto.CertificateTrustRequestDto; +import io.mosip.registration.keymanager.dto.CertificateTrustResponseDto; import io.mosip.registration.keymanager.exception.KeymanagerServiceException; import io.mosip.registration.keymanager.repository.KeyStoreRepository; import io.mosip.registration.keymanager.spi.CertificateManagerService; @@ -54,6 +56,7 @@ public CACertificateResponseDto uploadCACertificate(CACertificateRequestDto caCe String certSubject = CertificateManagerUtil.formatCertificateDN(reqX509Cert.getSubjectX500Principal().getName()); String certIssuer = CertificateManagerUtil.formatCertificateDN(reqX509Cert.getIssuerX500Principal().getName()); + boolean selfSigned = CertificateManagerUtil.isSelfSignedCertificate(reqX509Cert); if (selfSigned) { @@ -81,6 +84,26 @@ public CACertificateResponseDto uploadCACertificate(CACertificateRequestDto caCe return responseDto; } + public CertificateTrustResponseDto verifyCertificateTrust(CertificateTrustRequestDto certificateTrustRequestDto) { + Log.i(TAG, "Certificate Trust Path Validation."); + + String certificateData = certificateTrustRequestDto.getCertificateData(); + if (!CertificateManagerUtil.isValidCertificateData(certificateData)) { + Log.e(TAG, "Invalid Certificate Data provided to verify partner certificate trust."); + throw new KeymanagerServiceException(KeyManagerErrorCode.INVALID_CERTIFICATE.getErrorCode(), + KeyManagerErrorCode.INVALID_CERTIFICATE.getErrorMessage()); + } + X509Certificate reqX509Cert = (X509Certificate) CertificateManagerUtil.convertToCertificate(certificateData); + String partnerDomain = validateAllowedDomains(certificateTrustRequestDto.getPartnerDomain()); + + Log.i(TAG, "Certificate Trust Path Validation for domain: " + partnerDomain); + + boolean certValid = validateCertificatePath(reqX509Cert, partnerDomain); + CertificateTrustResponseDto responseDto = new CertificateTrustResponseDto(); + responseDto.setStatus(certValid); + return responseDto; + } + @Override public void uploadOtherDomainCertificate(CertificateRequestDto certificateRequestDto) { Log.i(TAG, "Uploading other domain Certificate."); diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/LocalClientCryptoServiceImpl.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/LocalClientCryptoServiceImpl.java index 04d41fb8e..571dca56e 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/LocalClientCryptoServiceImpl.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/service/LocalClientCryptoServiceImpl.java @@ -5,12 +5,22 @@ import android.security.keystore.KeyProperties; import android.util.Log; import io.mosip.registration.keymanager.dto.*; +import io.mosip.registration.keymanager.exception.KeymanagerServiceException; +import io.mosip.registration.keymanager.spi.CertificateManagerService; import io.mosip.registration.keymanager.spi.ClientCryptoManagerService; +import io.mosip.registration.keymanager.util.CertificateManagerUtil; import io.mosip.registration.keymanager.util.ConfigService; import io.mosip.registration.keymanager.util.CryptoUtil; +import io.mosip.registration.keymanager.util.JsonUtils; +import io.mosip.registration.keymanager.util.KeyManagerConstant; import io.mosip.registration.keymanager.util.KeyManagerErrorCode; +import java.security.cert.Certificate; + +import org.apache.commons.codec.binary.Base64; import org.apache.commons.io.IOUtils; import org.apache.commons.lang3.RandomStringUtils; +import org.jose4j.jws.JsonWebSignature; +import org.jose4j.jwx.CompactSerializer; import org.json.JSONObject; import org.spongycastle.crypto.InvalidCipherTextException; import org.spongycastle.crypto.digests.SHA256Digest; @@ -32,13 +42,15 @@ import java.math.BigInteger; import java.nio.charset.StandardCharsets; import java.security.*; +import java.security.cert.X509Certificate; import java.security.interfaces.RSAKey; import java.security.spec.MGF1ParameterSpec; import java.security.spec.X509EncodedKeySpec; import java.util.Arrays; import java.util.HashMap; +import java.util.List; import java.util.Map; - +import java.util.Objects; import static io.mosip.registration.keymanager.util.KeyManagerConstant.*; @@ -76,17 +88,21 @@ public class LocalClientCryptoServiceImpl implements ClientCryptoManagerService private static String CERTIFICATE_SIGN_ALGORITHM; + private static String SIGN_APPLICATION_ID; + private static String SIGN_REFERENCE_ID; + private static SecureRandom secureRandom = new SecureRandom(); private KeyStore keyStore = null; - + private CertificateManagerService certificateManagerService; @Inject - public LocalClientCryptoServiceImpl(Context appContext) { + public LocalClientCryptoServiceImpl(Context appContext, CertificateManagerService certificateManagerService) { Log.i(TAG, "LocalClientCryptoServiceImpl: Constructor call successful"); try { keyStore = KeyStore.getInstance(ANDROID_KEY_STORE); keyStore.load(null); initLocalClientCryptoService(appContext); + this.certificateManagerService = certificateManagerService; } catch (Exception e) { Log.e(TAG, "LocalClientCryptoServiceImpl: Failed Initialization", e); } @@ -122,6 +138,8 @@ private void initializeClientSecurity() { ConfigService.getProperty("mosip.kernel.crypto.gcm-tag-length",context)); KEYGEN_ASYMMETRIC_ALGO_SIGN_PAD = ConfigService.getProperty("mosip.kernel.crypto.sign-algorithm-padding-scheme",context); CERTIFICATE_SIGN_ALGORITHM = ConfigService.getProperty("mosip.kernel.certificate.sign.algorithm",context); + SIGN_APPLICATION_ID = ConfigService.getProperty("mosip.sign.applicationid", context); + SIGN_REFERENCE_ID = ConfigService.getProperty("mosip.sign.refid", context); } private void genSignKey() { @@ -231,6 +249,125 @@ public SignVerifyResponseDto verifySign(SignVerifyRequestDto signVerifyRequestDt return null; } + public JWTSignatureVerifyResponseDto jwtVerify(JWTSignatureVerifyRequestDto jwtVerifyRequestDto) throws Exception { + String signedData = jwtVerifyRequestDto.getJwtSignatureData(); + if (!CertificateManagerUtil.isDataValid(signedData)) { + Log.e(TAG,"Provided Signed Data value is invalid."); + throw new Exception(); + } + + String encodedActualData = CertificateManagerUtil.isDataValid(jwtVerifyRequestDto.getActualData()) + ? jwtVerifyRequestDto.getActualData() : null; + + String reqCertData = CertificateManagerUtil.isValidCertificateData(jwtVerifyRequestDto.getCertificateData()) + ? jwtVerifyRequestDto.getCertificateData(): null; + String applicationId = jwtVerifyRequestDto.getApplicationId(); + String referenceId = jwtVerifyRequestDto.getReferenceId(); + if (!CertificateManagerUtil.isValidApplicationId(applicationId)) { + applicationId = SIGN_APPLICATION_ID; + referenceId = SIGN_REFERENCE_ID; + } + + String[] jwtTokens = signedData.split(PERIOD, -1); + + boolean signatureValid = false; + Certificate certToVerify = certificateExistsInHeader(jwtTokens[0]); + if (Objects.nonNull(certToVerify)){ + signatureValid = verifySignature(jwtTokens, encodedActualData, certToVerify); + } else { + Certificate reqCertToVerify = getCertificateToVerify(reqCertData, applicationId, referenceId); + signatureValid = verifySignature(jwtTokens, encodedActualData, reqCertToVerify); + } + + JWTSignatureVerifyResponseDto responseDto = new JWTSignatureVerifyResponseDto(); + responseDto.setSignatureValid(signatureValid); + responseDto.setMessage(signatureValid ? KeyManagerConstant.VALIDATION_SUCCESSFUL : KeyManagerConstant.VALIDATION_FAILED); + responseDto.setTrustValid(validateTrust(jwtVerifyRequestDto, certToVerify, reqCertData)); + return responseDto; + } + + private Certificate getCertificateToVerify(String reqCertData, String applicationId, String referenceId) { + // 2nd precedence to consider certificate to use in signature verification (Certificate Data provided in request). + if (reqCertData != null) + return CertificateManagerUtil.convertToCertificate(reqCertData); + + // 3rd precedence to consider certificate to use in signature verification. (based on AppId & RefId) + String certificateData = certificateManagerService.getCertificate(applicationId, referenceId); + return CertificateManagerUtil.convertToCertificate(certificateData); + } + + private boolean verifySignature(String[] jwtTokens, String actualData, Certificate certToVerify) { + JsonWebSignature jws = new JsonWebSignature(); + try { + boolean validCert = CertificateManagerUtil.isCertificateDatesValid((X509Certificate) certToVerify); + if (!validCert) { + Log.e(TAG, "Error certificate dates are not valid."); + throw new KeymanagerServiceException(KeyManagerErrorCode.CERT_NOT_VALID.getErrorCode(), + KeyManagerErrorCode.CERT_NOT_VALID.getErrorMessage()); + } + + PublicKey publicKey = certToVerify.getPublicKey(); + if (Objects.nonNull(actualData)) + jwtTokens[1] = actualData; + + jws.setCompactSerialization(CompactSerializer.serialize(jwtTokens)); + if (Objects.nonNull(publicKey)) + jws.setKey(publicKey); + + return jws.verifySignature(); + } catch (Exception e) { + Log.e(TAG, "Provided Signed Data value is invalid."); + throw new KeymanagerServiceException(KeyManagerErrorCode.VERIFY_ERROR.getErrorCode(), + KeyManagerErrorCode.VERIFY_ERROR.getErrorMessage(), e); + } + } + + private Certificate certificateExistsInHeader(String jwtHeader) { + String jwtTokenHeader = new String(CryptoUtil.decodeBase64(jwtHeader)); + Map jwtTokenHeadersMap = JsonUtils.jsonStringToJavaMap(jwtTokenHeader); + if (jwtTokenHeadersMap == null){ + Log.e(TAG, "Provided Signed Data value is invalid."); + return null; + } + // 1st precedence to consider certificate to use in signature verification (JWT Header). + if (jwtTokenHeadersMap.containsKey(JWT_HEADER_CERT_KEY)) { + Log.i(TAG, "Certificate found in JWT Header."); + List certList = (List) jwtTokenHeadersMap.get(JWT_HEADER_CERT_KEY); + return CertificateManagerUtil.convertToCertificate(Base64.decodeBase64(certList.get(0))); + } + Log.i(TAG, "Certificate not found in JWT Header."); + return null; + } + + private String validateTrust(JWTSignatureVerifyRequestDto jwtVerifyRequestDto, Certificate headerCertificate, String reqCertData) { + if (jwtVerifyRequestDto.getValidateTrust() == null || !jwtVerifyRequestDto.getValidateTrust()) { + return KeyManagerConstant.TRUST_NOT_VERIFIED; + } + + String domain = jwtVerifyRequestDto.getDomain(); + if(!CertificateManagerUtil.isDataValid(domain)) + return KeyManagerConstant.TRUST_NOT_VERIFIED_NO_DOMAIN; + + String certData = null; + if (Objects.nonNull(headerCertificate)) { + certData = CertificateManagerUtil.getPEMFormatedData(headerCertificate); + } + String trustCertData = certData == null ? reqCertData : certData; + + if (trustCertData == null) + return KeyManagerConstant.TRUST_NOT_VERIFIED; + + CertificateTrustRequestDto trustRequestDto = new CertificateTrustRequestDto(); + trustRequestDto.setCertificateData(trustCertData); + trustRequestDto.setPartnerDomain(domain); + CertificateTrustResponseDto responseDto = certificateManagerService.verifyCertificateTrust(trustRequestDto); + + if (responseDto.getStatus()){ + return KeyManagerConstant.TRUST_VALID; + } + return KeyManagerConstant.TRUST_NOT_VALID; + } + @Override public CryptoResponseDto encrypt(CryptoRequestDto cryptoRequestDto) { CryptoResponseDto cryptoResponseDto = new CryptoResponseDto(); diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/CertificateManagerService.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/CertificateManagerService.java index 6fc28610f..d36e00eea 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/CertificateManagerService.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/CertificateManagerService.java @@ -3,10 +3,13 @@ import io.mosip.registration.keymanager.dto.CACertificateRequestDto; import io.mosip.registration.keymanager.dto.CACertificateResponseDto; import io.mosip.registration.keymanager.dto.CertificateRequestDto; +import io.mosip.registration.keymanager.dto.CertificateTrustRequestDto; +import io.mosip.registration.keymanager.dto.CertificateTrustResponseDto; public interface CertificateManagerService { CACertificateResponseDto uploadCACertificate(CACertificateRequestDto caCertificateRequestDto); void uploadOtherDomainCertificate(CertificateRequestDto certificateRequestDto); String getCertificate(String applicationId, String referenceId); + CertificateTrustResponseDto verifyCertificateTrust(CertificateTrustRequestDto certificateTrustRequestDto); } diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/ClientCryptoManagerService.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/ClientCryptoManagerService.java index cfe38bff3..ab919e754 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/ClientCryptoManagerService.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/spi/ClientCryptoManagerService.java @@ -27,4 +27,6 @@ public interface ClientCryptoManagerService { String getClientKeyIndex() throws Exception; Map getMachineDetails(); + + JWTSignatureVerifyResponseDto jwtVerify(JWTSignatureVerifyRequestDto jwtSignatureVerifyRequestDto) throws Exception; } diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CertificateManagerUtil.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CertificateManagerUtil.java index 96900ad2d..cf76d701b 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CertificateManagerUtil.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CertificateManagerUtil.java @@ -5,11 +5,13 @@ import io.mosip.registration.keymanager.exception.KeymanagerServiceException; import lombok.NonNull; import org.apache.commons.codec.digest.DigestUtils; +import org.apache.commons.lang3.StringUtils; import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.x500.RDN; import org.bouncycastle.asn1.x500.X500Name; import org.bouncycastle.asn1.x500.style.BCStyle; import org.bouncycastle.asn1.x500.style.IETFUtils; +import org.bouncycastle.openssl.PEMWriter; import org.bouncycastle.util.encoders.Hex; import org.bouncycastle.util.io.pem.PemObject; import org.bouncycastle.util.io.pem.PemReader; @@ -17,6 +19,7 @@ import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.StringReader; +import java.io.StringWriter; import java.security.InvalidKeyException; import java.security.NoSuchAlgorithmException; import java.security.NoSuchProviderException; @@ -31,7 +34,15 @@ public class CertificateManagerUtil { private static final String TAG = CertificateManagerUtil.class.getSimpleName(); public static boolean isValidCertificateData(String certData) { - return certData != null && !certData.trim().isEmpty(); + return !StringUtils.isBlank(certData); + } + + public static boolean isValidApplicationId(String appId) { + return !StringUtils.isBlank(appId); + } + + public static boolean isDataValid(String anyData) { + return !StringUtils.isBlank(anyData); } public static Certificate convertToCertificate(String certData) { @@ -53,6 +64,17 @@ public static Certificate convertToCertificate(String certData) { } } + public static Certificate convertToCertificate(byte[] certDataBytes) { + try { + CertificateFactory certFactory = CertificateFactory.getInstance(KeyManagerConstant.CERTIFICATE_TYPE); + return certFactory.generateCertificate(new ByteArrayInputStream(certDataBytes)); + } catch(CertificateException e) { + Log.e(TAG, "Error Parsing Certificate.", e); + throw new KeymanagerServiceException(KeyManagerErrorCode.CERTIFICATE_PARSING_ERROR.getErrorCode(), + KeyManagerErrorCode.CERTIFICATE_PARSING_ERROR.getErrorMessage() + e.getMessage()); + } + } + public static String getCertificateThumbprint(X509Certificate x509Cert) { if(x509Cert == null) throw new KeymanagerServiceException(KeyManagerErrorCode.CERTIFICATE_THUMBPRINT_ERROR.getErrorCode(), @@ -150,4 +172,16 @@ public static byte[] getCertificateThumbprint(Certificate cert) { public static String getCertificateThumbprintInHex(Certificate cert) { return Hex.toHexString(getCertificateThumbprint(cert)).toUpperCase(); } + + public static String getPEMFormatedData(Object anyObject){ + StringWriter stringWriter = new StringWriter(); + try (PEMWriter pemWriter = new PEMWriter(stringWriter)) { + pemWriter.writeObject(anyObject); + pemWriter.flush(); + return stringWriter.toString(); + } catch (IOException ioExp) { + throw new KeymanagerServiceException(KeyManagerErrorCode.INTERNAL_SERVER_ERROR.getErrorCode(), + KeyManagerErrorCode.INTERNAL_SERVER_ERROR.getErrorMessage(), ioExp); + } + } } diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CryptoUtil.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CryptoUtil.java index f82a01983..bf3f16345 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CryptoUtil.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/CryptoUtil.java @@ -4,6 +4,7 @@ import org.apache.commons.codec.binary.Hex; import org.apache.commons.codec.digest.DigestUtils; import org.apache.commons.lang3.ArrayUtils; +import org.apache.commons.lang3.StringUtils; import java.security.MessageDigest; import java.security.cert.Certificate; @@ -45,4 +46,15 @@ public static String generateMD5Hash(byte[] data) { return new String(Hex.encodeHex(messageDigestMD5.digest(data))); } + public static byte[] decodeBase64(String data) { + if (StringUtils.isBlank(data)) { + return null; + } + try { + return base64decoder.decode(data); + } catch (IllegalArgumentException exception) { + return Base64.getDecoder().decode(data); + } + } + } diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/JsonUtils.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/JsonUtils.java new file mode 100644 index 000000000..997a8f9a3 --- /dev/null +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/JsonUtils.java @@ -0,0 +1,45 @@ +package io.mosip.registration.keymanager.util; + +import android.util.Log; + +import com.fasterxml.jackson.core.type.TypeReference; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.json.JsonMapper; +import com.fasterxml.jackson.databind.SerializationFeature; +import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; +import com.fasterxml.jackson.module.afterburner.AfterburnerModule; + +import java.util.Map; + +public class JsonUtils { + + private static ObjectMapper objectMapper; + private static final String TAG = JsonUtils.class.getSimpleName(); + + static { + objectMapper = JsonMapper.builder().addModule(new AfterburnerModule()).build(); + objectMapper.registerModule(new JavaTimeModule()); + objectMapper.enable(SerializationFeature.INDENT_OUTPUT); + objectMapper.disable(SerializationFeature.FAIL_ON_EMPTY_BEANS); + } + + /** + * This method converts a JSON String containing multiple JSON and stores them + * in a java Map + * + * @param jsonString input String containing array of JSON string(always in + * double quotes) (eg."[{color=Black, type=BMW}, {color=Red, + * type=FIAT}]") + * @return java map containing JSON inputs + */ + public static Map jsonStringToJavaMap(String jsonString) { + Map javaMap = null; + try { + javaMap = objectMapper.readValue(jsonString, new TypeReference>() { + }); + } catch (Exception e) { + Log.e(TAG, "Exception in converting jsonString to map"); + } + return javaMap; + } +} diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerConstant.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerConstant.java index a15f6868c..1999a38c6 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerConstant.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerConstant.java @@ -40,4 +40,22 @@ public class KeyManagerConstant { public static final String KEYALIAS = "keyAlias"; public static final String CURRENTKEYALIAS = "currentKeyAlias"; + + public static final Boolean DEFAULT_INCLUDES = false; + + public static final String TRUST_NOT_VERIFIED = "TRUST_NOT_VERIFIED"; + + public static final String TRUST_NOT_VERIFIED_NO_DOMAIN = "TRUST_NOT_VERIFIED_NO_DOMAIN"; + + public static final String TRUST_NOT_VALID = "TRUST_CERT_PATH_NOT_VALID"; + + public static final String TRUST_VALID = "TRUST_CERT_PATH_VALID"; + + public static final String PERIOD = "\\."; + + public static final String JWT_HEADER_CERT_KEY = "x5c"; + + public static final String VALIDATION_SUCCESSFUL = "Validation Successful"; + + public static final String VALIDATION_FAILED = "Validation Failed"; } diff --git a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerErrorCode.java b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerErrorCode.java index c7718ff76..e07a75774 100644 --- a/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerErrorCode.java +++ b/android/keymanager/src/main/java/io/mosip/registration/keymanager/util/KeyManagerErrorCode.java @@ -83,6 +83,8 @@ public enum KeyManagerErrorCode { CERTIFICATE_EXIST_ERROR("KER-PCM-003", "Certificate already exists in store."), CERTIFICATE_DATES_NOT_VALID("KER-PCM-004", "Certificate Dates are not valid."), ROOT_CA_NOT_FOUND("KER-PCM-005", "Root CA Certificate not found."), + CERT_NOT_VALID("KER-JWS-107", "Signature verification certificate not valid."), + VERIFY_ERROR("KER-JWS-105", "Error - Unable to verify the data."), INTERNAL_SERVER_ERROR("KER-CRY-500", "Internal server error"); diff --git a/android/keymanager/src/test/java/io/mosip/registration/keymanager/CertificateManagerUtilTest.java b/android/keymanager/src/test/java/io/mosip/registration/keymanager/CertificateManagerUtilTest.java index 4d6813afb..cc29db495 100644 --- a/android/keymanager/src/test/java/io/mosip/registration/keymanager/CertificateManagerUtilTest.java +++ b/android/keymanager/src/test/java/io/mosip/registration/keymanager/CertificateManagerUtilTest.java @@ -66,7 +66,7 @@ public void convertToCertificate_valid_cert_test() { @Test(expected = KeymanagerServiceException.class) public void convertToCertificate_null_cert_test() { - CertificateManagerUtil.convertToCertificate(null); + CertificateManagerUtil.convertToCertificate((String) null); } @Test(expected = KeymanagerServiceException.class)