-
Notifications
You must be signed in to change notification settings - Fork 625
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add new Hypothekarbank Lenzburg AG PDF-Importer
- Loading branch information
Showing
4 changed files
with
254 additions
and
0 deletions.
There are no files selected for viewing
70 changes: 70 additions & 0 deletions
70
...o/datatransfer/pdf/hypothekarbanklenzburgag/HypothekarbankLenzburgAGPDFExtractorTest.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,70 @@ | ||
package name.abuchen.portfolio.datatransfer.pdf.hypothekarbanklenzburgag; | ||
|
||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasAmount; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasCurrencyCode; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasDate; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasFees; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasGrossValue; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasIsin; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasName; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasNote; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasShares; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasSource; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasTaxes; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasTicker; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.hasWkn; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.purchase; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorMatchers.security; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorTestUtilities.countAccountTransactions; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorTestUtilities.countBuySell; | ||
import static name.abuchen.portfolio.datatransfer.ExtractorTestUtilities.countSecurities; | ||
import static org.hamcrest.CoreMatchers.hasItem; | ||
import static org.hamcrest.CoreMatchers.is; | ||
import static org.hamcrest.MatcherAssert.assertThat; | ||
import static org.hamcrest.collection.IsEmptyCollection.empty; | ||
|
||
import java.util.ArrayList; | ||
import java.util.List; | ||
|
||
import org.junit.Test; | ||
|
||
import name.abuchen.portfolio.datatransfer.Extractor.Item; | ||
import name.abuchen.portfolio.datatransfer.actions.AssertImportActions; | ||
import name.abuchen.portfolio.datatransfer.pdf.HypothekarbankLenzburgAGPDFExtractor; | ||
import name.abuchen.portfolio.datatransfer.pdf.PDFInputFile; | ||
import name.abuchen.portfolio.model.Client; | ||
|
||
@SuppressWarnings("nls") | ||
public class HypothekarbankLenzburgAGPDFExtractorTest | ||
{ | ||
@Test | ||
public void testWertpapierKauf01() | ||
{ | ||
HypothekarbankLenzburgAGPDFExtractor extractor = new HypothekarbankLenzburgAGPDFExtractor(new Client()); | ||
|
||
List<Exception> errors = new ArrayList<>(); | ||
|
||
List<Item> results = extractor.extract(PDFInputFile.loadTestCase(getClass(), "Kauf01.txt"), errors); | ||
|
||
assertThat(errors, empty()); | ||
assertThat(countSecurities(results), is(1L)); | ||
assertThat(countBuySell(results), is(1L)); | ||
assertThat(countAccountTransactions(results), is(0L)); | ||
assertThat(results.size(), is(2)); | ||
new AssertImportActions().check(results, "CHF"); | ||
|
||
// check security | ||
assertThat(results, hasItem(security( // | ||
hasIsin("IE000716YHJ7"), hasWkn("125615212"), hasTicker(null), // | ||
hasName("Accum Shs USD Inve FTSE All"), // | ||
hasCurrencyCode("CHF")))); | ||
|
||
// check buy sell transaction | ||
assertThat(results, hasItem(purchase( // | ||
hasDate("2024-03-14T00:00"), hasShares(720), // | ||
hasSource("Kauf01.txt"), // | ||
hasNote("Transaktion 61327806-0002"), // | ||
hasAmount("CHF", 3974.14), hasGrossValue("CHF", 3948.48), // | ||
hasTaxes("CHF", 5.92), hasFees("CHF", 19.74)))); | ||
} | ||
} |
31 changes: 31 additions & 0 deletions
31
...lio.tests/src/name/abuchen/portfolio/datatransfer/pdf/hypothekarbanklenzburgag/Kauf01.txt
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
PDFBox Version: 1.8.17 | ||
Portfolio Performance Version: 0.68.2 | ||
----------------------------------------- | ||
Hypothekarbank Lenzburg AG | ||
Bahnhofstrasse 2 | 5600 Lenzburg 1 | ||
Telefon +41 62 885 11 11 | [email protected] | www.hbl.ch | ||
BC 8307 | HYPLCH22 | CHE-105.779.532 MWST | ||
E-Post | ||
Herr | ||
Max Mustermann | ||
Musterstrasse 1 | ||
1234 Musterdorf | ||
Ihr Betreuerteam: Service Center / Tel. +41 43 508 03 76 | ||
Lenzburg, 14.03.2024 Seite 1 von 1 | ||
Börse / Kauf Portfolio 314.391.703 | ||
Transaktion 61327806-0002 | ||
Wir haben am 14.03.2024 an der BX Swiss für Sie gekauft | ||
720 Accum Shs USD Inve FTSE All Depotstelle 3500 | ||
Valor: 125615212 / IE000716YHJ7 | ||
Menge 720 Kurs CHF 5.484 CHF 3'948.48 | ||
Eidg. Umsatzabgabe CHF 5.92 | ||
Eigene Kommission (NEON) CHF 19.74 | ||
Belastung 314.391.304 Valuta 18.03.2024 CHF 3'974.14 | ||
Neon Konto - neon | ||
Die Titel buchen wir in Ihr Portfolio ein. | ||
Dieser Auftrag erfolgte ohne Beratung durch die Bank. | ||
Sofern für das gehandelte Finanzinstrument ein BIB vorhanden ist, wird Ihnen dieses auf unserer Internetseite unter | ||
https://www.hbl.ch/de/private/anlegen/basisinformationsblatt/ zur Verfügung gestellt. | ||
Freundliche Grüsse | ||
Hypothekarbank Lenzburg AG | ||
Anzeige ohne Unterschrift |
152 changes: 152 additions & 0 deletions
152
...lio/src/name/abuchen/portfolio/datatransfer/pdf/HypothekarbankLenzburgAGPDFExtractor.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,152 @@ | ||
package name.abuchen.portfolio.datatransfer.pdf; | ||
|
||
import static name.abuchen.portfolio.util.TextUtil.trim; | ||
|
||
import java.math.BigDecimal; | ||
|
||
import name.abuchen.portfolio.datatransfer.ExtractorUtils; | ||
import name.abuchen.portfolio.datatransfer.pdf.PDFParser.Block; | ||
import name.abuchen.portfolio.datatransfer.pdf.PDFParser.DocumentType; | ||
import name.abuchen.portfolio.datatransfer.pdf.PDFParser.Transaction; | ||
import name.abuchen.portfolio.model.BuySellEntry; | ||
import name.abuchen.portfolio.model.Client; | ||
import name.abuchen.portfolio.model.PortfolioTransaction; | ||
import name.abuchen.portfolio.money.Values; | ||
|
||
/** | ||
* @formatter:off | ||
* @implNote Hypothekarbank Lenzburg AG | ||
* | ||
* @implSpec The Valorennumber number is the WKN number with 5 to 9 letters. | ||
* @formatter:on | ||
*/ | ||
|
||
@SuppressWarnings("nls") | ||
public class HypothekarbankLenzburgAGPDFExtractor extends AbstractPDFExtractor | ||
{ | ||
public HypothekarbankLenzburgAGPDFExtractor(Client client) | ||
{ | ||
super(client); | ||
|
||
addBankIdentifier("Hypothekarbank Lenzburg AG"); | ||
|
||
addBuySellTransaction(); | ||
} | ||
|
||
@Override | ||
public String getLabel() | ||
{ | ||
return "Hypothekarbank Lenzburg AG"; | ||
} | ||
|
||
private void addBuySellTransaction() | ||
{ | ||
DocumentType type = new DocumentType("Wir haben am .* f.r Sie gekauft"); | ||
this.addDocumentTyp(type); | ||
|
||
Transaction<BuySellEntry> pdfTransaction = new Transaction<>(); | ||
|
||
Block firstRelevantLine = new Block("^Transaktion .*$"); | ||
type.addBlock(firstRelevantLine); | ||
firstRelevantLine.set(pdfTransaction); | ||
|
||
pdfTransaction // | ||
|
||
.subject(() -> { | ||
BuySellEntry portfolioTransaction = new BuySellEntry(); | ||
portfolioTransaction.setType(PortfolioTransaction.Type.BUY); | ||
return portfolioTransaction; | ||
}) | ||
|
||
// @formatter:off | ||
// Wir haben am 14.03.2024 an der BX Swiss für Sie gekauft | ||
// 720 Accum Shs USD Inve FTSE All Depotstelle 3500 | ||
// Valor: 125615212 / IE000716YHJ7 | ||
// Menge 720 Kurs CHF 5.484 CHF 3'948.48 | ||
// @formatter:on | ||
.section("name", "wkn", "isin", "currency") // | ||
.find("Wir haben am .* f.r Sie gekauft") //) | ||
.match("^.*[\\,'\\d]+ (?<name>.*) Depotstelle .*$") // | ||
.match("^Valor: (?<wkn>[A-Z0-9]{5,9}) \\/ (?<isin>[A-Z]{2}[A-Z0-9]{9}[0-9])$") | ||
.match("^Menge[\\s]{1,}[\\.'\\d]+ Kurs (?<currency>[\\w]{3})[\\s]{1,}[\\.'\\d]+[\\s]{1,}[\\w]{3}[\\s]{1,}[\\.'\\d]+$") // | ||
.assign((t, v) -> t.setSecurity(getOrCreateSecurity(v))) | ||
|
||
// @formatter:off | ||
// Menge 720 Kurs CHF 5.484 CHF 3'948.48 | ||
// @formatter:on | ||
.section("shares") // | ||
.match("^Menge[\\s]{1,}(?<shares>[\\.'\\d]+) Kurs.*$") // | ||
.assign((t, v) -> t.setShares(asShares(v.get("shares")))) | ||
|
||
// @formatter:off | ||
// Wir haben am 14.03.2024 an der BX Swiss für Sie gekauft | ||
// @formatter:on | ||
.section("date") // | ||
.match("^Wir haben am (?<date>[\\d]{2}\\.[\\d]{2}\\.[\\d]{4}).*$") // | ||
.assign((t, v) -> t.setDate(asDate(v.get("date")))) | ||
|
||
// @formatter:off | ||
// Belastung 314.391.304 Valuta 18.03.2024 CHF 3'974.14 | ||
// @formatter:on | ||
.section("currency", "amount") // | ||
.match("^Belastung .* (?<currency>[\\w]{3})[\\s]{1,}(?<amount>[\\.'\\d]+)$") // | ||
.assign((t, v) -> { | ||
t.setCurrencyCode(asCurrencyCode(v.get("currency"))); | ||
t.setAmount(asAmount(v.get("amount"))); | ||
}) | ||
|
||
// @formatter:off | ||
// Transaktion 61327806-0002 | ||
// @formatter:on | ||
.section("note").optional() // | ||
.match("^(?<note>Transaktion .*)$") // | ||
.assign((t, v) -> t.setNote(trim(v.get("note")))) | ||
|
||
.wrap(BuySellEntryItem::new); | ||
|
||
addTaxesSectionsTransaction(pdfTransaction, type); | ||
addFeesSectionsTransaction(pdfTransaction, type); | ||
} | ||
|
||
private <T extends Transaction<?>> void addTaxesSectionsTransaction(T transaction, DocumentType type) | ||
{ | ||
transaction // | ||
|
||
// @formatter:off | ||
// Eidg. Umsatzabgabe CHF 5.92 | ||
// @formatter:on | ||
.section("currency", "tax").optional() // | ||
.match("^Eidg\\. Umsatzabgabe (?<currency>[\\w]{3})[\\s]{1,}(?<tax>[\\.'\\d]+)$") // | ||
.assign((t, v) -> processTaxEntries(t, v, type)); | ||
} | ||
|
||
private <T extends Transaction<?>> void addFeesSectionsTransaction(T transaction, DocumentType type) | ||
{ | ||
transaction // | ||
|
||
// @formatter:off | ||
// Eigene Kommission (NEON) CHF 19.74 | ||
// @formatter:on | ||
.section("currency", "fee").optional() // | ||
.match("^Eigene Kommission.* (?<currency>[\\w]{3})[\\s]{1,}(?<fee>[\\.'\\d]+)$") // | ||
.assign((t, v) -> processFeeEntries(t, v, type)); | ||
} | ||
|
||
@Override | ||
protected long asAmount(String value) | ||
{ | ||
return ExtractorUtils.convertToNumberLong(value, Values.Amount, "de", "CH"); | ||
} | ||
|
||
@Override | ||
protected long asShares(String value) | ||
{ | ||
return ExtractorUtils.convertToNumberLong(value, Values.Share, "de", "CH"); | ||
} | ||
|
||
@Override | ||
protected BigDecimal asExchangeRate(String value) | ||
{ | ||
return ExtractorUtils.convertToNumberBigDecimal(value, Values.Share, "de", "CH"); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters