Skip to content

Commit

Permalink
feat(banks): add support for UOB
Browse files Browse the repository at this point in the history
  • Loading branch information
benjamin-awd committed Sep 8, 2024
1 parent 5a626c2 commit 6e815e0
Show file tree
Hide file tree
Showing 6 changed files with 77 additions and 6 deletions.
2 changes: 2 additions & 0 deletions src/monopoly/banks/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
from .maybank import Maybank
from .ocbc import Ocbc
from .standard_chartered import StandardChartered
from .uob import Uob

banks: list[Type["BankBase"]] = [
Citibank,
Expand All @@ -19,6 +20,7 @@
Maybank,
Ocbc,
StandardChartered,
Uob,
]

logger = logging.getLogger(__name__)
Expand Down
3 changes: 3 additions & 0 deletions src/monopoly/banks/uob/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from .uob import Uob

__all__ = ["Uob"]
49 changes: 49 additions & 0 deletions src/monopoly/banks/uob/uob.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
import logging
from re import compile as regex

from monopoly.config import StatementConfig
from monopoly.constants import (
BankNames,
DebitTransactionPatterns,
EntryType,
StatementBalancePatterns,
)
from monopoly.constants.date import ISO8601
from monopoly.identifiers import MetadataIdentifier

from ..base import BankBase

logger = logging.getLogger(__name__)


class Uob(BankBase):
credit_config = StatementConfig(
statement_type=EntryType.CREDIT,
bank_name=BankNames.UOB,
statement_date_pattern=regex(rf"Statement Date.*{ISO8601.DD_MMM_YYYY}"),
header_pattern=regex(r"(Description of Transaction.*Transaction Amount)"),
prev_balance_pattern=StatementBalancePatterns.UOB,
transaction_pattern=DebitTransactionPatterns.UOB,
multiline_transactions=True,
)

debit_config = StatementConfig(
statement_type=EntryType.DEBIT,
bank_name=BankNames.UOB,
statement_date_pattern=regex(rf"Period: .* to {ISO8601.DD_MMM_YYYY}"),
header_pattern=regex(r"(Date.*Description.*Withdrawals.*Deposits.*Balance)"),
transaction_pattern=DebitTransactionPatterns.UOB,
transaction_bound=170,
multiline_transactions=True,
)

identifiers = [
[
MetadataIdentifier(
format="PDF 1.5",
creator="Vault Rendering Engine",
producer="Rendering Engine",
),
]
]
statement_configs = [credit_config, debit_config]
6 changes: 3 additions & 3 deletions src/monopoly/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,9 +44,9 @@ class StatementConfig:
- `header_pattern` is a regex pattern that is used to find the 'header' line
of a statement, and determine if it is a debit or credit card statement.
- `transaction_bound` will cause transactions that have an amount past a certain
number of spaces will be ignored. For example, if `transaction_bound` = 5:
"01 NOV BALANCE B/F 190.77" (will be ignored)
"01 NOV YA KUN KAYA TOAST 12.00" (will be kept)
number of spaces will be ignored. For example, if `transaction_bound` = 32:
"01 NOV BALANCE B/F 190.77" (will be ignored)
"01 NOV YA KUN KAYA TOAST 12.00 " (will be kept)
"""

bank_name: BankNames | InternalBankNames
Expand Down
17 changes: 17 additions & 0 deletions src/monopoly/constants/statement.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ class BankNames(AutoEnum):
MAYBANK = auto()
OCBC = auto()
STANDARD_CHARTERED = auto()
UOB = auto()


class InternalBankNames(AutoEnum):
Expand Down Expand Up @@ -89,6 +90,10 @@ class StatementBalancePatterns(RegexEnum):
r"(?P<description>BALANCE FROM PREVIOUS STATEMENT?)\s+"
+ SharedPatterns.AMOUNT_EXTENDED_WITHOUT_EOL
)
UOB = (
r"(?P<description>PREVIOUS BALANCE?)\s+"
+ SharedPatterns.AMOUNT_EXTENDED_WITHOUT_EOL
)


class CreditTransactionPatterns(RegexEnum):
Expand Down Expand Up @@ -126,6 +131,12 @@ class CreditTransactionPatterns(RegexEnum):
+ r"(?:(?P<transaction_ref>Transaction\sRef\s\d+)?)\s+"
+ SharedPatterns.AMOUNT_EXTENDED
)
UOB = (
rf"(?P<posting_date>{ISO8601.DD_MMM})\s+"
rf"(?P<transaction_date>{ISO8601.DD_MMM})\s+"
+ SharedPatterns.DESCRIPTION
+ SharedPatterns.AMOUNT_EXTENDED
)


class DebitTransactionPatterns(RegexEnum):
Expand All @@ -150,3 +161,9 @@ class DebitTransactionPatterns(RegexEnum):
+ SharedPatterns.AMOUNT_EXTENDED_WITHOUT_EOL
+ SharedPatterns.BALANCE
)
UOB = (
rf"(?P<transaction_date>{ISO8601.DD_MMM})\s+"
+ SharedPatterns.DESCRIPTION
+ SharedPatterns.AMOUNT_EXTENDED_WITHOUT_EOL
+ SharedPatterns.BALANCE
)
6 changes: 3 additions & 3 deletions src/monopoly/generic/handler.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,14 @@


class GenericBank(BankBase):
identifiers = []
statement_configs = None

"""
Empty bank class with variables that can be populated by
the `GenericStatementHandler` class
"""

identifiers = []
statement_configs = None


class GenericStatementHandler(StatementHandler):
def __init__(self, bank: Type[BankBase], pages: list[PdfPage]):
Expand Down

0 comments on commit 6e815e0

Please sign in to comment.