support reverse charge
This commit is contained in:
@@ -2,6 +2,8 @@
|
|||||||
=======
|
=======
|
||||||
- #197 file attachments
|
- #197 file attachments
|
||||||
- Charges/Allowances CategoryCode improvement PR #198 Thanks to weclapp-dev
|
- Charges/Allowances CategoryCode improvement PR #198 Thanks to weclapp-dev
|
||||||
|
- support reverse charge
|
||||||
|
- support intra community supply also in product class, not only interface
|
||||||
|
|
||||||
2.0.1
|
2.0.1
|
||||||
=====
|
=====
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ import java.math.BigDecimal;
|
|||||||
public class Product implements IZUGFeRDExportableProduct {
|
public class Product implements IZUGFeRDExportableProduct {
|
||||||
protected String unit, name, description, sellerAssignedID, buyerAssignedID;
|
protected String unit, name, description, sellerAssignedID, buyerAssignedID;
|
||||||
protected BigDecimal VATPercent;
|
protected BigDecimal VATPercent;
|
||||||
|
protected boolean isReverseCharge=false;
|
||||||
|
protected boolean isIntraCommunitySupply=false;
|
||||||
|
|
||||||
/***
|
/***
|
||||||
* default constructor
|
* default constructor
|
||||||
@@ -54,6 +56,37 @@ public class Product implements IZUGFeRDExportableProduct {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isReverseCharge() {
|
||||||
|
return isReverseCharge;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isIntraCommunitySupply() {
|
||||||
|
return isIntraCommunitySupply;
|
||||||
|
}
|
||||||
|
|
||||||
|
/***
|
||||||
|
* sets reverse charge(=delivery to outside EU)
|
||||||
|
* @return fluent setter
|
||||||
|
*/
|
||||||
|
public Product setReverseCharge() {
|
||||||
|
isReverseCharge=true;
|
||||||
|
setVATPercent(BigDecimal.ZERO);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/***
|
||||||
|
* sets intra community supply(=delivery outside the country inside the EU)
|
||||||
|
* @return fluent setter
|
||||||
|
*/
|
||||||
|
public Product setIntraCommunitySupply() {
|
||||||
|
isIntraCommunitySupply=true;
|
||||||
|
setVATPercent(BigDecimal.ZERO);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getUnit() {
|
public String getUnit() {
|
||||||
return unit;
|
return unit;
|
||||||
|
|||||||
@@ -108,10 +108,16 @@ public interface IZUGFeRDExportableProduct {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
default boolean isReverseCharge() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
default String getTaxCategoryCode() {
|
default String getTaxCategoryCode() {
|
||||||
if (isIntraCommunitySupply()) {
|
if (isIntraCommunitySupply()) {
|
||||||
return "K";
|
return "K"; // within europe
|
||||||
} else if (getVATPercent().equals(new BigDecimal(0))) {
|
} else if (isReverseCharge()) {
|
||||||
|
return "AE"; // to out of europe...
|
||||||
|
} else if (getVATPercent().equals(BigDecimal.ZERO)) {
|
||||||
return "Z"; // zero rated goods
|
return "Z"; // zero rated goods
|
||||||
} else {
|
} else {
|
||||||
return "S"; // one of the "standard" rates (not neccessarily a default rate, even a deducted VAT is standard calculation)
|
return "S"; // one of the "standard" rates (not neccessarily a default rate, even a deducted VAT is standard calculation)
|
||||||
@@ -119,8 +125,11 @@ public interface IZUGFeRDExportableProduct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
default String getTaxExemptionReason() {
|
default String getTaxExemptionReason() {
|
||||||
if (isIntraCommunitySupply())
|
if (isIntraCommunitySupply()) {
|
||||||
return "Intra-community supply";
|
return "Intra-community supply";
|
||||||
|
} else if (isReverseCharge()) {
|
||||||
|
return "Reverse Charge";
|
||||||
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -45,6 +45,8 @@ public class ZF2PushTest extends TestCase {
|
|||||||
final String TARGET_RELATIVECHARGESALLOWANCESPDF = "./target/testout-ZF2PushRelativeChargesAllowances.pdf";
|
final String TARGET_RELATIVECHARGESALLOWANCESPDF = "./target/testout-ZF2PushRelativeChargesAllowances.pdf";
|
||||||
final String TARGET_ATTACHMENTSPDF = "./target/testout-ZF2PushAttachments.pdf";
|
final String TARGET_ATTACHMENTSPDF = "./target/testout-ZF2PushAttachments.pdf";
|
||||||
final String TARGET_PUSHEDGE = "./target/testout-ZF2PushEdge.pdf";
|
final String TARGET_PUSHEDGE = "./target/testout-ZF2PushEdge.pdf";
|
||||||
|
final String TARGET_INTRACOMMUNITYSUPPLYPDF = "./target/testout-ZF2PushIntraCommunitySupply.pdf";
|
||||||
|
final String TARGET_REVERSECHARGEPDF = "./target/testout-ZF2PushReverseCharge.pdf";
|
||||||
|
|
||||||
public void testPushExport() {
|
public void testPushExport() {
|
||||||
|
|
||||||
@@ -198,6 +200,108 @@ public class ZF2PushTest extends TestCase {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public void testIntraCommunitySupplyExport() {
|
||||||
|
|
||||||
|
String orgname = "Test company";
|
||||||
|
String number = "123";
|
||||||
|
String amountStr = "3.00";
|
||||||
|
BigDecimal amount = new BigDecimal(amountStr);
|
||||||
|
try (InputStream SOURCE_PDF = this.getClass()
|
||||||
|
.getResourceAsStream("/MustangGnuaccountingBeispielRE-20170509_505blanko.pdf");
|
||||||
|
|
||||||
|
ZUGFeRDExporterFromA1 ze = new ZUGFeRDExporterFromA1().setProducer("My Application")
|
||||||
|
.setCreator(System.getProperty("user.name")).setZUGFeRDVersion(2).setProfile("extended").ignorePDFAErrors()
|
||||||
|
.load(SOURCE_PDF)) {
|
||||||
|
// ze.setTransaction(new Invoice().setDueDate(new Date()).setIssueDate(new Date()).setDeliveryDate(new Date()).setSender(new TradeParty(orgname,"teststr", "55232","teststadt","DE")).setOwnTaxID("4711").setOwnVATID("DE0815").setRecipient(new TradeParty("Franz Müller", "teststr.12", "55232", "Entenhausen", "DE")).setNumber(number)
|
||||||
|
// .addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)), amount, new BigDecimal(1.0)).addAllowance(new Allowance().setPercent(new BigDecimal(50)))));
|
||||||
|
|
||||||
|
|
||||||
|
ze.setTransaction(new Invoice().setDueDate(new Date()).setIssueDate(new Date()).setDeliveryDate(new Date())
|
||||||
|
.setSender(new TradeParty(orgname, "teststr", "55232", "teststadt", "DE").addVATID("DE0815")).setOwnTaxID("4711")
|
||||||
|
.setRecipient(new TradeParty("Franz Müller", "teststr.12", "55232", "Entenhausen", "DE").addVATID("DE0816").setContact(new Contact("contact testname", "123456", "contact.testemail@example.org").setFax("0911623562")))
|
||||||
|
.setDeliveryAddress(new TradeParty("Franz Müller", "teststr.12", "55232", "Entenhausen", "DE").addVATID("DE0816"))
|
||||||
|
.setNumber(number)
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setIntraCommunitySupply(), amount, new BigDecimal(1.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setIntraCommunitySupply(), amount, new BigDecimal(1.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setIntraCommunitySupply(), amount, new BigDecimal(2.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setIntraCommunitySupply(), amount, new BigDecimal(1.0)))
|
||||||
|
);
|
||||||
|
|
||||||
|
String theXML = new String(ze.getProvider().getXML());
|
||||||
|
assertTrue(theXML.contains("<rsm:CrossIndustryInvoice"));
|
||||||
|
ze.export(TARGET_INTRACOMMUNITYSUPPLYPDF);
|
||||||
|
} catch (IOException e) {
|
||||||
|
fail("IOException should not be raised in testEdgeExport");
|
||||||
|
}
|
||||||
|
|
||||||
|
// now check the contents (like MustangReaderTest)
|
||||||
|
ZUGFeRDImporter zi = new ZUGFeRDImporter(TARGET_INTRACOMMUNITYSUPPLYPDF);
|
||||||
|
|
||||||
|
assertTrue(zi.getUTF8().contains("EUR"));
|
||||||
|
assertTrue(zi.getUTF8().contains("0911623562")); // fax number
|
||||||
|
|
||||||
|
// Reading ZUGFeRD
|
||||||
|
assertEquals("15.00", zi.getAmount());
|
||||||
|
assertEquals(zi.getHolder(), orgname);
|
||||||
|
assertEquals(zi.getForeignReference(), number);
|
||||||
|
try {
|
||||||
|
assertEquals(zi.getVersion(), 2);
|
||||||
|
} catch (Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testReverseChargeExport() {
|
||||||
|
|
||||||
|
String orgname = "Test company";
|
||||||
|
String number = "123";
|
||||||
|
String amountStr = "3.00";
|
||||||
|
BigDecimal amount = new BigDecimal(amountStr);
|
||||||
|
try (InputStream SOURCE_PDF = this.getClass()
|
||||||
|
.getResourceAsStream("/MustangGnuaccountingBeispielRE-20170509_505blanko.pdf");
|
||||||
|
|
||||||
|
ZUGFeRDExporterFromA1 ze = new ZUGFeRDExporterFromA1().setProducer("My Application")
|
||||||
|
.setCreator(System.getProperty("user.name")).setZUGFeRDVersion(2).setProfile("extended").ignorePDFAErrors()
|
||||||
|
.load(SOURCE_PDF)) {
|
||||||
|
// ze.setTransaction(new Invoice().setDueDate(new Date()).setIssueDate(new Date()).setDeliveryDate(new Date()).setSender(new TradeParty(orgname,"teststr", "55232","teststadt","DE")).setOwnTaxID("4711").setOwnVATID("DE0815").setRecipient(new TradeParty("Franz Müller", "teststr.12", "55232", "Entenhausen", "DE")).setNumber(number)
|
||||||
|
// .addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)), amount, new BigDecimal(1.0)).addAllowance(new Allowance().setPercent(new BigDecimal(50)))));
|
||||||
|
|
||||||
|
|
||||||
|
ze.setTransaction(new Invoice().setDueDate(new Date()).setIssueDate(new Date()).setDeliveryDate(new Date()).setSender(new TradeParty(orgname, "teststr", "55232", "teststadt", "DE").addVATID("DE0815")).setOwnTaxID("4711").setRecipient(new TradeParty("Franz Müller", "teststr.12", "55232", "Entenhausen", "DE").addVATID("DE0816").setContact(new Contact("contact testname", "123456", "contact.testemail@example.org").setFax("0911623562"))).setNumber(number)
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setReverseCharge(), amount, new BigDecimal(1.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setReverseCharge(), amount, new BigDecimal(1.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setReverseCharge(), amount, new BigDecimal(2.0)))
|
||||||
|
.addItem(new Item(new Product("Testprodukt", "", "C62", new BigDecimal(19)).setReverseCharge(), amount, new BigDecimal(1.0)))
|
||||||
|
);
|
||||||
|
|
||||||
|
String theXML = new String(ze.getProvider().getXML());
|
||||||
|
assertTrue(theXML.contains("<rsm:CrossIndustryInvoice"));
|
||||||
|
ze.export(TARGET_REVERSECHARGEPDF);
|
||||||
|
} catch (IOException e) {
|
||||||
|
fail("IOException should not be raised in testEdgeExport");
|
||||||
|
}
|
||||||
|
|
||||||
|
// now check the contents (like MustangReaderTest)
|
||||||
|
ZUGFeRDImporter zi = new ZUGFeRDImporter(TARGET_REVERSECHARGEPDF);
|
||||||
|
|
||||||
|
assertTrue(zi.getUTF8().contains("EUR"));
|
||||||
|
assertTrue(zi.getUTF8().contains("0911623562")); // fax number
|
||||||
|
|
||||||
|
// Reading ZUGFeRD
|
||||||
|
assertEquals("15.00", zi.getAmount());
|
||||||
|
assertEquals(zi.getHolder(), orgname);
|
||||||
|
assertEquals(zi.getForeignReference(), number);
|
||||||
|
try {
|
||||||
|
assertEquals(zi.getVersion(), 2);
|
||||||
|
} catch (Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
public void testChargesAllowancesExport() {
|
public void testChargesAllowancesExport() {
|
||||||
|
|
||||||
String orgname = "Test company";
|
String orgname = "Test company";
|
||||||
|
|||||||
Reference in New Issue
Block a user