Using now XPath to assert generated invoices

This commit is contained in:
dankito 2024-11-14 17:31:12 +01:00
parent a512456a48
commit 5aae0bfe77
4 changed files with 76 additions and 3 deletions

View File

@ -13,6 +13,7 @@ val mustangVersion: String by project
val klfVersion: String by project val klfVersion: String by project
val assertKVersion: String by project val assertKVersion: String by project
val xunitVersion: String by project
dependencies { dependencies {
implementation("org.mustangproject:library:$mustangVersion") implementation("org.mustangproject:library:$mustangVersion")
@ -23,6 +24,7 @@ dependencies {
testImplementation(kotlin("test")) testImplementation(kotlin("test"))
implementation("com.willowtreeapps.assertk:assertk:$assertKVersion") implementation("com.willowtreeapps.assertk:assertk:$assertKVersion")
testImplementation("org.xmlunit:xmlunit-core:$xunitVersion")
} }

View File

@ -1,9 +1,10 @@
package net.codinux.invoicing.creation package net.codinux.invoicing.creation
import assertk.assertThat import assertk.assertThat
import assertk.assertions.contains
import assertk.assertions.isNotEmpty import assertk.assertions.isNotEmpty
import net.codinux.invoicing.test.DataGenerator import net.codinux.invoicing.test.DataGenerator
import net.codinux.invoicing.test.XPathAsserter
import java.math.BigDecimal
import kotlin.test.Test import kotlin.test.Test
class EInvoiceCreatorTest { class EInvoiceCreatorTest {
@ -35,8 +36,43 @@ class EInvoiceCreatorTest {
private fun assertInvoiceXml(xml: String) { private fun assertInvoiceXml(xml: String) {
assertThat(xml).isNotEmpty() assertThat(xml).isNotEmpty()
assertThat(xml).contains("<ram:ID>${DataGenerator.InvoiceNumber}</ram:ID>") val asserter = XPathAsserter(xml)
assertThat(xml).contains("""<udt:DateTimeString format="102">${DataGenerator.InvoicingDate.toString().replace("-", "")}</udt:DateTimeString>""")
asserter.xpathHasValue("//rsm:ExchangedDocument/ram:ID", DataGenerator.InvoiceNumber)
asserter.xpathHasValue("//rsm:ExchangedDocument/ram:IssueDateTime/udt:DateTimeString", DataGenerator.InvoicingDate.toString().replace("-", ""))
val senderXPath = "//rsm:SupplyChainTradeTransaction/ram:ApplicableHeaderTradeAgreement/ram:SellerTradeParty"
assertParty(asserter, senderXPath, DataGenerator.SenderName, DataGenerator.SenderStreet, DataGenerator.SenderPostalCode, DataGenerator.SenderCity, DataGenerator.SenderVatId, DataGenerator.SenderEmail)
val receiverXPath = "//rsm:SupplyChainTradeTransaction/ram:ApplicableHeaderTradeAgreement/ram:BuyerTradeParty"
assertParty(asserter, receiverXPath, DataGenerator.RecipientName, DataGenerator.RecipientStreet, DataGenerator.RecipientPostalCode, DataGenerator.RecipientCity, DataGenerator.RecipientVatId, DataGenerator.RecipientEmail)
val lineItemXPath = "//rsm:SupplyChainTradeTransaction/ram:IncludedSupplyChainTradeLineItem"
assertLineItem(asserter, lineItemXPath, DataGenerator.ItemName, DataGenerator.ItemUnit, DataGenerator.ItemQuantity, DataGenerator.ItemPrice, DataGenerator.ItemVat, DataGenerator.ItemDescription)
}
private fun assertParty(asserter: XPathAsserter, partyXPath: String, name: String, street: String, postalCode: String, city: String, vatId: String, email: String) {
asserter.xpathHasValue("$partyXPath/ram:Name", name)
asserter.xpathHasValue("$partyXPath/ram:PostalTradeAddress/ram:LineOne", street)
asserter.xpathHasValue("$partyXPath/ram:PostalTradeAddress/ram:PostcodeCode", postalCode)
asserter.xpathHasValue("$partyXPath/ram:PostalTradeAddress/ram:CityName", city)
asserter.xpathHasValue("$partyXPath/ram:SpecifiedTaxRegistration/ram:ID", vatId)
asserter.xpathHasValue("$partyXPath/ram:URIUniversalCommunication/ram:URIID", email)
}
private fun assertLineItem(asserter: XPathAsserter, partyXPath: String, name: String, unit: String, quantity: BigDecimal, price: BigDecimal, vatPercentage: BigDecimal, description: String?) {
asserter.xpathHasValue("$partyXPath/ram:SpecifiedTradeProduct/ram:Name", name)
asserter.xpathHasValue("$partyXPath/ram:SpecifiedLineTradeDelivery/ram:BilledQuantity/@unitCode", unit)
asserter.xpathHasValue("$partyXPath/ram:SpecifiedLineTradeDelivery/ram:BilledQuantity", quantity, 4)
asserter.xpathHasValue("$partyXPath/ram:SpecifiedLineTradeSettlement/ram:SpecifiedTradeSettlementLineMonetarySummation/ram:LineTotalAmount", price, 2)
asserter.xpathHasValue("$partyXPath/ram:SpecifiedLineTradeSettlement/ram:ApplicableTradeTax/ram:RateApplicablePercent", vatPercentage, 2)
// asserter.xpathHasValue("$partyXPath/ram:URIUniversalCommunication/ram:URIID", description)
} }
} }

View File

@ -0,0 +1,34 @@
package net.codinux.invoicing.test
import assertk.assertThat
import assertk.assertions.isEqualTo
import net.codinux.log.Platform
import org.xmlunit.builder.Input
import org.xmlunit.xpath.JAXPXPathEngine
import java.math.BigDecimal
import java.math.RoundingMode
class XPathAsserter(
xml: String
) {
private val source = Input.fromString(xml).build()
private val xpathEngine = JAXPXPathEngine().apply {
setNamespaceContext(mapOf(
"rsm" to "urn:un:unece:uncefact:data:standard:CrossIndustryInvoice:100",
"ram" to "urn:un:unece:uncefact:data:standard:ReusableAggregateBusinessInformationEntity:100",
"udt" to "urn:un:unece:uncefact:data:standard:UnqualifiedDataType:100"
))
}
fun xpathHasValue(xpath: String, value: String) {
assertThat(xpathEngine.evaluate(xpath, source)).isEqualTo(value)
}
fun xpathHasValue(xpath: String, value: BigDecimal, countDecimalPlatform: Int = 2) {
xpathHasValue(xpath, value.setScale(countDecimalPlatform, RoundingMode.HALF_UP).toString())
}
}

View File

@ -10,3 +10,4 @@ mustangVersion=2.14.2
klfVersion=1.6.2 klfVersion=1.6.2
assertKVersion=0.28.1 assertKVersion=0.28.1
xunitVersion=2.10.0