support currencies
This commit is contained in:
parent
636c5c4bd5
commit
d91dad2b2b
17 changed files with 95 additions and 30 deletions
|
|
@ -72,15 +72,24 @@ class AccountsPage(BasePage):
|
|||
account_type = self.ACCOUNT_TYPES.get(div.text.strip(), Account.TYPE_UNKNOWN)
|
||||
|
||||
for tr in div.getnext().xpath('.//tbody/tr'):
|
||||
if not 'id' in tr.attrib:
|
||||
continue
|
||||
|
||||
args = dict(parse_qsl(tr.attrib['id']))
|
||||
tds = tr.findall('td')
|
||||
|
||||
if len(tds) < 4 or not 'identifiant' in args:
|
||||
self.logger.warning('Unable to parse an account')
|
||||
continue
|
||||
|
||||
account = Account()
|
||||
account.id = args['identifiant']
|
||||
account.label = u' '.join([u''.join([txt.strip() for txt in tds[1].itertext()]),
|
||||
u''.join([txt.strip() for txt in tds[2].itertext()])]).strip()
|
||||
account.type = account_type
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(u''.join([txt.strip() for txt in tds[3].itertext()])))
|
||||
balance = u''.join([txt.strip() for txt in tds[3].itertext()])
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(balance))
|
||||
account.currency = account.get_currency(balance)
|
||||
account._params = params.copy()
|
||||
account._params['dialogActionPerformed'] = 'SOLDE'
|
||||
account._params['attribute($SEL_$%s)' % tr.attrib['id'].split('_')[0]] = tr.attrib['id'].split('_', 1)[1]
|
||||
|
|
|
|||
|
|
@ -21,6 +21,7 @@
|
|||
import re
|
||||
from decimal import Decimal
|
||||
|
||||
from weboob.tools.capabilities.bank.transactions import FrenchTransaction
|
||||
from weboob.capabilities.bank import Account
|
||||
from weboob.capabilities.base import NotAvailable
|
||||
from weboob.tools.browser import BasePage, BrokenPageError, BrowserPasswordExpired
|
||||
|
|
@ -69,6 +70,7 @@ class AccountsList(BasePage):
|
|||
account.label = u''+a.text.strip()
|
||||
|
||||
tds = tr.findall('td')
|
||||
account.currency = account.get_currency(tds[3].find('a').text)
|
||||
account.balance = self._parse_amount(tds[3].find('a'))
|
||||
if tds[4].find('a') is not None:
|
||||
account.coming = self._parse_amount(tds[4].find('a'))
|
||||
|
|
@ -78,7 +80,7 @@ class AccountsList(BasePage):
|
|||
return account
|
||||
|
||||
def _parse_amount(self, elem):
|
||||
return Decimal(elem.text.replace('.', '').replace(',', '.').strip(u' \t\u20ac\xa0€\n\r'))
|
||||
return Decimal(FrenchTransaction.clean_amount(elem.text))
|
||||
|
||||
def get_list(self):
|
||||
l = []
|
||||
|
|
|
|||
|
|
@ -24,6 +24,7 @@ from decimal import Decimal
|
|||
from weboob.capabilities.bank import Account
|
||||
from weboob.tools.browser import BasePage
|
||||
from weboob.tools.misc import to_unicode
|
||||
from weboob.tools.capabilities.bank.transactions import FrenchTransaction
|
||||
|
||||
|
||||
class AccountsList(BasePage):
|
||||
|
|
@ -31,7 +32,6 @@ class AccountsList(BasePage):
|
|||
pass
|
||||
|
||||
def get_list(self):
|
||||
l = []
|
||||
for div in self.document.getiterator('div'):
|
||||
if div.attrib.get('id', '') == 'synthese-list':
|
||||
for tr in div.getiterator('tr'):
|
||||
|
|
@ -57,7 +57,8 @@ class AccountsList(BasePage):
|
|||
balance = td.text
|
||||
else:
|
||||
balance = span.text
|
||||
balance = balance.strip(u' \n\t€+').replace(',', '.').replace(' ', '')
|
||||
account.currency = account.get_currency(balance)
|
||||
balance = FrenchTransaction.clean_amount(balance)
|
||||
if balance != "":
|
||||
account.balance = Decimal(balance)
|
||||
else:
|
||||
|
|
@ -66,6 +67,4 @@ class AccountsList(BasePage):
|
|||
else:
|
||||
# because of some weird useless <tr>
|
||||
if account.id is not None:
|
||||
l.append(account)
|
||||
|
||||
return l
|
||||
yield account
|
||||
|
|
|
|||
|
|
@ -23,6 +23,7 @@ from decimal import Decimal
|
|||
from weboob.capabilities.bank import Account, AccountNotFound
|
||||
from weboob.tools.browser import BasePage
|
||||
from weboob.tools.misc import to_unicode
|
||||
from weboob.tools.capabilities.bank.transactions import FrenchTransaction
|
||||
|
||||
|
||||
__all__ = ['AccountList']
|
||||
|
|
@ -63,7 +64,8 @@ class AccountList(BasePage):
|
|||
tmp_balance = tmp[0].text
|
||||
|
||||
account.id = tmp_id
|
||||
account.balance = Decimal(''.join(tmp_balance.replace('.','').replace(',','.').split()))
|
||||
account.currency = account.get_currency(tmp_balance)
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(tmp_balance))
|
||||
self.account_list.append(account)
|
||||
|
||||
def get_account(self, id):
|
||||
|
|
|
|||
|
|
@ -84,7 +84,7 @@ class AccountsPage(BredBasePage):
|
|||
continue
|
||||
|
||||
try:
|
||||
amount = sum([Decimal(txt.strip(' EUR').replace(' ', '').replace(',', '.')) for txt in cols[-1].itertext() if len(txt.strip()) > 0])
|
||||
amount = sum([Decimal(FrenchTransaction.clean_amount(txt)) for txt in cols[-1].itertext() if len(txt.strip()) > 0])
|
||||
except InvalidOperation:
|
||||
continue
|
||||
|
||||
|
|
@ -117,6 +117,7 @@ class AccountsPage(BredBasePage):
|
|||
account.id = u'%s.%s' % (args['numero_compte'], args['numero_poste'])
|
||||
account.label = to_unicode(a.attrib.get('alt', a.text.strip()))
|
||||
account.balance = amount
|
||||
account.currency = [account.get_currency(txt) for txt in cols[-1].itertext() if len(txt.strip()) > 0][0]
|
||||
account._card_links = []
|
||||
accounts.append(account)
|
||||
|
||||
|
|
|
|||
|
|
@ -110,7 +110,8 @@ class IndexPage(BasePage):
|
|||
account.label = unicode(a.text.strip())
|
||||
account.type = account_type
|
||||
amount = u''.join([txt.strip() for txt in tds[-1].itertext()])
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(amount.rstrip(' EUR')))
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(amount))
|
||||
account.currency = account.get_currency(amount)
|
||||
yield account
|
||||
|
||||
def go_history(self, id):
|
||||
|
|
|
|||
|
|
@ -69,7 +69,8 @@ class AccountsPage(BasePage):
|
|||
continue
|
||||
|
||||
for i in (2,1):
|
||||
balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text.strip(' EUR'))
|
||||
balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text)
|
||||
currency = Account.get_currency(tr.getchildren()[i].text)
|
||||
if len(balance) > 0:
|
||||
break
|
||||
balance = Decimal(balance)
|
||||
|
|
@ -90,6 +91,7 @@ class AccountsPage(BasePage):
|
|||
account._card_links = []
|
||||
|
||||
account.balance = balance
|
||||
account.currency = currency
|
||||
|
||||
accounts[account.id] = account
|
||||
|
||||
|
|
|
|||
|
|
@ -114,6 +114,7 @@ class AccountsList(CragrBasePage):
|
|||
account.label = required_tokens['account_name']
|
||||
account.id = required_tokens['account_number']
|
||||
account.balance = FrenchTransaction.clean_amount(required_tokens['account_amount'])
|
||||
account.currency = account.get_currency(required_tokens['account_amount'])
|
||||
# we found almost all required information to create an account object
|
||||
self.logger.debug('Found account %s with number %s and balance = %.2f' % (account.label, account.id, account.balance))
|
||||
# we may have found the owner name too
|
||||
|
|
|
|||
|
|
@ -72,6 +72,7 @@ class AccountsPage(BasePage):
|
|||
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(tds[self.CPT_ROW_BALANCE].find("a").text))
|
||||
account.coming = Decimal(FrenchTransaction.clean_amount( tds[self.CPT_ROW_ENCOURS].find("a").text))
|
||||
account.currency = account.get_currency(tds[self.CPT_ROW_BALANCE].find("a").text)
|
||||
yield account
|
||||
|
||||
return
|
||||
|
|
|
|||
|
|
@ -69,7 +69,8 @@ class AccountsPage(BasePage):
|
|||
continue
|
||||
|
||||
for i in (2,1):
|
||||
balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text.strip(' EUR'))
|
||||
balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text)
|
||||
currency = Account.get_currency(tr.getchildren()[i].text)
|
||||
if len(balance) > 0:
|
||||
break
|
||||
balance = Decimal(balance)
|
||||
|
|
@ -90,6 +91,7 @@ class AccountsPage(BasePage):
|
|||
account._card_links = []
|
||||
|
||||
account.balance = balance
|
||||
account.currency = currency
|
||||
|
||||
accounts[account.id] = account
|
||||
|
||||
|
|
|
|||
|
|
@ -22,13 +22,31 @@ import re
|
|||
import datetime
|
||||
|
||||
from weboob.capabilities.bank import Account
|
||||
from weboob.tools.capabilities.bank.transactions import Transaction
|
||||
from weboob.tools.browser import BasePage#, BrokenPageError
|
||||
from weboob.capabilities import NotAvailable
|
||||
from weboob.tools.capabilities.bank.transactions import FrenchTransaction
|
||||
|
||||
|
||||
__all__ = ['AccountsList', 'AccountHistoryPage']
|
||||
|
||||
|
||||
class Transaction(FrenchTransaction):
|
||||
PATTERNS = [(re.compile(u'^(?P<category>CHEQUE)(?P<text>.*)'), FrenchTransaction.TYPE_CHECK),
|
||||
(re.compile('^(?P<category>FACTURE CARTE) DU (?P<dd>\d{2})(?P<mm>\d{2})(?P<yy>\d{2}) (?P<text>.*?)( CA?R?T?E? ?\d*X*\d*)?$'),
|
||||
FrenchTransaction.TYPE_CARD),
|
||||
(re.compile('^(?P<category>(PRELEVEMENT|TELEREGLEMENT|TIP)) (?P<text>.*)'),
|
||||
FrenchTransaction.TYPE_ORDER),
|
||||
(re.compile('^(?P<category>ECHEANCEPRET)(?P<text>.*)'), FrenchTransaction.TYPE_LOAN_PAYMENT),
|
||||
(re.compile('^(?P<category>RETRAIT DAB) (?P<dd>\d{2})/(?P<mm>\d{2})/(?P<yy>\d{2})( (?P<HH>\d+)H(?P<MM>\d+))? (?P<text>.*)'),
|
||||
FrenchTransaction.TYPE_WITHDRAWAL),
|
||||
(re.compile('^(?P<category>VIR(EMEN)?T? ((RECU|FAVEUR) TIERS|SEPA RECU)?)( /FRM)?(?P<text>.*)'),
|
||||
FrenchTransaction.TYPE_TRANSFER),
|
||||
(re.compile('^(?P<category>REMBOURST)(?P<text>.*)'), FrenchTransaction.TYPE_PAYBACK),
|
||||
(re.compile('^(?P<category>COMMISSIONS)(?P<text>.*)'), FrenchTransaction.TYPE_BANK),
|
||||
(re.compile('^(?P<text>(?P<category>REMUNERATION).*)'), FrenchTransaction.TYPE_BANK),
|
||||
(re.compile('^(?P<category>REMISE CHEQUES)(?P<text>.*)'), FrenchTransaction.TYPE_DEPOSIT),
|
||||
]
|
||||
|
||||
class AccountHistoryPage(BasePage):
|
||||
def get_operations(self, _id):
|
||||
"""history, see http://docs.weboob.org/api/capabilities/bank.html?highlight=transaction#weboob.capabilities.bank.Transaction"""
|
||||
|
|
@ -42,23 +60,23 @@ class AccountHistoryPage(BasePage):
|
|||
|
||||
for i in range(len(tables)):
|
||||
operation = Transaction(len(operations))
|
||||
operation.type = 0
|
||||
operation.category = NotAvailable
|
||||
|
||||
date_oper = tables[i].xpath("./td[2]/text()")[0]
|
||||
date_val = tables[i].xpath("./td[3]/text()")[0]
|
||||
label = tables[i].xpath("./td[4]/text()")[0]
|
||||
operation.label = operation.raw = unicode(label.strip())
|
||||
amount = tables[i].xpath("./td[5]/text() | ./td[6]/text()")
|
||||
operation.date = datetime.datetime.strptime(date_val, "%d/%m/%Y")
|
||||
|
||||
operation.parse(date=date_val, raw=label)
|
||||
operation.rdate = datetime.datetime.strptime(date_oper,"%d/%m/%Y")
|
||||
operation.type = 0
|
||||
|
||||
if amount[1] == u'\xa0':
|
||||
amount = amount[0].replace(u"\xa0", "").replace(",", ".").strip()
|
||||
amount = amount[0]
|
||||
else:
|
||||
amount = amount[1].replace(u"\xa0", "").replace(",", ".").strip()
|
||||
operation.amount = Decimal(amount)
|
||||
amount = amount[1]
|
||||
|
||||
operation.category = NotAvailable
|
||||
operation.set_amount(amount)
|
||||
|
||||
operations.append(operation)
|
||||
|
||||
|
|
@ -75,7 +93,8 @@ class AccountsList(BasePage):
|
|||
account.id = cpt.xpath("./span[1]/text()")[0].replace(u"\xa0", "").replace(',', '.').replace("EUR", "").replace("\n", "").replace("\t", "").replace(u"\xb0", '').replace(" ", "").replace('N', '')
|
||||
|
||||
# account balance
|
||||
account.balance = Decimal(cpt.xpath("./span[2]/text()")[0].replace("+", "").replace(u"\xa0", "").replace(',', '.').replace("EUR", "").replace("\n", "").replace("\t", "").replace(" ", ""))
|
||||
account.balance = Decimal(Transaction.clean_amount(cpt.xpath("./span[2]/text()")[0]))
|
||||
account.currency = account.get_currency(cpt.xpath("./span[2]/text()")[0])
|
||||
|
||||
# account coming TODO
|
||||
#mycomingval = cpt.xpath("../../following-sibling::*[1]/td[2]/a[@class='lien_synthese_encours']/span/text()")[0].replace(',', '.').replace("EUR", "").replace("\n", "").replace("\t", "").replace(u"\xa0", "")
|
||||
|
|
|
|||
|
|
@ -53,7 +53,8 @@ class AccountsListPage(BasePage):
|
|||
tag = tds[2].find('font')
|
||||
if tag is None:
|
||||
tag = tds[2]
|
||||
account.balance = Decimal(tag.text.replace('.','').replace(',','.').replace(' ', '').strip(u' \t\u20ac\xa0€\n\r'))
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(tag.text))
|
||||
account.currency = account.get_currency(tag.text)
|
||||
account.coming = NotAvailable
|
||||
|
||||
yield account
|
||||
|
|
|
|||
|
|
@ -24,6 +24,7 @@ import re
|
|||
from weboob.capabilities.bank import Account
|
||||
from weboob.capabilities.base import NotAvailable
|
||||
from weboob.tools.browser import BasePage
|
||||
from weboob.tools.capabilities.bank.transactions import FrenchTransaction
|
||||
|
||||
|
||||
__all__ = ['AccountsList']
|
||||
|
|
@ -47,7 +48,7 @@ class AccountsList(BasePage):
|
|||
linkbis = self.document.xpath(urltofind).pop()
|
||||
if linkbis.text == link.text:
|
||||
linkbis = self.document.xpath(urltofind)[1]
|
||||
account.balance = Decimal(linkbis.text.replace('.', '').\
|
||||
replace(' ', '').replace(',', '.'))
|
||||
account.balance = Decimal(FrenchTransaction.clean_amount(linkbis.text))
|
||||
account.currency = account.get_currency(linkbis.text)
|
||||
account.coming = NotAvailable
|
||||
yield account
|
||||
|
|
|
|||
|
|
@ -168,10 +168,11 @@ class AccountsPage(BasePage):
|
|||
if not div.text.strip():
|
||||
div = div.find('div')
|
||||
account.label=u''+div.text.strip()
|
||||
balance=a.text.replace(u"\u00A0",'').replace(' ','').replace('.','').replace('+','').replace(',','.').strip()
|
||||
balance = FrenchTransaction.clean_amount(a.text)
|
||||
if '-' in balance:
|
||||
balance='-'+balance.replace('-', '')
|
||||
account.balance=Decimal(balance)
|
||||
account.currency = account.get_currency(a.text)
|
||||
self.logger.debug('%s Type: %s' % (account.label, account._type))
|
||||
l.append(account)
|
||||
if link.startswith('/outil/UWCB/UWCBEncours'):
|
||||
|
|
@ -181,7 +182,7 @@ class AccountsPage(BasePage):
|
|||
|
||||
account = l[-1]
|
||||
|
||||
coming = a.text.replace(u"\u00A0",'').replace(' ','').replace('.','').replace('+','').replace(',','.').strip()
|
||||
coming = FrenchTransaction.clean_amount(a.text)
|
||||
if '-' in coming:
|
||||
coming = '-'+coming.replace('-', '')
|
||||
if not account.coming:
|
||||
|
|
|
|||
|
|
@ -64,7 +64,8 @@ class AccountsList(BasePage):
|
|||
elif td.attrib.get('headers', '') == 'Solde':
|
||||
balance = td.find('div').text
|
||||
if balance != None:
|
||||
balance = balance.replace(u'\xa0','').replace(',','.')
|
||||
account.currency = account.get_currency(balance)
|
||||
balance = FrenchTransaction.clean_amount(balance)
|
||||
account.balance = Decimal(balance)
|
||||
else:
|
||||
account.balance = Decimal(0)
|
||||
|
|
|
|||
|
|
@ -18,6 +18,7 @@
|
|||
# along with weboob. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
import re
|
||||
from datetime import date, datetime
|
||||
|
||||
from .base import CapBaseObject, Field, StringField, DateField, DecimalField, IntField, UserError
|
||||
|
|
@ -40,6 +41,25 @@ class TransferError(UserError):
|
|||
A transfer has failed.
|
||||
"""
|
||||
|
||||
class Currency:
|
||||
CUR_UNKNOWN = 0
|
||||
CUR_EUR = 1
|
||||
CUR_CHF = 2
|
||||
CUR_USD = 3
|
||||
|
||||
TXT2CUR = {u'€': CUR_EUR,
|
||||
u'EUR': CUR_EUR,
|
||||
u'CHF': CUR_CHF,
|
||||
u'$': CUR_USD,
|
||||
u'USD': CUR_USD,
|
||||
}
|
||||
|
||||
@classmethod
|
||||
def get_currency(klass, text):
|
||||
text = re.sub(u'[^A-Za-z€]', '', text)
|
||||
return klass.TXT2CUR.get(text, klass.CUR_UNKNOWN)
|
||||
|
||||
|
||||
class Recipient(CapBaseObject):
|
||||
"""
|
||||
Recipient of a transfer.
|
||||
|
|
@ -50,7 +70,7 @@ class Recipient(CapBaseObject):
|
|||
def __init__(self):
|
||||
CapBaseObject.__init__(self, 0)
|
||||
|
||||
class Account(Recipient):
|
||||
class Account(Recipient, Currency):
|
||||
"""
|
||||
Bank account.
|
||||
|
||||
|
|
@ -68,6 +88,7 @@ class Account(Recipient):
|
|||
type = IntField('Type of account', default=TYPE_UNKNOWN)
|
||||
balance = DecimalField('Balance on this bank account')
|
||||
coming = DecimalField('Coming balance')
|
||||
currency = IntField('Currency', default=Currency.CUR_UNKNOWN)
|
||||
|
||||
def __repr__(self):
|
||||
return u"<Account id=%r label=%r>" % (self.id, self.label)
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@
|
|||
|
||||
from decimal import Decimal
|
||||
import datetime
|
||||
import re
|
||||
|
||||
from weboob.capabilities.bank import Transaction
|
||||
from weboob.capabilities import NotAvailable
|
||||
|
|
@ -40,8 +41,8 @@ class FrenchTransaction(Transaction):
|
|||
"""
|
||||
Clean a string containing an amount.
|
||||
"""
|
||||
return text.replace(' ', '').replace('.','').replace(u'\xa0', '') \
|
||||
.replace(',','.').strip(u' \t\u20ac\xa0\x80€\n\rEUR')
|
||||
text = text.replace('.','').replace(',','.')
|
||||
return re.sub(u'[^\d\-\.]', '', text)
|
||||
|
||||
def set_amount(self, credit='', debit=''):
|
||||
"""
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue