예제 #1
0
파일: pages.py 프로젝트: P4ncake/weboob
    def _add_account(self, accounts, link, label, account_type, balance):
        info = self._get_account_info(link, accounts)
        if info is None:
            self.logger.warning('Unable to parse account %r: %r' % (label, link))
            return

        account = Account()
        account.id = info['id']
        if is_rib_valid(info['id']):
            account.iban = rib2iban(info['id'])
        account._info = info
        account.label = label
        account.type = self.ACCOUNT_TYPES.get(label, info['acc_type'] if 'acc_type' in info else account_type)

        balance = balance or self.get_balance(account)
        account.balance = Decimal(FrenchTransaction.clean_amount(balance)) if balance and balance is not NotAvailable else NotAvailable

        account.currency = account.get_currency(balance) if balance and balance is not NotAvailable else NotAvailable
        account._card_links = []

        if account._info['type'] == 'HISTORIQUE_CB' and account.id in accounts:
            a = accounts[account.id]
            if not a.coming:
                a.coming = Decimal('0.0')
            if account.balance and account.balance is not NotAvailable:
                a.coming += account.balance
            a._card_links.append(account._info)
            return

        accounts[account.id] = account
예제 #2
0
    def _add_account(self, accounts, link, label, account_type, balance):
        info = self._get_account_info(link)
        if info is None:
            self.logger.warning('Unable to parse account %r: %r' %
                                (label, link))
            return

        account = Account()
        account.id = info['id']
        account.iban = u'FR76' + info['id']
        account._info = info
        account.label = label
        account.type = info['acc_type'] if 'acc_type' in info else account_type
        account.balance = Decimal(FrenchTransaction.clean_amount(
            balance)) if balance else self.get_balance(account)
        account.currency = account.get_currency(balance)
        account._card_links = []

        if account._info['type'] == 'HISTORIQUE_CB' and account.id in accounts:
            a = accounts[account.id]
            if not a.coming:
                a.coming = Decimal('0.0')
            a.coming += account.balance
            a._card_links.append(account._info)
            return

        accounts[account.id] = account
예제 #3
0
    def get_accounts_list(self):
        for table in self.document.xpath('//div[@class="comptestabl"]/table'):
            try:
                account_type = self.ACCOUNT_TYPES[table.get('summary')]
                if not account_type:
                    account_type = self.ACCOUNT_TYPES[table.xpath(
                        './caption/text()')[0].strip()]
            except (IndexError, KeyError):
                account_type = Account.TYPE_UNKNOWN
            for tr in table.xpath('./tbody/tr'):
                cols = tr.findall('td')

                link = cols[0].find('a')
                if link is None:
                    continue

                a = Account()
                a.type = account_type
                a.id = unicode(
                    re.search('([A-Z\d]{4}[A-Z\d\*]{3}[A-Z\d]{4})',
                              link.attrib['title']).group(1))
                a.label = unicode(link.attrib['title'].replace(
                    '%s ' % a.id, ''))
                tmp_balance = self.parser.tocleanstring(cols[1])
                a.currency = a.get_currency(tmp_balance)
                a.balance = Decimal(Transaction.clean_amount(tmp_balance))
                a._card_links = []
                a._link_id = link.attrib['href']
                yield a
예제 #4
0
파일: pages.py 프로젝트: dasimon/weboob
 def get_loan_list(self):
     accounts = OrderedDict()
     # New website
     for table in self.document.xpath('//div[@class="panel"]'):
         title = table.getprevious()
         if title is None:
             continue
         account_type = self.ACCOUNT_TYPES.get(self.parser.tocleanstring(title), Account.TYPE_UNKNOWN)
         for tr in table.xpath('./table/tbody/tr[contains(@id,"MM_SYNTHESE_CREDITS") and contains(@id,"IdTrGlobal")]'):
             tds = tr.findall('td')
             if len(tds) == 0 :
                 continue
             for i in tds[0].xpath('.//a/strong'):
                 label = i.text.strip()
                 break
             balance = Decimal(FrenchTransaction.clean_amount(self.parser.tocleanstring(tds[-1])))
             account = Account()
             account.id = label.split(' ')[-1]
             account.label = unicode(label)
             account.type = account_type
             account.balance = -abs(balance)
             account.currency = account.get_currency(self.parser.tocleanstring(tds[-1]))
             account._card_links = []
             accounts[account.id] = account
     return accounts.itervalues()
예제 #5
0
파일: pages.py 프로젝트: dermorz/weboob
    def get_loan_list(self):
        accounts = OrderedDict()

        # Old website
        for tr in self.doc.xpath(
                '//table[@cellpadding="1"]/tr[not(@class) and td[a]]'):
            tds = tr.findall('td')

            account = Account()
            account.id = CleanText('./a')(tds[2]).split('-')[0].strip()
            account.label = CleanText('./a')(tds[2]).split('-')[-1].strip()
            account.type = Account.TYPE_LOAN
            account.balance = -CleanDecimal('./a', replace_dots=True)(tds[4])
            account.currency = account.get_currency(CleanText('./a')(tds[4]))
            accounts[account.id] = account

        if len(accounts) == 0:
            # New website
            for table in self.doc.xpath('//div[@class="panel"]'):
                title = table.getprevious()
                if title is None:
                    continue
                account_type = self.ACCOUNT_TYPES.get(
                    CleanText('.')(title), Account.TYPE_UNKNOWN)
                for tr in table.xpath(
                        './table/tbody/tr[contains(@id,"MM_SYNTHESE_CREDITS") and contains(@id,"IdTrGlobal")]'
                ):
                    tds = tr.findall('td')
                    if len(tds) == 0:
                        continue
                    for i in tds[0].xpath('.//a/strong'):
                        label = i.text.strip()
                        break
                    if len(tds) == 3 and Decimal(
                            FrenchTransaction.clean_amount(
                                CleanText('.')(tds[-2]))) and any(
                                    cls in Attr('.', 'id')(tr)
                                    for cls in ['dgImmo', 'dgConso']) == False:
                        # in case of Consumer credit or revolving credit, we substract avalaible amount with max amout
                        # to get what was spend
                        balance = Decimal(
                            FrenchTransaction.clean_amount(
                                CleanText('.')(tds[-2]))) - Decimal(
                                    FrenchTransaction.clean_amount(
                                        CleanText('.')(tds[-1])))
                    else:
                        balance = Decimal(
                            FrenchTransaction.clean_amount(
                                CleanText('.')(tds[-1])))
                    account = Account()
                    account.id = label.split(' ')[-1]
                    account.label = unicode(label)
                    account.type = account_type
                    account.balance = -abs(balance)
                    account.currency = account.get_currency(
                        CleanText('.')(tds[-1]))
                    account._card_links = []
                    accounts[account.id] = account

        return accounts.itervalues()
예제 #6
0
    def parse_table(self, what):
        tables = self.document.xpath("//table[@id='%s']" % what, smart_strings=False)
        if len(tables) < 1:
            return

        lines = tables[0].xpath(".//tbody/tr")
        for line in lines:
            account = Account()
            tmp = line.xpath("./td//a")[0]
            account.label = to_unicode(tmp.text)
            account._link_id = tmp.get("href")
            if "BourseEnLigne" in account._link_id:
                continue

            tmp = line.xpath("./td/span/strong")
            if len(tmp) >= 2:
                tmp_id = tmp[0].text
                tmp_balance = tmp[1].text
            else:
                tmp_id = line.xpath("./td//span")[1].text
                tmp_balance = tmp[0].text

            account.id = tmp_id
            account.currency = account.get_currency(tmp_balance)
            account.balance = Decimal(FrenchTransaction.clean_amount(tmp_balance))

            if account.id in self.accounts:
                a = self.accounts[account.id]
                a._card_links.append(account._link_id)
                if not a.coming:
                    a.coming = Decimal("0.0")
                a.coming += account.balance
            else:
                account._card_links = []
                self.accounts[account.id] = account
