aboutsummaryrefslogtreecommitdiff
path: root/ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt
diff options
context:
space:
mode:
Diffstat (limited to 'ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt')
-rw-r--r--ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt350
1 files changed, 350 insertions, 0 deletions
diff --git a/ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt b/ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt
new file mode 100644
index 00000000..57841e28
--- /dev/null
+++ b/ebics/src/main/kotlin/ebics_h004/EbicsResponse.kt
@@ -0,0 +1,350 @@
+package tech.libeufin.ebics.ebics_h004
+
+import org.apache.xml.security.binding.xmldsig.SignatureType
+import org.apache.xml.security.binding.xmldsig.SignedInfoType
+import tech.libeufin.common.CryptoUtil
+import tech.libeufin.ebics.XMLUtil
+import java.math.BigInteger
+import javax.xml.bind.annotation.*
+import javax.xml.bind.annotation.adapters.CollapsedStringAdapter
+import javax.xml.bind.annotation.adapters.NormalizedStringAdapter
+import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter
+import kotlin.math.min
+
+@XmlAccessorType(XmlAccessType.NONE)
+@XmlType(name = "", propOrder = ["header", "authSignature", "body"])
+@XmlRootElement(name = "ebicsResponse")
+class EbicsResponse {
+ @get:XmlAttribute(name = "Version", required = true)
+ @get:XmlJavaTypeAdapter(CollapsedStringAdapter::class)
+ lateinit var version: String
+
+ @get:XmlAttribute(name = "Revision")
+ var revision: Int? = null
+
+ @get:XmlElement(required = true)
+ lateinit var header: Header
+
+ @get:XmlElement(name = "AuthSignature", required = true)
+ lateinit var authSignature: SignatureType
+
+ @get:XmlElement(required = true)
+ lateinit var body: Body
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ @XmlType(name = "", propOrder = ["_static", "mutable"])
+ class Header {
+ @get:XmlElement(name = "static", required = true)
+ lateinit var _static: StaticHeaderType
+
+ @get:XmlElement(required = true)
+ lateinit var mutable: MutableHeaderType
+
+ @get:XmlAttribute(name = "authenticate", required = true)
+ var authenticate: Boolean = false
+ }
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ @XmlType(name = "", propOrder = ["dataTransfer", "returnCode", "timestampBankParameter"])
+ class Body {
+ @get:XmlElement(name = "DataTransfer")
+ var dataTransfer: DataTransferResponseType? = null
+
+ @get:XmlElement(name = "ReturnCode", required = true)
+ lateinit var returnCode: ReturnCode
+
+ @get:XmlElement(name = "TimestampBankParameter")
+ var timestampBankParameter: EbicsTypes.TimestampBankParameter? = null
+ }
+
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ @XmlType(
+ name = "",
+ propOrder = ["transactionPhase", "segmentNumber", "orderID", "returnCode", "reportText"]
+ )
+ class MutableHeaderType {
+ @get:XmlElement(name = "TransactionPhase", required = true)
+ @get:XmlSchemaType(name = "token")
+ lateinit var transactionPhase: EbicsTypes.TransactionPhaseType
+
+ @get:XmlElement(name = "SegmentNumber")
+ var segmentNumber: EbicsTypes.SegmentNumber? = null
+
+ @get:XmlElement(name = "OrderID")
+ @get:XmlJavaTypeAdapter(CollapsedStringAdapter::class)
+ @get:XmlSchemaType(name = "token")
+ var orderID: String? = null
+
+ @get:XmlElement(name = "ReturnCode", required = true)
+ @get:XmlJavaTypeAdapter(CollapsedStringAdapter::class)
+ @get:XmlSchemaType(name = "token")
+ lateinit var returnCode: String
+
+ @get:XmlElement(name = "ReportText", required = true)
+ @get:XmlJavaTypeAdapter(NormalizedStringAdapter::class)
+ @get:XmlSchemaType(name = "normalizedString")
+ lateinit var reportText: String
+ }
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ class OrderData {
+ @get:XmlValue
+ lateinit var value: String
+ }
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ class ReturnCode {
+ @get:XmlValue
+ @get:XmlJavaTypeAdapter(CollapsedStringAdapter::class)
+ lateinit var value: String
+
+ @get:XmlAttribute(name = "authenticate", required = true)
+ var authenticate: Boolean = false
+ }
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ @XmlType(name = "DataTransferResponseType", propOrder = ["dataEncryptionInfo", "orderData"])
+ class DataTransferResponseType {
+ @get:XmlElement(name = "DataEncryptionInfo")
+ var dataEncryptionInfo: EbicsTypes.DataEncryptionInfo? = null
+
+ @get:XmlElement(name = "OrderData", required = true)
+ lateinit var orderData: OrderData
+ }
+
+
+ @XmlAccessorType(XmlAccessType.NONE)
+ @XmlType(name = "ResponseStaticHeaderType", propOrder = ["transactionID", "numSegments"])
+ class StaticHeaderType {
+ @get:XmlElement(name = "TransactionID")
+ var transactionID: String? = null
+
+ @get:XmlElement(name = "NumSegments")
+ @get:XmlSchemaType(name = "positiveInteger")
+ var numSegments: BigInteger? = null
+ }
+
+ companion object {
+
+ fun createForUploadWithError(
+ errorText: String, errorCode: String, phase: EbicsTypes.TransactionPhaseType
+ ): EbicsResponse {
+ val resp = EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = EbicsResponse.Header().apply {
+ this.authenticate = true
+ this.mutable = EbicsResponse.MutableHeaderType().apply {
+ this.reportText = errorText
+ this.returnCode = errorCode
+ this.transactionPhase = phase
+ }
+ _static = EbicsResponse.StaticHeaderType()
+ }
+ this.authSignature = SignatureType()
+ this.body = EbicsResponse.Body().apply {
+ this.returnCode = EbicsResponse.ReturnCode().apply {
+ this.authenticate = true
+ this.value = errorCode
+ }
+ }
+ }
+ return resp
+ }
+
+ fun createForUploadInitializationPhase(transactionID: String, orderID: String): EbicsResponse {
+ return EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = Header().apply {
+ this.authenticate = true
+ this._static = StaticHeaderType().apply {
+ this.transactionID = transactionID
+ }
+ this.mutable = MutableHeaderType().apply {
+ this.transactionPhase =
+ EbicsTypes.TransactionPhaseType.INITIALISATION
+ this.orderID = orderID
+ this.reportText = "[EBICS_OK] OK"
+ this.returnCode = "000000"
+ }
+ }
+ this.authSignature = SignatureType()
+ this.body = Body().apply {
+ this.returnCode = ReturnCode().apply {
+ this.authenticate = true
+ this.value = "000000"
+ }
+ }
+ }
+ }
+
+ fun createForDownloadReceiptPhase(transactionID: String, positiveAck: Boolean): EbicsResponse {
+ return EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = Header().apply {
+ this.authenticate = true
+ this._static = StaticHeaderType().apply {
+ this.transactionID = transactionID
+ }
+ this.mutable = MutableHeaderType().apply {
+ this.transactionPhase =
+ EbicsTypes.TransactionPhaseType.RECEIPT
+ if (positiveAck) {
+ this.reportText = "[EBICS_DOWNLOAD_POSTPROCESS_DONE] Received positive receipt"
+ this.returnCode = "011000"
+ } else {
+ this.reportText = "[EBICS_DOWNLOAD_POSTPROCESS_SKIPPED] Received negative receipt"
+ this.returnCode = "011001"
+ }
+ }
+ }
+ this.authSignature = SignatureType()
+ this.body = Body().apply {
+ this.returnCode = ReturnCode().apply {
+ this.authenticate = true
+ this.value = "000000"
+ }
+ }
+ }
+ }
+
+ fun createForUploadTransferPhase(
+ transactionID: String,
+ segmentNumber: Int,
+ lastSegment: Boolean,
+ orderID: String
+ ): EbicsResponse {
+ return EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = Header().apply {
+ this.authenticate = true
+ this._static = StaticHeaderType().apply {
+ this.transactionID = transactionID
+ }
+ this.mutable = MutableHeaderType().apply {
+ this.transactionPhase =
+ EbicsTypes.TransactionPhaseType.TRANSFER
+ this.segmentNumber = EbicsTypes.SegmentNumber().apply {
+ this.value = BigInteger.valueOf(segmentNumber.toLong())
+ if (lastSegment) {
+ this.lastSegment = true
+ }
+ }
+ this.orderID = orderID
+ this.reportText = "[EBICS_OK] OK"
+ this.returnCode = "000000"
+ }
+ }
+ this.authSignature = SignatureType()
+ this.body = Body().apply {
+ this.returnCode = ReturnCode().apply {
+ this.authenticate = true
+ this.value = "000000"
+ }
+ }
+ }
+ }
+
+ /**
+ * @param requestedSegment requested segment as a 1-based index
+ */
+ fun createForDownloadTransferPhase(
+ transactionID: String,
+ numSegments: Int,
+ segmentSize: Int,
+ encodedData: String,
+ requestedSegment: Int
+ ): EbicsResponse {
+ return EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = Header().apply {
+ this.authenticate = true
+ this._static = StaticHeaderType().apply {
+ this.transactionID = transactionID
+ this.numSegments = BigInteger.valueOf(numSegments.toLong())
+ }
+ this.mutable = MutableHeaderType().apply {
+ this.transactionPhase =
+ EbicsTypes.TransactionPhaseType.TRANSFER
+ this.segmentNumber = EbicsTypes.SegmentNumber().apply {
+ this.lastSegment = numSegments == requestedSegment
+ this.value = BigInteger.valueOf(requestedSegment.toLong())
+ }
+ this.reportText = "[EBICS_OK] OK"
+ this.returnCode = "000000"
+ }
+ }
+ this.authSignature = SignatureType()
+ this.body = Body().apply {
+ this.returnCode = ReturnCode().apply {
+ this.authenticate = true
+ this.value = "000000"
+ }
+ this.dataTransfer = DataTransferResponseType().apply {
+ this.orderData = OrderData().apply {
+ val start = segmentSize * (requestedSegment - 1)
+ this.value = encodedData.substring(start, min(start + segmentSize, encodedData.length))
+ }
+ }
+ }
+ }
+ }
+
+ fun createForDownloadInitializationPhase(
+ transactionID: String,
+ numSegments: Int,
+ segmentSize: Int,
+ enc: CryptoUtil.EncryptionResult,
+ encodedData: String
+ ): EbicsResponse {
+ return EbicsResponse().apply {
+ this.version = "H004"
+ this.revision = 1
+ this.header = Header().apply {
+ this.authenticate = true
+ this._static = StaticHeaderType().apply {
+ this.transactionID = transactionID
+ this.numSegments = BigInteger.valueOf(numSegments.toLong())
+ }
+ this.mutable = MutableHeaderType().apply {
+ this.transactionPhase =
+ EbicsTypes.TransactionPhaseType.INITIALISATION
+ this.segmentNumber = EbicsTypes.SegmentNumber().apply {
+ this.lastSegment = (numSegments == 1)
+ this.value = BigInteger.valueOf(1)
+ }
+ this.reportText = "[EBICS_OK] OK"
+ this.returnCode = "000000"
+ }
+ }
+ this.authSignature = SignatureType()
+ this.body = Body().apply {
+ this.returnCode = ReturnCode().apply {
+ this.authenticate = true
+ this.value = "000000"
+ }
+ this.dataTransfer = DataTransferResponseType().apply {
+ this.dataEncryptionInfo = EbicsTypes.DataEncryptionInfo().apply {
+ this.authenticate = true
+ this.encryptionPubKeyDigest = EbicsTypes.PubKeyDigest()
+ .apply {
+ this.algorithm = "http://www.w3.org/2001/04/xmlenc#sha256"
+ this.version = "E002"
+ this.value = enc.pubKeyDigest
+ }
+ this.transactionKey = enc.encryptedTransactionKey
+ }
+ this.orderData = OrderData().apply {
+ this.value = encodedData.substring(0, min(segmentSize, encodedData.length))
+ }
+ }
+ }
+ }
+ }
+ }
+}