/*
    This Class file manages the offline-signing process. Required data will be extracted of a certificate.
*/

::CLASS SEHandlerOffline PUBLIC
::ATTRIBUTE Base64
::ATTRIBUTE ECDSASigner
::ATTRIBUTE Decoder
::ATTRIBUTE KeyPairGenerator
::ATTRIBUTE SecureRandom
::ATTRIBUTE zertValue
::ATTRIBUTE Certificate
::METHOD init
 EXPOSE Base64  ECDSASigner Decoder KeyPairGenerator SecureRandom Certificate zertValue
 Base64 = bsf.import("java.util.Base64")
 ECDSASigner = bsf.import("com.nimbusds.jose.crypto.ECDSASigner")
 JWSSigner = bsf.loadClass("com.nimbusds.jose.JWSSigner")
 Decoder = Base64~getDecoder
 Certificate = "-----BEGIN CERTIFICATE-----MIIEvTCCA6WgAwIBAgIEIVm59jANBgkqhkiG9w0BAQsFADCBoTELMAkGA1UEBgwCQVQxSDBGBgNVBAoMP0EtVHJ1c3QgR2VzLiBmLiBTaWNoZXJoZWl0c3N5c3RlbWUgaW0gZWxla3RyLiBEYXRlbnZlcmtlaHIgR21iSDEjMCEGA1UECwwaYS1zaWduLVByZW1pdW0tVGVzdC1TaWctMDIxIzAhBgNVBAMMGmEtc2lnbi1QcmVtaXVtLVRlc3QtU2lnLTAyMB4XDTE2MDMxMDE0NDczOVoXDTIwMDUxMDE0NDczOVowYzELMAkGA1UEBgwCQVQxGTAXBgNVBAMMEFVJRDogQVRVMTIzNDU2NzgxFDASBgNVBAQMC0FUVTEyMzQ1Njc4MQwwCgYDVQQqDANVSUQxFTATBgNVBAUMDDUyOTkxMjU1MjI4NjBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABDmCCjepLRPT+MvR4CHqycC25UNfFaFcyqCL8lwEVsUVk10bmQn290u20foEaa075geQvJokWbTwTQqLgORYVVejggIDMIIB/zCBhAYIKwYBBQUHAQEEeDB2MEYGCCsGAQUFBzAChjpodHRwOi8vd3d3LmEtdHJ1c3QuYXQvY2VydHMvYS1zaWduLVByZW1pdW0tVGVzdC1TaWctMDIuY3J0MCwGCCsGAQUFBzABhiBodHRwOi8vb2NzcC10ZXN0LmEtdHJ1c3QuYXQvb2NzcDAOBgNVHQ8BAf8EBAMCBsAwJwYIKwYBBQUHAQMBAf8EGDAWMAgGBgQAjkYBATAKBggrBgEFBQcLATCBrgYDVR0fBIGmMIGjMIGgoIGdoIGahoGXbGRhcDovL2xkYXAtdGVzdC5hLXRydXN0LmF0L291PWEtc2lnbi1QcmVtaXVtLVRlc3QtU2lnLTAyIChTSEEtMjU2KSxvPUEtVHJ1c3QsYz1BVD9jZXJ0aWZpY2F0ZXJldm9jYXRpb25saXN0P2Jhc2U/b2JqZWN0Y2xhc3M9ZWlkQ2VydGlmaWNhdGlvbkF1dGhvcml0eTAJBgNVHRMEAjAAMFkGA1UdIARSMFAwCAYGBACLMAEBMEQGBiooABEBCzA6MDgGCCsGAQUFBwIBFixodHRwOi8vd3d3LmEtdHJ1c3QuYXQvZG9jcy9jcC9hLXNpZ24tUHJlbWl1bTATBgNVHSMEDDAKgAhGBp+OQY4VvTARBgNVHQ4ECgQITEStzGF8AcEwDQYJKoZIhvcNAQELBQADggEBADKLJSnaG7sMsX0USrzLHRXuWPKCrOXbLfXmnmlAN2+2Pzd/wAXXL1G2dpRpyspoC4QxLVQrUQE+WQae94lXdI7yFwVk8Y5bR+K/bY/EfNSPiwSyxXtYOnMrH+s9szH5nCG4aRGxys5hrbxfyS8GHXqv8V6cUlddCYkwXL4XXBpSxh9UofVOA1+mtKEtESg9ifcayV6TwBOHmzg7GZe0IY32VIpjaJQA8LQU1YDARx+yfuxtc4KBk3o5ZaVmZ4xyX/elUTLQX8aMnT7sIbhA3+FFvaD70iYp+9kZL9LO9bzfS/yv0xmPjFLVQ817DwTHM1ZFGk5d6WRGBIm7fjq8QuM=-----END CERTIFICATE-----"
 PARSE VAR Certificate "-----BEGIN CERTIFICATE-----" zertValue "-----END CERTIFICATE-----"