예제 #7
0
파일: pages.py 프로젝트: dasimon/weboob
    def _add_account(self, accounts, link, label, account_type, balance):
        info = self._get_account_info(link)
        if info is None:
            self.logger.warning('Unable to parse account %r: %r' % (label, link))
            return

        account = Account()
        account.id = info['id']
        account.iban = u'FR76' + info['id']
        account._info = info
        account.label = label
        account.type = info['acc_type'] if 'acc_type' in info else account_type
        account.balance = Decimal(FrenchTransaction.clean_amount(balance)) if balance else self.get_balance(account)
        account.currency = account.get_currency(balance)
        account._card_links = []

        if account._info['type'] == 'HISTORIQUE_CB' and account.id in accounts:
            a = accounts[account.id]
            if not a.coming:
                a.coming = Decimal('0.0')
            a.coming += account.balance
            a._card_links.append(account._info)
            return

        accounts[account.id] = account
예제 #8
0
파일: pages.py 프로젝트: yang2lalang/weboob
 def get_loan_list(self):
     accounts = OrderedDict()
     # New website
     for table in self.document.xpath('//div[@class="panel"]'):
         title = table.getprevious()
         if title is None:
             continue
         account_type = self.ACCOUNT_TYPES.get(
             self.parser.tocleanstring(title), Account.TYPE_UNKNOWN)
         for tr in table.xpath(
                 './table/tbody/tr[contains(@id,"MM_SYNTHESE_CREDITS") and contains(@id,"IdTrGlobal")]'
         ):
             tds = tr.findall('td')
             if len(tds) == 0:
                 continue
             for i in tds[0].xpath('.//a/strong'):
                 label = i.text.strip()
                 break
             balance = Decimal(
                 FrenchTransaction.clean_amount(
                     self.parser.tocleanstring(tds[-1])))
             account = Account()
             account.id = label.split(' ')[-1]
             account.label = unicode(label)
             account.type = account_type
             account.balance = -abs(balance)
             account.currency = account.get_currency(
                 self.parser.tocleanstring(tds[-1]))
             account._card_links = []
             accounts[account.id] = account
     return accounts.itervalues()
예제 #9
0
파일: pages.py 프로젝트: blckshrk/Weboob
    def get_list(self):
        accounts = OrderedDict()

        for tr in self.document.getiterator('tr'):
            first_td = tr.getchildren()[0]
            if (first_td.attrib.get('class', '') == 'i g' or first_td.attrib.get('class', '') == 'p g') \
               and first_td.find('a') is not None:

                a = first_td.find('a')
                link = a.get('href', '')
                if link.startswith('POR_SyntheseLst'):
                    continue

                url = urlparse(link)
                p = parse_qs(url.query)
                if not 'rib' in p:
                    continue

                for i in (2,1):
                    balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text)
                    currency = Account.get_currency(tr.getchildren()[i].text)
                    if len(balance) > 0:
                        break
                balance = Decimal(balance)

                id = p['rib'][0]
                if id in accounts:
                    account = accounts[id]
                    if not account.coming:
                        account.coming = Decimal('0.0')
                    account.coming += balance
                    account._card_links.append(link)
                    continue

                account = Account()
                account.id = id
                account.label = unicode(a.text).strip().lstrip(' 0123456789').title()
                account._link_id = link
                account._card_links = []

                # Find accounting amount
                page = self.browser.get_document(self.browser.openurl(link))
                coming = self.find_amount(page, u"Opérations à venir")
                accounting = self.find_amount(page, u"Solde comptable")

                if accounting is not None and accounting + (coming or Decimal('0')) != balance:
                    self.logger.warning('%s + %s != %s' % (accounting, coming, balance))

                if accounting is not None:
                    balance = accounting

                if coming is not None:
                    account.coming = coming
                account.balance = balance
                account.currency = currency

                accounts[account.id] = account

        return accounts.itervalues()
예제 #10
0
파일: pages.py 프로젝트: P4ncake/weboob
    def get_loan_list(self):
        accounts = OrderedDict()

        # Old website
        for tr in self.doc.xpath('//table[@cellpadding="1"]/tr[not(@class) and td[a]]'):
            tds = tr.findall('td')

            account = Account()
            account.id = CleanText('./a')(tds[2]).split('-')[0].strip()
            account.label = CleanText('./a')(tds[2]).split('-')[-1].strip()
            account.type = Account.TYPE_LOAN
            account.balance = -CleanDecimal('./a', replace_dots=True)(tds[4])
            account.currency = account.get_currency(CleanText('./a')(tds[4]))
            accounts[account.id] = account

        if len(accounts) == 0:
            # New website
            for table in self.doc.xpath('//div[@class="panel"]'):
                title = table.getprevious()
                if title is None:
                    continue
                account_type = self.ACCOUNT_TYPES.get(CleanText('.')(title), Account.TYPE_UNKNOWN)
                for tr in table.xpath('./table/tbody/tr[contains(@id,"MM_SYNTHESE_CREDITS") and contains(@id,"IdTrGlobal")]'):
                    tds = tr.findall('td')
                    if len(tds) == 0 :
                        continue
                    for i in tds[0].xpath('.//a/strong'):
                        label = i.text.strip()
                        break
                    if len(tds) == 3 and Decimal(FrenchTransaction.clean_amount(CleanText('.')(tds[-2]))) and any(cls in Attr('.', 'id')(tr) for cls in ['dgImmo', 'dgConso']) == False:
                        # in case of Consumer credit or revolving credit, we substract avalaible amount with max amout
                        # to get what was spend
                        balance = Decimal(FrenchTransaction.clean_amount(CleanText('.')(tds[-2]))) - Decimal(FrenchTransaction.clean_amount(CleanText('.')(tds[-1])))
                    else:
                        balance = Decimal(FrenchTransaction.clean_amount(CleanText('.')(tds[-1])))
                    account = Loan()
                    account.id = label.split(' ')[-1]
                    account.label = unicode(label)
                    account.type = account_type
                    account.balance = -abs(balance)
                    account.currency = account.get_currency(CleanText('.')(tds[-1]))
                    account._card_links = []
                    if "immobiliers" in CleanText('.')(title):
                        xp = './/div[contains(@id, "IdDivDetail")]/table/tbody/tr[contains(@id, "%s")]/td'
                        account.maturity_date = Date(CleanText(xp % 'IdDerniereEcheance'), dayfirst=True, default=NotAvailable)(tr)
                        account.total_amount = CleanDecimal(CleanText(xp % 'IdCapitalEmprunte'), replace_dots=True, default=NotAvailable)(tr)
                        account.subscription_date = Date(CleanText(xp % 'IdDateOuverture'), dayfirst=True, default=NotAvailable)(tr)
                        account.next_payment_date = Date(CleanText(xp % 'IdDateProchaineEcheance'), dayfirst=True, default=NotAvailable)(tr)
                        account.rate = CleanDecimal(CleanText(xp % 'IdTaux'), replace_dots=True, default=NotAvailable)(tr)
                        account.next_payment_amount = CleanDecimal(CleanText(xp % 'IdMontantEcheance'), replace_dots=True, default=NotAvailable)(tr)
                    elif "renouvelables" in CleanText('.')(title):
                        self.go_loans_conso(tr)
                        d = self.browser.loans_conso()
                        if d:
                            account.total_amount = d['contrat']['creditMaxAutorise']
                            account.available_amount = d['situationCredit']['disponible']
                            account.next_payment_amount = d['situationCredit']['mensualiteEnCours']
                    accounts[account.id] = account
        return accounts.values()
