From 6862129449f60f49f376cedb9e094cbf1768441d Mon Sep 17 00:00:00 2001 From: Quentin Defenouillere Date: Thu, 24 Jan 2019 16:24:18 +0100 Subject: [PATCH] [cragr] Implemented history, coming and summaries for Cards MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This commit implements iter_history and iter_coming for deferred cards with the new API website of crédit agricole. Note that if there are several cards on the same parent account, it is not possible to figure out which summary belongs to which card so summaries are only fetched if the card is unique on its parent account. --- modules/cragr/api/browser.py | 71 +++++++++++++++++++++++++++++++++++- modules/cragr/api/pages.py | 3 +- 2 files changed, 71 insertions(+), 3 deletions(-) diff --git a/modules/cragr/api/browser.py b/modules/cragr/api/browser.py index 7148df53b2..f05e2f3395 100644 --- a/modules/cragr/api/browser.py +++ b/modules/cragr/api/browser.py @@ -23,13 +23,14 @@ from decimal import Decimal import re -from weboob.capabilities.bank import Account +from weboob.capabilities.bank import Account, Transaction from weboob.capabilities.base import empty, NotAvailable from weboob.browser import LoginBrowser, URL, need_login from weboob.exceptions import BrowserUnavailable, BrowserIncorrectPassword, ActionNeeded from weboob.browser.exceptions import ServerError from weboob.capabilities.bank import Loan from weboob.tools.capabilities.bank.iban import is_iban_valid +from weboob.tools.capabilities.bank.transactions import sorted_transactions from .pages import ( LoginPage, LoggedOutPage, KeypadPage, SecurityPage, ContractsPage, AccountsPage, AccountDetailsPage, @@ -242,6 +243,74 @@ def go_to_account_space(self, contract): @need_login def get_history(self, account, coming=False): + if account.type == Account.TYPE_CARD: + card_transactions = [] + self.go_to_account_space(account._contract) + # Deferred cards transactions have a specific JSON. + # Only three months of history available for cards. + value = 0 if coming else 1 + params = { + 'grandeFamilleCode': int(account._category), + 'compteIdx': int(account.parent._index), + 'carteIdx': int(account._index), + 'rechercheEncoursDebite': value + } + self.card_history.go(params=params) + for tr in self.page.iter_card_history(): + card_transactions.append(tr) + + # Before fetching card summaries, we must check if this card + # is unique on the parent account, otherwise it is impossible + # to know which summary corresponds to which card... + unique = True + for acc in self.all_accounts.values(): + if acc.type == Account.TYPE_CARD: + if (acc.parent == account.parent) and (acc.id != account.id): + unique = False + break + + if not coming and card_transactions and unique: + # Get card summaries from parent account + # until we reach the oldest card transaction + last_transaction = card_transactions[-1] + before_last_transaction = False + params = { + 'compteIdx': int(account.parent._index), + 'grandeFamilleCode': int(account.parent._category), + 'idDevise': str(account.parent.currency), + 'idElementContrat': str(account.parent._id_element_contrat), + } + self.history.go(params=params) + for tr in self.page.iter_history(): + if tr.date < last_transaction.date: + before_last_transaction = True + break + if tr.type == Transaction.TYPE_CARD_SUMMARY: + tr.amount = -tr.amount + card_transactions.append(tr) + + while self.page.has_next_page() and not before_last_transaction: + next_index = self.page.get_next_index() + params = { + 'grandeFamilleCode': int(account.parent._category), + 'compteIdx': int(account.parent._index), + 'idDevise': str(account.parent.currency), + 'startIndex': next_index, + 'count': 100, + } + self.history.go(params=params) + for tr in self.page.iter_history(): + if tr.date < last_transaction.date: + before_last_transaction = True + break + if tr.type == Transaction.TYPE_CARD_SUMMARY: + tr.amount = -tr.amount + card_transactions.append(tr) + + for tr in sorted_transactions(card_transactions): + yield tr + return + # These three parameters are required to get the transactions for non_card accounts if empty(account._index) or empty(account._category) or empty(account._id_element_contrat): return diff --git a/modules/cragr/api/pages.py b/modules/cragr/api/pages.py index b4839ddccf..194973e8d0 100644 --- a/modules/cragr/api/pages.py +++ b/modules/cragr/api/pages.py @@ -280,11 +280,10 @@ class item(ItemElement): klass = Transaction + obj_raw = Format('%s %s %s', CleanText(Dict('libelleTypeOperation')), CleanText(Dict('libelleOperation')), CleanText(Dict('libelleComplementaire'))) obj_label = Format('%s %s', CleanText(Dict('libelleTypeOperation')), CleanText(Dict('libelleOperation'))) obj_amount = Eval(float_to_decimal, Dict('montant')) obj_type = Map(CleanText(Dict('libelleTypeOperation')), TRANSACTION_TYPES, Transaction.TYPE_UNKNOWN) - # Needed to fetch deferred card summaries - obj__index = Dict('indexCarte') def obj_date(self): return dateutil.parser.parse(Dict('dateValeur')(self)) -- GitLab