::METHOD signString PUBLIC
 EXPOSE ECDSASigner
 USE ARG string
 key = .my.app~DatabaseHandler~getJWSSigningKey
 payl = box("STring", string~string)

 JWSObject = bsf.import("com.nimbusds.jose.JWSObject")
 JWSAlgorithm = bsf.import("com.nimbusds.jose.JWSAlgorithm")
 JWSHeader = bsf.import("com.nimbusds.jose.JWSHeader")
 Payload = bsf.import("com.nimbusds.jose.Payload")

 JWSAlgorithmParse = JWSAlgorithm~parse("ES256")
 payload = Payload~new(payl)
 JWSHeaderNew = JWSHeader~new(JWSAlgorithmParse)
 jwsSigner = ECDSASigner~new(self~getPrivateKey(key))
 jwsObject = JWSObject~new(JWSHeaderNew,payload)
 jwsObject~sign(jwsSigner)
 compactJWS = jwsObject~serialize
 PARSE VAR compactJWS jws_header "." jws_payload "." jws_signature
 RETURN jws_header jws_payload jws_signature

::METHOD getPrivateKey PUBLIC
 EXPOSE Decoder
 USE ARG keyString
 PKCS8EncodedKeySpec = bsf.import("java.security.spec.PKCS8EncodedKeySpec")
 KeyFactory = bsf.loadClass("java.security.KeyFactory")~getInstance("EC")
 privateBytes = Decoder~decode(keyString)
 private = KeyFactory~generatePrivate(PKCS8EncodedKeySpec~new(privateBytes))
 RETURN private

::METHOD getCertNr PUBLIC
 EXPOSE Certificate
 X509CertUtils = bsf.import("com.nimbusds.jose.util.X509CertUtils")~NEW
 CertificateParsed = X509CertUtils~parse(Certificate)
 CertificateString = CertificateParsed~toString
 PARSE VAR CertificateString "SerialNumber: [" certSerialNumber "]"
 certSerialNumber = certSerialNumber~strip()
 RETURN certSerialNumber

::METHOD getZDA PUBLIC
 EXPOSE Certificate
 X509CertUtils = bsf.import("com.nimbusds.jose.util.X509CertUtils")~NEW
 CertificateParsed = X509CertUtils~parse(Certificate)
 CertificateString = CertificateParsed~toString
 PARSE VAR CertificateString  "C=" c +4 " "
 PARSE VAR c "C=" zda
 zda = zda || "1"
 RETURN ZDA
------------------------------------------------------------------------------------------------------------------------
::REQUIRES "BSF.CLS"

/*   License:

     ------------------------ Apache Version 2.0 license -------------------------
        Copyright (C) 2021 Manuel Schwarzer

        Licensed under the Apache License, Version 2.0 (the "License");
        you may not use this file except in compliance with the License.
        You may obtain a copy of the License at

            http://www.apache.org/licenses/LICENSE-2.0

        Unless required by applicable law or agreed to in writing, software
        distributed under the License is distributed on an "AS IS" BASIS,
        WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
        See the License for the specific language governing permissions and
        limitations under the License.
     -----------------------------------------------------------------------------
 */