예제 #11
0
    def get_list(self):
        accounts = []
        for tr in self.document.getiterator('tr'):
            if not 'LGNTableRow' in tr.attrib.get('class', '').split():
                continue

            account = Account()
            for td in tr.getiterator('td'):
                if td.attrib.get('headers', '') == 'TypeCompte':
                    a = td.find('a')
                    if a is None:
                        break
                    account.label = unicode(a.find("span").text)
                    for pattern, actype in self.TYPES.iteritems():
                        if account.label.startswith(pattern):
                            account.type = actype
                    account._link_id = a.get('href', '')

                elif td.attrib.get('headers', '') == 'NumeroCompte':
                    id = td.text
                    id = id.replace(u'\xa0','')
                    account.id = id

                elif td.attrib.get('headers', '') == 'Libelle':
                    pass

                elif td.attrib.get('headers', '') == 'Solde':
                    div = td.xpath('./div[@class="Solde"]')
                    if len(div) > 0:
                        balance = self.parser.tocleanstring(div[0])
                        if len(balance) > 0 and balance not in ('ANNULEE', 'OPPOSITION'):
                            try:
                                account.balance = Decimal(FrenchTransaction.clean_amount(balance))
                            except InvalidOperation:
                                raise BrokenPageError('Unable to parse balance %r' % balance)
                            account.currency = account.get_currency(balance)
                        else:
                            account.balance = NotAvailable

            if not account.label or empty(account.balance):
                continue

            if 'CARTE_' in account._link_id:
                ac = accounts[0]
                ac._card_links.append(account._link_id)
                if not ac.coming:
                    ac.coming = Decimal('0.0')
                ac.coming += account.balance
            else:
                account._card_links = []
                accounts.append(account)
        return iter(accounts)
예제 #12
0
파일: pages.py 프로젝트: Boussadia/weboob
    def get_list(self):
        accounts = []

        for tr in self.document.xpath('//table[@class="compteTable"]/tr'):
            if not tr.attrib.get('class', '').startswith('ligne_'):
                continue

            cols = tr.findall('td')

            if len(cols) < 2:
                continue

            try:
                amount = sum([Decimal(FrenchTransaction.clean_amount(txt)) for txt in cols[-1].itertext() if len(txt.strip()) > 0])
            except InvalidOperation:
                continue

            a = cols[0].find('a')
            if a is None:
                # this line is a cards line. attach it on the first account.
                if len(accounts) == 0:
                    self.logger.warning('There is a card link but no accounts!')
                    continue

                for a in cols[0].xpath('.//li/a'):
                    args = self.js2args(a.attrib['href'])
                    if not 'numero_compte' in args or not 'numero_poste' in args:
                        self.logger.warning('Card link with strange args: %s' % args)
                        continue

                    accounts[0]._card_links.append('%s.%s' % (args['numero_compte'], args['numero_poste']))
                    if not accounts[0].coming:
                        accounts[0].coming = Decimal('0.0')
                    accounts[0].coming += amount
                continue

            args = self.js2args(a.attrib['href'])

            if not 'numero_compte' in args or not 'numero_poste' in args:
                self.logger.warning('Account link for %r with strange args: %s' % (a.attrib.get('alt', a.text), args))
                continue

            account = Account()
            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)

        return accounts
예제 #13
0
    def get_list(self):
        accounts = []
        for tr in self.document.getiterator('tr'):
            if not 'LGNTableRow' in tr.attrib.get('class', '').split():
                continue

            account = Account()
            for td in tr.getiterator('td'):
                if td.attrib.get('headers', '') == 'TypeCompte':
                    a = td.find('a')
                    if a is None:
                        break
                    account.label = unicode(a.find("span").text)
                    account._link_id = a.get('href', '')

                elif td.attrib.get('headers', '') == 'NumeroCompte':
                    id = td.text
                    id = id.replace(u'\xa0','')
                    account.id = id

                elif td.attrib.get('headers', '') == 'Libelle':
                    pass

                elif td.attrib.get('headers', '') == 'Solde':
                    div = td.xpath('./div[@class="Solde"]')
                    if len(div) > 0:
                        balance = self.parser.tocleanstring(div[0])
                        if len(balance) > 0 and balance not in ('ANNULEE', 'OPPOSITION'):
                            try:
                                account.balance = Decimal(FrenchTransaction.clean_amount(balance))
                            except InvalidOperation:
                                raise BrokenPageError('Unable to parse balance %r' % balance)
                            account.currency = account.get_currency(balance)
                        else:
                            account.balance = NotAvailable

            if not account.label or empty(account.balance):
                continue

            if 'CARTE_' in account._link_id:
                ac = accounts[0]
                ac._card_links.append(account._link_id)
                if not ac.coming:
                    ac.coming = Decimal('0.0')
                ac.coming += account.balance
            else:
                account._card_links = []
                accounts.append(account)
        return iter(accounts)
예제 #14
0
    def get_accounts_list(self):
        for tr in self.document.xpath('//div[@class="comptestabl"]/table/tbody/tr'):
            cols = tr.findall('td')

            link = cols[0].find('a')
            if link is None:
                continue

            a = Account()
            a.id, a.label = map(unicode, link.attrib['title'].split(' ', 1))
            tmp_balance = self.parser.tocleanstring(cols[1])
            a.currency = a.get_currency(tmp_balance)
            a.balance = Decimal(Transaction.clean_amount(tmp_balance))
            a._card_links = []
            a._link_id = link.attrib['href']
            yield a
예제 #15
0
    def parse_table(self, what, actype=Account.TYPE_UNKNOWN):
        tables = self.document.xpath("//table[@id='%s']" % what,
                                     smart_strings=False)
        if len(tables) < 1:
            return

        lines = tables[0].xpath(".//tbody/tr")
        for line in lines:
            account = Account()
            tmp = line.xpath("./td//a")[0]
            account.label = to_unicode(tmp.text)
            account.type = actype
            account._link_id = tmp.get("href")
            if 'BourseEnLigne' in account._link_id:
                account.type = Account.TYPE_MARKET

            tmp = line.xpath("./td/span/strong")
            if len(tmp) >= 2:
                tmp_id = tmp[0].text
                tmp_balance = tmp[1].text
            else:
                tmp_id = line.xpath("./td//span")[1].text
                tmp_balance = tmp[0].text

            account.id = tmp_id
            account.currency = account.get_currency(tmp_balance)
            account.balance = Decimal(
                FrenchTransaction.clean_amount(tmp_balance))

            if account.id in self.accounts:
                a = self.accounts[account.id]
                a._card_links.append(account._link_id)
                if not a.coming:
                    a.coming = Decimal('0.0')
                a.coming += account.balance
            else:
                account._card_links = []
                self.accounts[account.id] = account

                page = self.browser.get_page(
                    self.browser.openurl(
                        self.browser.buildurl(
                            '/voscomptes/canalXHTML/comptesCommun/imprimerRIB/init-imprimer_rib.ea',
                            ('compte.numero', account.id))))
                account.iban = page.get_iban()
