Implemented parsing user's supported tan procedures

This commit is contained in:
dankito 2019-10-15 22:47:17 +02:00 committed by dankito
parent c203c753f2
commit c857b874f7
5 changed files with 84 additions and 8 deletions

View File

@ -2,6 +2,7 @@ package net.dankito.fints.response
import net.dankito.fints.messages.MessageBuilderResult import net.dankito.fints.messages.MessageBuilderResult
import net.dankito.fints.messages.Separators import net.dankito.fints.messages.Separators
import net.dankito.fints.messages.datenelemente.implementierte.signatur.Sicherheitsfunktion
import net.dankito.fints.messages.segmente.id.ISegmentId import net.dankito.fints.messages.segmente.id.ISegmentId
import net.dankito.fints.messages.segmente.id.MessageSegmentId import net.dankito.fints.messages.segmente.id.MessageSegmentId
import net.dankito.fints.response.segments.* import net.dankito.fints.response.segments.*
@ -72,6 +73,11 @@ open class Response constructor(
open val supportedJobs: List<SupportedJob> open val supportedJobs: List<SupportedJob>
get() = receivedSegments.mapNotNull { it as? SupportedJob } get() = receivedSegments.mapNotNull { it as? SupportedJob }
open val supportedTanProceduresForUser: List<Sicherheitsfunktion>
get() = segmentFeedbacks.flatMap { it.feedbacks }
.filterIsInstance<SupportedTanProceduresForUserFeedback>()
.flatMap { it.supportedTanProcedures }
open fun <T : ReceivedSegment> getFirstSegmentById(id: ISegmentId): T? { open fun <T : ReceivedSegment> getFirstSegmentById(id: ISegmentId): T? {
return getFirstSegmentById(id.id) return getFirstSegmentById(id.id)

View File

@ -34,6 +34,10 @@ open class ResponseParser @JvmOverloads constructor(
val AllowedJobSegmentPattern = Pattern.compile("HI[A-Z]{3}S") val AllowedJobSegmentPattern = Pattern.compile("HI[A-Z]{3}S")
val FeedbackParametersSeparator = "; "
val SupportedTanProceduresForUserResponseCode = 3920
private val log = LoggerFactory.getLogger(ResponseParser::class.java) private val log = LoggerFactory.getLogger(ResponseParser::class.java)
} }
@ -124,12 +128,18 @@ open class ResponseParser @JvmOverloads constructor(
protected open fun parseFeedback(dataElementGroup: String): Feedback { protected open fun parseFeedback(dataElementGroup: String): Feedback {
val dataElements = getDataElements(dataElementGroup) val dataElements = getDataElements(dataElementGroup)
return Feedback( val responseCode = parseInt(dataElements[0])
parseInt(dataElements[0]), val referencedDataElement = parseStringToNullIfEmpty(dataElements[1])
parseString(dataElements[2]), val message = parseString(dataElements[2])
parseStringToNullIfEmpty(dataElements[1]),
if (dataElements.size > 3) parseStringToNullIfEmpty(dataElements[3]) else null if (responseCode == SupportedTanProceduresForUserResponseCode) {
) val supportedProcedures = parseCodeEnum(dataElements.subList(3, dataElements.size), Sicherheitsfunktion.values())
return SupportedTanProceduresForUserFeedback(supportedProcedures, message)
}
val parameter = if (dataElements.size > 3) dataElements.subList(3, dataElements.size).joinToString(FeedbackParametersSeparator) else null
return Feedback(responseCode, message, referencedDataElement, parameter)
} }
protected open fun parseSynchronization(segment: String, dataElementGroups: List<String>): ReceivedSynchronization { protected open fun parseSynchronization(segment: String, dataElementGroups: List<String>): ReceivedSynchronization {

View File

@ -33,9 +33,9 @@ open class Feedback(
* Segmentkopf+DE+GD:GD:GD:|GD|+DE+GD:GD : 3,4 * Segmentkopf+DE+GD:GD:GD:|GD|+DE+GD:GD : 3,4
* Segmentkopf+DE+GD:GD:GD:GD+DE+GD:|GD| : 5,2 * Segmentkopf+DE+GD:GD:GD:GD+DE+GD:|GD| : 5,2
*/ */
val referencedDataElement: String?, val referencedDataElement: String? = null,
val parameter: String? val parameter: String? = null
) { ) {

View File

@ -0,0 +1,10 @@
package net.dankito.fints.response.segments
import net.dankito.fints.messages.datenelemente.implementierte.signatur.Sicherheitsfunktion
import net.dankito.fints.response.ResponseParser
open class SupportedTanProceduresForUserFeedback(
val supportedTanProcedures: List<Sicherheitsfunktion>,
message: String
)
: Feedback(ResponseParser.SupportedTanProceduresForUserResponseCode, message)

View File

@ -3,6 +3,7 @@ package net.dankito.fints.response
import net.dankito.fints.FinTsTestBase import net.dankito.fints.FinTsTestBase
import net.dankito.fints.messages.datenelemente.implementierte.Dialogsprache import net.dankito.fints.messages.datenelemente.implementierte.Dialogsprache
import net.dankito.fints.messages.datenelemente.implementierte.HbciVersion import net.dankito.fints.messages.datenelemente.implementierte.HbciVersion
import net.dankito.fints.messages.datenelemente.implementierte.signatur.Sicherheitsfunktion
import net.dankito.fints.messages.datenelemente.implementierte.signatur.Sicherheitsverfahren import net.dankito.fints.messages.datenelemente.implementierte.signatur.Sicherheitsverfahren
import net.dankito.fints.messages.datenelemente.implementierte.signatur.VersionDesSicherheitsverfahrens import net.dankito.fints.messages.datenelemente.implementierte.signatur.VersionDesSicherheitsverfahrens
import net.dankito.fints.messages.datenelemente.implementierte.tan.TanProcess import net.dankito.fints.messages.datenelemente.implementierte.tan.TanProcess
@ -207,6 +208,55 @@ class ResponseParserTest : FinTsTestBase() {
} }
@Test
fun parseSegmentFeedback_AllowedUserTanProcedures() {
// when
val result = underTest.parse("HIRMS:4:2:4+3050::BPD nicht mehr aktuell, aktuelle Version enthalten.+3920::Zugelassene Zwei-Schritt-Verfahren für den Benutzer.:910:911:912:913+0020::Der Auftrag wurde ausgeführt.")
// then
assertCouldParseSegment(result, InstituteSegmentId.SegmentFeedback, 4, 2, 4)
assertThat(result.segmentFeedbacks).hasSize(1)
assertThat(result.supportedTanProceduresForUser).containsExactlyInAnyOrder(Sicherheitsfunktion.PIN_TAN_910,
Sicherheitsfunktion.PIN_TAN_911, Sicherheitsfunktion.PIN_TAN_912, Sicherheitsfunktion.PIN_TAN_913)
val segmentFeedback = result.segmentFeedbacks.first()
assertThat(segmentFeedback.feedbacks).hasSize(3)
val firstFeedback = segmentFeedback.feedbacks[0]
assertThat(firstFeedback.responseCode).isEqualTo(3050)
assertThat(firstFeedback.isSuccess).isFalse()
assertThat(firstFeedback.isWarning).isTrue()
assertThat(firstFeedback.isError).isFalse()
assertThat(firstFeedback.message).isEqualTo("BPD nicht mehr aktuell, aktuelle Version enthalten.")
assertThat(firstFeedback.parameter).isNull()
val secondFeedback = segmentFeedback.feedbacks[1]
assertThat(secondFeedback is SupportedTanProceduresForUserFeedback).isTrue()
assertThat((secondFeedback as SupportedTanProceduresForUserFeedback).supportedTanProcedures)
.containsExactlyInAnyOrder(Sicherheitsfunktion.PIN_TAN_910,Sicherheitsfunktion.PIN_TAN_911,
Sicherheitsfunktion.PIN_TAN_912, Sicherheitsfunktion.PIN_TAN_913)
assertThat(secondFeedback.responseCode).isEqualTo(3920)
assertThat(secondFeedback.isSuccess).isFalse()
assertThat(secondFeedback.isWarning).isTrue()
assertThat(secondFeedback.isError).isFalse()
assertThat(secondFeedback.message).isEqualTo("Zugelassene Zwei-Schritt-Verfahren für den Benutzer.")
assertThat(secondFeedback.parameter).isNull()
val thirdFeedback = segmentFeedback.feedbacks[2]
assertThat(thirdFeedback.responseCode).isEqualTo(20)
assertThat(thirdFeedback.isSuccess).isTrue()
assertThat(thirdFeedback.isWarning).isFalse()
assertThat(thirdFeedback.isError).isFalse()
assertThat(thirdFeedback.message).isEqualTo("Der Auftrag wurde ausgeführt.")
assertThat(thirdFeedback.parameter).isNull()
}
@Test @Test
fun parseSynchronization() { fun parseSynchronization() {