예제 #16
0
파일: pages.py 프로젝트: eirmag/weboob
    def get_list(self):
        accounts = OrderedDict()

        for tr in self.document.getiterator('tr'):
            first_td = tr.getchildren()[0]
            if (first_td.attrib.get('class', '') == 'i g' or first_td.attrib.get('class', '') == 'p g') \
               and first_td.find('a') is not None:

                a = first_td.find('a')
                link = a.get('href', '')
                if link.startswith('POR_SyntheseLst'):
                    continue

                url = urlparse(link)
                p = parse_qs(url.query)
                if not 'rib' in p:
                    continue

                for i in (2,1):
                    balance = FrenchTransaction.clean_amount(tr.getchildren()[i].text.strip(' EUR'))
                    if len(balance) > 0:
                        break
                balance = Decimal(balance)

                id = p['rib'][0]
                if id in accounts:
                    account = accounts[id]
                    if not account.coming:
                        account.coming = Decimal('0.0')
                    account.coming += balance
                    account._card_links.append(link)
                    continue

                account = Account()
                account.id = id
                account.label = unicode(a.text).strip().lstrip(' 0123456789').title()
                account._link_id = link
                account._card_links = []

                account.balance = balance

                accounts[account.id] = account

        return accounts.itervalues()
예제 #17
0
    def get_list(self):
        account = None

        for cpt in self.document.xpath(
                '//a[@class="synthese_id_compte" or @class="synthese_carte_differe"]'
        ):
            url_to_parse = cpt.xpath('@href')[0].replace("\n", "")  # link
            # account._link_id = lien vers historique d'un compte (courant ou livret)
            if '/mes-comptes/livret/' in url_to_parse:
                compte_id_re = re.compile(r'.*\?(.*)$')
                link_id = '/fr/prive/mes-comptes/livret/consulter-situation/consulter-solde.jsp?%s' % \
                    (compte_id_re.search(url_to_parse).groups()[0])
            else:
                link_id = url_to_parse

            number = cpt.xpath('./span[@class="synthese_numero_compte"]')
            if len(number) == 0:
                account._card_links.append(link_id)
                continue

            account = Account()
            account.id = self.parser.tocleanstring(number[0]).replace(
                u'N°', '')

            try:
                balance = self.parser.tocleanstring(
                    cpt.xpath('./span[contains(@class, "synthese_solde")]')[0])
            except IndexError:
                continue

            account.balance = Decimal(Transaction.clean_amount(balance))
            account.currency = account.get_currency(balance)
            account._link_id = link_id
            account._card_links = []
            account.label = (' '.join([
                CleanText.clean(part) for part in cpt.xpath('./text()')
            ])).strip(' - ').strip()

            for pattern, type in self.ACCOUNT_TYPES.iteritems():
                if pattern in account._link_id:
                    account.type = type

            yield account
예제 #18
0
    def get_list(self):
        accounts = []
        for tr in self.document.getiterator('tr'):
            tds = tr.findall('td')
            if len(tds) != 3 or tds[0].find('a') is None or tds[0].find('a').attrib.get('class', '') != 'flecheM':
                continue

            account = Account()
            account.id = tds[1].text.strip()

            a = tds[0].findall('a')[-1]
            account.label = unicode(a.text.strip())
            account._link_id = a.attrib['href']

            balance = u''.join([txt.strip() for txt in tds[2].itertext()])
            account.balance = Decimal(FrenchTransaction.clean_amount(balance))

            # check account type
            m = re.search('(\w+)_IdPrestation', account._link_id)
            account_type = None
            if m:
                account_type = m.group(1)
                if account_type != 'CPT':
                    account.id += '.%s' % account_type

            if account_type == 'CB':
                accounts[0]._card_links.append(account._link_id)
                if not accounts[0].coming:
                    accounts[0].coming = Decimal('0.0')
                accounts[0].coming += account.balance
                continue

            if account_type != 'CPT':
                # Don't support other kind of account histories.
                account._link_id = None

            account.currency = account.get_currency(tds[1].text)
            account._card_links = []

            accounts.append(account)

        return iter(accounts)
예제 #19
0
    def parse_table(self, what, actype=Account.TYPE_UNKNOWN):
        tables = self.document.xpath("//table[@id='%s']" % what, smart_strings=False)
        if len(tables) < 1:
            return

        lines = tables[0].xpath(".//tbody/tr")
        for line in lines:
            account = Account()
            tmp = line.xpath("./td//a")[0]
            account.label = to_unicode(tmp.text)
            account.type = actype
            account._link_id = tmp.get("href")
            if 'BourseEnLigne' in account._link_id:
                account.type = Account.TYPE_MARKET

            tmp = line.xpath("./td/span/strong")
            if len(tmp) >= 2:
                tmp_id = tmp[0].text
                tmp_balance = tmp[1].text
            else:
                tmp_id = line.xpath("./td//span")[1].text
                tmp_balance = tmp[0].text

            account.id = tmp_id
            account.currency = account.get_currency(tmp_balance)
            account.balance = Decimal(FrenchTransaction.clean_amount(tmp_balance))

            if account.id in self.accounts:
                a = self.accounts[account.id]
                a._card_links.append(account._link_id)
                if not a.coming:
                    a.coming = Decimal('0.0')
                a.coming += account.balance
            else:
                account._card_links = []
                self.accounts[account.id] = account

                page = self.browser.get_page(self.browser.openurl(self.browser.buildurl('/voscomptes/canalXHTML/comptesCommun/imprimerRIB/init-imprimer_rib.ea', ('compte.numero', account.id))))
                account.iban = page.get_iban()
예제 #20
0
    def get_list(self):
        accounts = []
        for tr in self.document.getiterator('tr'):
            if not 'LGNTableRow' in tr.attrib.get('class', '').split():
                continue

            account = Account()
            for td in tr.getiterator('td'):
                if td.attrib.get('headers', '') == 'TypeCompte':
                    a = td.find('a')
                    account.label = unicode(a.find("span").text)
                    account._link_id = a.get('href', '')

                elif td.attrib.get('headers', '') == 'NumeroCompte':
                    id = td.text
                    id = id.replace(u'\xa0','')
                    account.id = id

                elif td.attrib.get('headers', '') == 'Libelle':
                    pass

                elif td.attrib.get('headers', '') == 'Solde':
                    balance = td.find('div').text
                    if balance != None:
                        balance = balance.replace(u'\xa0','').replace(',','.')
                        account.balance = Decimal(balance)
                    else:
                        account.balance = Decimal(0)

            if 'CARTE_' in account._link_id:
                ac = accounts[0]
                ac._card_links.append(account._link_id)
                if not ac.coming:
                    ac.coming = Decimal('0.0')
                ac.coming += account.balance
            else:
                account._card_links = []
                accounts.append(account)
        return iter(accounts)
예제 #21
0
파일: pro.py 프로젝트: nojhan/weboob-devel
    def get_accounts_list(self):
        for table in self.document.xpath('//div[@class="comptestabl"]/table'):
            try:
                account_type = self.ACCOUNT_TYPES[table.xpath('./caption/text()')[0].strip()]
            except (IndexError,KeyError):
                account_type = Account.TYPE_UNKNOWN
            for tr in table.xpath('./tbody/tr'):
                cols = tr.findall('td')

                link = cols[0].find('a')
                if link is None:
                    continue

                a = Account()
                a.type = account_type
                a.id, a.label = map(unicode, link.attrib['title'].split(' ', 1))
                tmp_balance = self.parser.tocleanstring(cols[1])
                a.currency = a.get_currency(tmp_balance)
                a.balance = Decimal(Transaction.clean_amount(tmp_balance))
                a._card_links = []
                a._link_id = link.attrib['href']
                yield a
예제 #22
0
    def parse_table(self, what, actype=Account.TYPE_UNKNOWN):
        tables = self.document.xpath("//table[@id='%s']" % what,
                                     smart_strings=False)
        if len(tables) < 1:
            return

        lines = tables[0].xpath(".//tbody/tr")
        for line in lines:
            account = Account()
            tmp = line.xpath("./td//a")[0]
            account.label = to_unicode(tmp.text)
            account.type = actype
            account._link_id = tmp.get("href")
            if 'BourseEnLigne' in account._link_id:
                account.type = Account.TYPE_MARKET

            tmp = line.xpath("./td/span/strong")
            if len(tmp) >= 2:
                tmp_id = tmp[0].text
                tmp_balance = tmp[1].text
            else:
                tmp_id = line.xpath("./td//span")[1].text
                tmp_balance = tmp[0].text

            account.id = tmp_id
            account.currency = account.get_currency(tmp_balance)
            account.balance = Decimal(
                FrenchTransaction.clean_amount(tmp_balance))

            if account.id in self.accounts:
                a = self.accounts[account.id]
                a._card_links.append(account._link_id)
                if not a.coming:
                    a.coming = Decimal('0.0')
                a.coming += account.balance
            else:
                account._card_links = []
                self.accounts[account.id] = account
예제 #23
0
    def get_list(self):
        account = None

        for cpt in self.document.xpath('//a[@class="synthese_id_compte" or @class="synthese_carte_differe"]'):
            url_to_parse = cpt.xpath('@href')[0].replace("\n", "")  # link
            # account._link_id = lien vers historique d'un compte (courant ou livret)
            if '/mes-comptes/livret/' in url_to_parse:
                compte_id_re = re.compile(r'.*\?(.*)$')
                link_id = '/fr/prive/mes-comptes/livret/consulter-situation/consulter-solde.jsp?%s' % \
                    (compte_id_re.search(url_to_parse).groups()[0])
            else:
                link_id = url_to_parse

            number = cpt.xpath('./span[@class="synthese_numero_compte"]')
            if len(number) == 0:
                account._card_links.append(link_id)
                continue

            account = Account()
            account.id = self.parser.tocleanstring(number[0]).replace(u'N°', '')

            try:
                balance = self.parser.tocleanstring(cpt.xpath('./span[contains(@class, "synthese_solde")]')[0])
            except IndexError:
                continue

            account.balance = Decimal(Transaction.clean_amount(balance))
            account.currency = account.get_currency(balance)
            account._link_id = link_id
            account._card_links = []
            account.label = (' '.join([CleanText.clean(part) for part in cpt.xpath('./text()')])).strip(' - ').strip()

            for pattern, type in self.ACCOUNT_TYPES.iteritems():
                if pattern in account._link_id:
                    account.type = type

            yield account
예제 #24
0
파일: pages.py 프로젝트: dermorz/weboob
    def _add_account(self, accounts, link, label, account_type, balance):
        info = self._get_account_info(link, accounts)
        if info is None:
            self.logger.warning('Unable to parse account %r: %r' %
                                (label, link))
            return

        account = Account()
        account.id = info['id']
        if is_rib_valid(info['id']):
            account.iban = rib2iban(info['id'])
        account._info = info
        account.label = label
        account.type = self.ACCOUNT_TYPES.get(
            label, info['acc_type'] if 'acc_type' in info else account_type)

        balance = balance or self.get_balance(account)
        account.balance = Decimal(
            FrenchTransaction.clean_amount(balance)
        ) if balance and balance is not NotAvailable else NotAvailable

        account.currency = account.get_currency(
            balance
        ) if balance and balance is not NotAvailable else NotAvailable
        account._card_links = []

        if account._info['type'] == 'HISTORIQUE_CB' and account.id in accounts:
            a = accounts[account.id]
            if not a.coming:
                a.coming = Decimal('0.0')
            if account.balance and account.balance is not NotAvailable:
                a.coming += account.balance
            a._card_links.append(account._info)
            return

        accounts[account.id] = account
예제 #25
0
    def get_accounts_list(self):
        for table in self.document.xpath('//div[@class="comptestabl"]/table'):
            try:
                account_type = self.ACCOUNT_TYPES[table.xpath(
                    './caption/text()')[0].strip()]
            except (IndexError, KeyError):
                account_type = Account.TYPE_UNKNOWN
            for tr in table.xpath('./tbody/tr'):
                cols = tr.findall('td')

                link = cols[0].find('a')
                if link is None:
                    continue

                a = Account()
                a.type = account_type
                a.id, a.label = map(unicode,
                                    link.attrib['title'].split(' ', 1))
                tmp_balance = self.parser.tocleanstring(cols[1])
                a.currency = a.get_currency(tmp_balance)
                a.balance = Decimal(Transaction.clean_amount(tmp_balance))
                a._card_links = []
                a._link_id = link.attrib['href']
                yield a
예제 #26
0
    def get_list(self):
        accounts = []

        for tr in self.document.xpath('//table[@class="compteTable"]/tr'):
            if not tr.attrib.get('class', '').startswith('ligne_'):
                continue

            cols = tr.findall('td')

            if len(cols) < 2:
                continue

            try:
                amount = sum([
                    Decimal(FrenchTransaction.clean_amount(txt))
                    for txt in cols[-1].itertext() if len(txt.strip()) > 0
                ])
            except InvalidOperation:
                continue

            a = cols[0].find('a')
            if a is None:
                # this line is a cards line. attach it on the first account.
                if len(accounts) == 0:
                    self.logger.warning(
                        'There is a card link but no accounts!')
                    continue

                for a in cols[0].xpath('.//li/a'):
                    args = self.js2args(a.attrib['href'])
                    if not 'numero_compte' in args or not 'numero_poste' in args:
                        self.logger.warning('Card link with strange args: %s' %
                                            args)
                        continue

                    accounts[0]._card_links.append(
                        '%s.%s' %
                        (args['numero_compte'], args['numero_poste']))
                    if not accounts[0].coming:
                        accounts[0].coming = Decimal('0.0')
                    accounts[0].coming += amount
                continue

            args = self.js2args(a.attrib['href'])

            if not 'numero_compte' in args or not 'numero_poste' in args:
                self.logger.warning(
                    'Account link for %r with strange args: %s' %
                    (a.attrib.get('alt', a.text), args))
                continue

            account = Account()
            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)

        return accounts
예제 #27
0
파일: pages.py 프로젝트: dasimon/weboob
    def get_list(self):
        accounts = []

        for block in self.document.xpath('//div[@class="pave"]/div'):
            head_type = block.xpath('./div/span[@class="accGroupLabel"]')[0].text.strip()
            account_type = self.ACCOUNT_TYPES.get(head_type, Account.TYPE_UNKNOWN)
            for tr in block.cssselect('ul li.tbord_account'):
                id = tr.attrib.get('id', '')
                if id.find('contratId') != 0:
                    self.logger.warning('Unable to parse contract ID: %r' % id)
                    continue
                id = id[id.find('contratId')+len('contratId'):]

                link = tr.cssselect('span.accountLabel a')[0]
                balance = Decimal(FrenchTransaction.clean_amount(tr.cssselect('span.accountTotal')[0].text))

                if id.endswith('CRT'):
                    account = accounts[-1]
                    account._card_links.append(link.attrib['href'])
                    if not account.coming:
                        account.coming = Decimal('0.0')
                    account.coming += balance
                    continue

                account = Account()
                account.id = id
                account.label = unicode(link.text.strip())
                account.type = account_type
                account.balance = balance
                account.currency = account.get_currency(tr.cssselect('span.accountDev')[0].text)
                account._link = link.attrib['href']
                account._card_links = []
                accounts.append(account)

        if len(accounts) == 0:
            # Sometimes, accounts are only in javascript...
            for script in self.document.xpath('//script'):
                text = script.text
                if text is None:
                    continue
                if 'remotePerso' not in text:
                    continue

                account = None
                card_account = None
                attribs = {}
                account_type = Account.TYPE_UNKNOWN
                for line in text.split('\n'):
                    line = line.strip()
                    m = re.match("data.libelle = '(.*)';", line)
                    if m:
                        account_type = self.ACCOUNT_TYPES.get(m.group(1), Account.TYPE_UNKNOWN)
                    elif line == 'var remotePerso = new Object;':
                        account = Account()
                    elif account is not None:
                        m = re.match("remotePerso.(\w+) = '?(.*?)'?;", line)
                        if m:
                            attribs[m.group(1)] = m.group(2)
                        elif line.startswith('listProduitsGroup'):
                            account.id = attribs['refContrat']

                            account.label = attribs['libelle']
                            account.type = account_type
                            account.balance = Decimal(FrenchTransaction.clean_amount(attribs['soldeDateOpeValeurFormatted']))
                            account.currency = account.get_currency(attribs['codeDevise'])
                            account._link = 'tbord.do?id=%s&%s' % (attribs['id'], self.browser.SESSION_PARAM)
                            account._card_links = []

                            if account.id.endswith('CRT'):
                                if not len(accounts):
                                    card_account = account
                                else:
                                    a = accounts[-1]
                                    a._card_links.append(account._link)
                                    if not a.coming:
                                        a.coming = Decimal('0.0')
                                    a.coming += account.balance
                            else:
                                if 'COURANT' in account.label:
                                    account.type = account.TYPE_CHECKING
                                elif account.id.endswith('TTR'):
                                    account.type = account.TYPE_MARKET
                                elif re.match('^\d+C$', account.id):
                                    account.type = account.TYPE_LIFE_INSURANCE
                                elif re.match('^\d+PRT$', account.id):
                                    account.type = account.TYPE_LOAN
                                elif not account.type:
                                    account.type = account.TYPE_SAVINGS

                                if card_account:
                                    account._card_links.append(card_account._link)
                                    if not account.coming:
                                        account.coming = Decimal('0.0')
                                    account.coming += card_account.balance
                                    card_account = None
                                accounts.append(account)
                            account = None

        return accounts
예제 #28
0
    def get_list(self):
        accounts = []

        for cpt in self.doc.xpath(
                '//div[contains(@class, " compte") and not(contains(@class, "compte_selected"))]'
        ):

            # ignore auto assurance accounts
            if 'aut' in cpt.get('class'):
                continue

            account = Account()
            account._history_link = Link(
                './ul/li/a[contains(@id, "consulter_solde") '
                'or contains(@id, "historique") '
                'or contains(@id, "assurance_vie_operations")]')(cpt)

            # this is to test if there is a redirection to a form for recently created profiles
            if len(accounts) == 0:
                message = self.browser.open(
                    account._history_link).page.doc.xpath(
                        '//div[@id="as_renouvellementMIFID.do_"]')
                if message:
                    raise ActionNeeded(
                        CleanText('./div[contains(text(), "Bonjour")]')(
                            message[0]))

            number = RawText('./a[contains(@class, "numero_compte")]')(
                cpt).replace(u'N° ', '')

            account.id = CleanText(None).filter(number).replace(u'N°', '')

            account._card_links = []
            card_link = Link('./ul/li/a[contains(text(), "Carte bancaire")]',
                             default='')(cpt)
            if len(card_link) > 0:
                account._card_links.append(card_link)

            account.label = CleanText(
                './a[contains(@class, "numero_compte")]/@title')(cpt)

            for pattern, type in self.ACCOUNT_TYPES.iteritems():
                if pattern in account._history_link:
                    account.type = type
                    break

            if account.type in {
                    Account.TYPE_PEA, Account.TYPE_MARKET,
                    Account.TYPE_LIFE_INSURANCE
            }:
                account._investment_link = Link(
                    './ul/li/a[contains(@id, "portefeuille")]')(cpt)
                balance = self.browser.open(
                    account._investment_link).page.get_balance(account.type)
                if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                    self.browser.cache["investments"][account.id] = list(
                        self.browser.open(
                            account._investment_link).page.get_investments(
                                account))
            else:
                balance = self.browser.open(
                    account._history_link).page.get_balance()

            if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                account.currency = self.browser.open(
                    account._investment_link).page.get_currency()
            else:
                account.currency = account.get_currency(balance)
            account.balance = CleanDecimal(None,
                                           replace_dots=True).filter(balance)

            if account.type in (Account.TYPE_CHECKING, Account.TYPE_SAVINGS):
                # Need a token sent by SMS to customers
                account.iban = NotAvailable

            if (account.label, account.id, account.balance) not in [
                (a.label, a.id, a.balance) for a in accounts
            ]:
                accounts.append(account)
        return iter(accounts)
예제 #29
0
파일: pages.py 프로젝트: hugues/weboob
    def get_list(self):
        accounts = OrderedDict()

        for tr in self.document.getiterator('tr'):
            first_td = tr.getchildren()[0]
            if (first_td.attrib.get('class', '') == 'i g' or first_td.attrib.get('class', '') == 'p g') \
               and first_td.find('a') is not None:

                a = first_td.find('a')
                link = a.get('href', '')
                if link.startswith('POR_SyntheseLst'):
                    continue

                url = urlparse(link)
                p = parse_qs(url.query)
                if not 'rib' in p:
                    continue

                for i in (2, 1):
                    balance = FrenchTransaction.clean_amount(
                        tr.getchildren()[i].text)
                    currency = Account.get_currency(tr.getchildren()[i].text)
                    if len(balance) > 0:
                        break
                balance = Decimal(balance)

                id = p['rib'][0]
                if id in accounts:
                    account = accounts[id]
                    if not account.coming:
                        account.coming = Decimal('0.0')
                    account.coming += balance
                    account._card_links.append(link)
                    continue

                account = Account()
                account.id = id
                account.label = unicode(
                    a.text).strip().lstrip(' 0123456789').title()
                account._link_id = link
                account._card_links = []

                # Find accounting amount
                page = self.browser.get_document(self.browser.openurl(link))
                coming = self.find_amount(page, u"Opérations à venir")
                accounting = self.find_amount(page, u"Solde comptable")

                if accounting is not None and accounting + (
                        coming or Decimal('0')) != balance:
                    self.logger.warning('%s + %s != %s' %
                                        (accounting, coming, balance))

                if accounting is not None:
                    balance = accounting

                if coming is not None:
                    account.coming = coming
                account.balance = balance
                account.currency = currency

                accounts[account.id] = account

        return accounts.itervalues()
예제 #30
0
    def get_list(self):
        accounts = []

        for cpt in self.doc.xpath('//div[contains(@class, " compte") and not(contains(@class, "compte_selected"))]'):

            # ignore auto assurance accounts
            if 'aut' in cpt.get('class'):
                continue

            account = Account()
            account._history_link = Link('./ul/li/a[contains(@id, "consulter_solde") '
                                         'or contains(@id, "historique") '
                                         'or contains(@id, "contrat") '
                                         'or contains(@id, "assurance_vie_operations")]')(cpt)

            # this is to test if access to the accounts info is blocked for different reasons
            page = self.browser.open(account._history_link).page
            if isinstance(page, LoanPage):
                account = Loan()

            account._history_link = Link('./ul/li/a[contains(@id, "consulter_solde") '
                                         'or contains(@id, "historique") '
                                         'or contains(@id, "contrat") '
                                         'or contains(@id, "assurance_vie_operations")]')(cpt)
            if isinstance(page, LoanPage):
                account.id = CleanText('(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]')(cpt)
                account.label = CleanText('(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]')(cpt)
                account.type = Account.TYPE_LOAN
                account_history_page = page
                account.total_amount = account_history_page.get_total_amount()
                account.next_payment_amount = account_history_page.get_next_payment_amount()
                account.next_payment_date = account_history_page.get_next_payment_date()
                account.account_label = account_history_page.get_account_label()
                account.subscription_date = account_history_page.get_subscription_date()
                account.maturity_date = account_history_page.get_maturity_date()

            if len(accounts) == 0:
                global_error_message = page.doc.xpath('//div[@id="as_renouvellementMIFID.do_"]/div[contains(text(), "Bonjour")] '
                                                      '| //div[@id="as_afficherMessageBloquantMigration.do_"]//div[@class="content_message"] '
                                                      '| //p[contains(text(), "Et si vous faisiez de Fortuneo votre banque principale")] '
                                                      '| //div[@id="as_renouvellementMotDePasse.do_"]//p[contains(text(), "votre mot de passe")]'
                                                      '| //div[@id="as_afficherSecuriteForteOTPIdentification.do_"]//span[contains(text(), "Pour valider ")]')
                if global_error_message:
                    raise ActionNeeded(CleanText('.')(global_error_message[0]))
            local_error_message = page.doc.xpath('//div[@id="error"]/p[@class="erreur_texte1"]')
            if local_error_message:
                raise BrowserUnavailable(CleanText('.')(local_error_message[0]))

            number = RawText('./a[contains(@class, "numero_compte")]')(cpt).replace(u'N° ', '')

            account.id = CleanText(None).filter(number).replace(u'N°', '')

            account._card_links = []
            card_link = Link('./ul/li/a[contains(text(), "Carte bancaire")]', default='')(cpt)
            if len(card_link) > 0:
                account._card_links.append(card_link)

            account.label = CleanText('./a[contains(@class, "numero_compte")]/@title')(cpt)

            for pattern, type in self.ACCOUNT_TYPES.items():
                if pattern in account._history_link:
                    account.type = type
                    break

            investment_page = None
            if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET, Account.TYPE_LIFE_INSURANCE}:
                account._investment_link = Link('./ul/li/a[contains(@id, "portefeuille")]')(cpt)
                investment_page = self.browser.open(account._investment_link).page
                balance = investment_page.get_balance(account.type)
                if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                    self.browser.investments[account.id] = list(self.browser.open(account._investment_link).page.get_investments(account))
            else:
                balance = page.get_balance()
                if account.type is not Account.TYPE_LOAN:
                    account.coming = page.get_coming()

            if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                account.currency = investment_page.get_currency()
            else:
                account.currency = account.get_currency(balance)
            account.balance = CleanDecimal(None, replace_dots=True).filter(balance)

            if account.type in (Account.TYPE_CHECKING, Account.TYPE_SAVINGS):
                # Need a token sent by SMS to customers
                account.iban = NotAvailable

            if (account.label, account.id, account.balance) not in [(a.label, a.id, a.balance) for a in accounts]:
                accounts.append(account)
        return accounts
예제 #31
0
    def get_list(self):
        accounts = []

        for block in self.document.xpath('//div[@class="pave"]/div'):
            head_type = block.xpath(
                './div/span[@class="accGroupLabel"]')[0].text.strip()
            account_type = self.ACCOUNT_TYPES.get(head_type,
                                                  Account.TYPE_UNKNOWN)
            for tr in block.cssselect('ul li.tbord_account'):
                id = tr.attrib.get('id', '')
                if id.find('contratId') != 0:
                    self.logger.warning('Unable to parse contract ID: %r' % id)
                    continue
                id = id[id.find('contratId') + len('contratId'):]

                link = tr.cssselect('span.accountLabel a')[0]
                balance = Decimal(
                    FrenchTransaction.clean_amount(
                        tr.cssselect('span.accountTotal')[0].text))

                if id.endswith('CRT'):
                    account = accounts[-1]
                    account._card_links.append(link.attrib['href'])
                    if not account.coming:
                        account.coming = Decimal('0.0')
                    account.coming += balance
                    continue

                account = Account()
                account.id = id
                account.label = unicode(link.text.strip())
                account.type = account_type
                account.balance = balance
                account.currency = account.get_currency(
                    tr.cssselect('span.accountDev')[0].text)
                account._link = link.attrib['href']
                account._card_links = []
                accounts.append(account)

        if not accounts:
            # Sometimes, accounts are only in javascript...
            for script in self.document.xpath('//script'):
                text = script.text
                if text is None:
                    continue
                if 'remotePerso' not in text:
                    continue

                account = None
                attribs = {}
                account_type = Account.TYPE_UNKNOWN
                for line in text.split('\n'):
                    line = line.strip()
                    m = re.match("data.libelle = '(.*)';", line)
                    if m:
                        account_type = self.ACCOUNT_TYPES.get(
                            m.group(1), Account.TYPE_UNKNOWN)
                    elif line == 'var remotePerso = new Object;':
                        account = Account()
                    elif account is not None:
                        m = re.match("remotePerso.(\w+) = '?(.*?)'?;", line)
                        if m:
                            attribs[m.group(1)] = m.group(2)
                        elif line.startswith('listProduitsGroup'):
                            account.id = attribs['refContrat']

                            account.label = attribs['libelle']
                            account.type = account_type
                            account.balance = Decimal(
                                FrenchTransaction.clean_amount(
                                    attribs['soldeDateOpeValeurFormatted']))
                            account.currency = account.get_currency(
                                attribs['codeDevise'])
                            account._link = 'tbord.do?id=%s' % attribs['id']
                            account._card_links = []

                            if account.id.endswith('CRT'):
                                a = accounts[-1]
                                a._card_links.append(account._link)
                                if not a.coming:
                                    a.coming = Decimal('0.0')
                                a.coming += account.balance
                            else:
                                accounts.append(account)
                            account = None

        return accounts
예제 #32
0
    def get_list(self):
        accounts = []

        for cpt in self.doc.xpath(
                '//div[contains(@class, " compte") and not(contains(@class, "compte_selected"))]'
        ):

            # ignore auto assurance accounts
            if 'aut' in cpt.get('class'):
                continue

            account = Account()
            account._history_link = Link(
                './ul/li/a[contains(@id, "consulter_solde") '
                'or contains(@id, "historique") '
                'or contains(@id, "contrat") '
                'or contains(@id, "assurance_vie_operations")]')(cpt)

            # this is to test if access to the accounts info is blocked for different reasons
            page = self.browser.open(account._history_link).page
            if isinstance(page, LoanPage):
                account = Loan()

            account._history_link = Link(
                './ul/li/a[contains(@id, "consulter_solde") '
                'or contains(@id, "historique") '
                'or contains(@id, "contrat") '
                'or contains(@id, "assurance_vie_operations")]')(cpt)
            if isinstance(page, LoanPage):
                account.id = CleanText(
                    '(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]'
                )(cpt)
                account.label = CleanText(
                    '(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]'
                )(cpt)
                account.type = Account.TYPE_LOAN
                account_history_page = self.browser.open(
                    account._history_link).page
                account.total_amount = account_history_page.get_total_amount()
                account.next_payment_amount = account_history_page.get_next_payment_amount(
                )
                account.next_payment_date = account_history_page.get_next_payment_date(
                )
                account.account_label = account_history_page.get_account_label(
                )
                account.subscription_date = account_history_page.get_subscription_date(
                )
                account.maturity_date = account_history_page.get_maturity_date(
                )

            if len(accounts) == 0:
                global_error_message = page.doc.xpath(
                    '//div[@id="as_renouvellementMIFID.do_"]/div[contains(text(), "Bonjour")] '
                    '| //div[@id="as_afficherMessageBloquantMigration.do_"]//div[@class="content_message"] '
                    '| //p[contains(text(), "Et si vous faisiez de Fortuneo votre banque principale")] '
                    '| //div[@id="as_renouvellementMotDePasse.do_"]//p[contains(text(), "votre mot de passe")]'
                    '| //div[@id="as_afficherSecuriteForteOTPIdentification.do_"]//span[contains(text(), "Pour valider ")]'
                )
                if global_error_message:
                    raise ActionNeeded(CleanText('.')(global_error_message[0]))
            local_error_message = page.doc.xpath(
                '//div[@id="error"]/p[@class="erreur_texte1"]')
            if local_error_message:
                raise BrowserUnavailable(
                    CleanText('.')(local_error_message[0]))

            number = RawText('./a[contains(@class, "numero_compte")]')(
                cpt).replace(u'N° ', '')

            account.id = CleanText(None).filter(number).replace(u'N°', '')

            account._card_links = []
            card_link = Link('./ul/li/a[contains(text(), "Carte bancaire")]',
                             default='')(cpt)
            if len(card_link) > 0:
                account._card_links.append(card_link)

            account.label = CleanText(
                './a[contains(@class, "numero_compte")]/@title')(cpt)

            for pattern, type in self.ACCOUNT_TYPES.items():
                if pattern in account._history_link:
                    account.type = type
                    break

            if account.type in {
                    Account.TYPE_PEA, Account.TYPE_MARKET,
                    Account.TYPE_LIFE_INSURANCE
            }:
                account._investment_link = Link(
                    './ul/li/a[contains(@id, "portefeuille")]')(cpt)
                balance = self.browser.open(
                    account._investment_link).page.get_balance(account.type)
                if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                    self.browser.investments[account.id] = list(
                        self.browser.open(
                            account._investment_link).page.get_investments(
                                account))
            else:
                balance = self.browser.open(
                    account._history_link).page.get_balance()
                if account.type is not Account.TYPE_LOAN:
                    account.coming = self.browser.open(
                        account._history_link).page.get_coming()

            if account.type in {Account.TYPE_PEA, Account.TYPE_MARKET}:
                account.currency = self.browser.open(
                    account._investment_link).page.get_currency()
            else:
                account.currency = account.get_currency(balance)
            account.balance = CleanDecimal(None,
                                           replace_dots=True).filter(balance)

            if account.type in (Account.TYPE_CHECKING, Account.TYPE_SAVINGS):
                # Need a token sent by SMS to customers
                account.iban = NotAvailable

            if (account.label, account.id, account.balance) not in [
                (a.label, a.id, a.balance) for a in accounts
            ]:
                accounts.append(account)
        return accounts
예제 #33
0
    def get_list(self):
        accounts = []

        for cpt in self.doc.xpath('//div[contains(@class, " compte") and not(contains(@class, "compte_selected"))]'):

            # ignore auto assurance accounts
            if 'aut' in cpt.get('class'):
                continue

            account = Account()
            account._history_link = Link('./ul/li/a[contains(@id, "consulter_solde") '
                                         'or contains(@id, "historique") '
                                         'or contains(@id, "contrat") '
                                         'or contains(@id, "assurance_vie_operations")]')(cpt)

            # this is to test if access to the accounts info is blocked for different reasons
            page = self.browser.open(account._history_link).page
            if isinstance(page, LoanPage):
                account = Loan()

            account._history_link = Link('./ul/li/a[contains(@id, "consulter_solde") '
                                         'or contains(@id, "historique") '
                                         'or contains(@id, "contrat") '
                                         'or contains(@id, "assurance_vie_operations")]')(cpt)
            if isinstance(page, LoanPage):
                account.id = CleanText('(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]')(cpt)
                account.label = CleanText('(//p[@id="c_montantEmprunte"]//span[@class="valStatic"]//strong)[1]')(cpt)
                account.type = Account.TYPE_LOAN
                account_history_page = page
                account.total_amount = account_history_page.get_total_amount()
                account.next_payment_amount = account_history_page.get_next_payment_amount()
                account.next_payment_date = account_history_page.get_next_payment_date()
                account.account_label = account_history_page.get_account_label()
                account.subscription_date = account_history_page.get_subscription_date()
                account.maturity_date = account_history_page.get_maturity_date()
                account.ownership = account_history_page.get_owner()

            if len(accounts) == 0:
                global_error_message = page.doc.xpath('//div[@id="as_renouvellementMIFID.do_"]/div[contains(text(), "Bonjour")] '
                                                      '| //div[@id="as_afficherMessageBloquantMigration.do_"]//div[@class="content_message"] '
                                                      '| //p[contains(text(), "Et si vous faisiez de Fortuneo votre banque principale")] '
                                                      '| //div[@id="as_renouvellementMotDePasse.do_"]//p[contains(text(), "votre mot de passe")]'
                                                      '| //div[@id="as_afficherSecuriteForteOTPIdentification.do_"]//span[contains(text(), "Pour valider ")]')
                if global_error_message:
                    if "Et si vous faisiez de Fortuneo votre banque principale" in CleanText(global_error_message)(self):
                        self.browser.location('/ReloadContext', data={'action': 4})
                        return
                    raise ActionNeeded(CleanText('.')(global_error_message[0]))
            local_error_message = page.doc.xpath('//div[@id="error"]/p[@class="erreur_texte1"]')
            if local_error_message:
                raise BrowserUnavailable(CleanText('.')(local_error_message[0]))

            account.id = account.number = CleanText('./a[contains(@class, "numero_compte")]/div')(cpt).replace(u'N° ', '')
            account._ca = CleanText('./a[contains(@class, "numero_compte")]/@rel')(cpt)

            account._card_links = []
            card_link = Link('./ul/li/a[contains(text(), "Carte bancaire")]', default='')(cpt)
            if len(card_link) > 0:
                account._card_links.append(card_link)

            account.label = CleanText('./a[contains(@class, "numero_compte")]/@title')(cpt)

            for pattern, type in self.ACCOUNT_TYPES.items():
                if pattern in account._history_link:
                    account.type = type
                    break

            investment_page = None
            if account.type in (Account.TYPE_PEA, Account.TYPE_MARKET, Account.TYPE_LIFE_INSURANCE):
                account._investment_link = Link('./ul/li/a[contains(@id, "portefeuille")]')(cpt)
                investment_page = self.browser.location(account._investment_link).page
                balance = investment_page.get_balance(account.type)
                if account.type in (Account.TYPE_PEA, Account.TYPE_MARKET):
                    self.browser.investments[account.id] = list(self.browser.open(account._investment_link).page.get_investments(account))
            else:
                balance = page.get_balance()
                if account.type is not Account.TYPE_LOAN:
                    account.coming = page.get_coming()

            if account.type in (Account.TYPE_PEA, Account.TYPE_MARKET):
                account.currency = investment_page.get_currency()
            elif balance:
                account.currency = account.get_currency(balance)

            account.balance = CleanDecimal.French().filter(balance)

            if account.type in (Account.TYPE_CHECKING, Account.TYPE_SAVINGS):
                # Need a token sent by SMS to customers
                account.iban = NotAvailable

            if account.type is not Account.TYPE_LOAN:
                regexp = re.search(r'(m\. |mme\. )(.+)', CleanText('//span[has-class("mon_espace_nom")]')(self.doc), re.IGNORECASE)
                if regexp and len(regexp.groups()) == 2:
                    gender = regexp.group(1).replace('.', '').rstrip()
                    name = regexp.group(2)
                    label = account.label
                    if re.search(r'(m|mr|me|mme|mlle|mle|ml)\.? (.*)\bou (m|mr|me|mme|mlle|mle|ml)\b(.*)', label, re.IGNORECASE):
                        account.ownership = AccountOwnership.CO_OWNER
                    elif re.search(r'{} {}'.format(gender, name), label, re.IGNORECASE):
                        account.ownership = AccountOwnership.OWNER
                    else:
                        account.ownership = AccountOwnership.ATTORNEY

            if (account.label, account.id, account.balance) not in [(a.label, a.id, a.balance) for a in accounts]:
                accounts.append(account)
        return accounts