mirror of
https://github.com/OCA/account-reconcile.git
synced 2025-01-20 12:27:39 +02:00
[FIX] Bug fixing and first running version
(lp:c2c-financial-addons/6.1 rev 24.1.19)
This commit is contained in:
@@ -29,9 +29,18 @@
|
|||||||
'description': """
|
'description': """
|
||||||
The goal of this module is to improve the basic bank statement, help dealing with huge volume of
|
The goal of this module is to improve the basic bank statement, help dealing with huge volume of
|
||||||
reconciliation by providing basic rules to identify the partner of a bank statement line.
|
reconciliation by providing basic rules to identify the partner of a bank statement line.
|
||||||
It will also take care of the chosen profile to make his work.
|
Each bank statement profile can have his own rules to apply respecting a sequence order.
|
||||||
|
|
||||||
|
Some basic rules are provided in this module:
|
||||||
|
|
||||||
|
1) Match from statement line label (based on partner field 'Bank Statement Label')
|
||||||
|
2) Match from statement line label (based on partner name)
|
||||||
|
3) Match from statement line reference (based on SO number)
|
||||||
|
|
||||||
|
It add as well a label on the bank statement line (on which the pre-define rules can match) and
|
||||||
|
a char field on the partner called 'Bank Statement Label'. Using the pre-define rules, you'll be
|
||||||
|
able to match various label for a partner.
|
||||||
|
|
||||||
His goal is to provide an easy way to fullfill the info of a bank statement line based on rules.
|
|
||||||
The reference of the line is always used by the reconciliation process. We're supposed to copy
|
The reference of the line is always used by the reconciliation process. We're supposed to copy
|
||||||
there (or write manually) the matching string. That can be : the order Number or an invoice number,
|
there (or write manually) the matching string. That can be : the order Number or an invoice number,
|
||||||
or anything that will be found in the invoice entry part to make the match.
|
or anything that will be found in the invoice entry part to make the match.
|
||||||
@@ -41,6 +50,7 @@
|
|||||||
'init_xml': [],
|
'init_xml': [],
|
||||||
'update_xml': [
|
'update_xml': [
|
||||||
'statement_view.xml',
|
'statement_view.xml',
|
||||||
|
'partner_view.xml',
|
||||||
'data.xml',
|
'data.xml',
|
||||||
],
|
],
|
||||||
'demo_xml': [],
|
'demo_xml': [],
|
||||||
|
|||||||
@@ -6,16 +6,25 @@
|
|||||||
<field name="name">Match from line label (based on partner field 'Bank Statement Label')</field>
|
<field name="name">Match from line label (based on partner field 'Bank Statement Label')</field>
|
||||||
<field name="sequence">60</field>
|
<field name="sequence">60</field>
|
||||||
<field name="function_to_call">get_from_label_and_partner_field</field>
|
<field name="function_to_call">get_from_label_and_partner_field</field>
|
||||||
</field>
|
|
||||||
</record>
|
</record>
|
||||||
|
|
||||||
<record id="bank_statement_completion_rule_3" model="account.statement.completion.rule">
|
<record id="bank_statement_completion_rule_3" model="account.statement.completion.rule">
|
||||||
<field name="name">Match from line label (based on partner name)</field>
|
<field name="name">Match from line label (based on partner name)</field>
|
||||||
<field name="sequence">70</field>
|
<field name="sequence">70</field>
|
||||||
<field name="function_to_call">get_from_label_and_partner_name</field>
|
<field name="function_to_call">get_from_label_and_partner_name</field>
|
||||||
</field>
|
|
||||||
</record>
|
</record>
|
||||||
|
|
||||||
|
<record id="bank_statement_completion_rule_1" model="account.statement.completion.rule">
|
||||||
|
<field name="name">Match from line reference (based on SO number)</field>
|
||||||
|
<field name="sequence">50</field>
|
||||||
|
<field name="function_to_call">get_from_ref_and_so</field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
<record id="bank_statement_completion_rule_4" model="account.statement.completion.rule">
|
||||||
|
<field name="name">Match from line reference (based on Invoice number)</field>
|
||||||
|
<field name="sequence">40</field>
|
||||||
|
<field name="function_to_call">get_from_ref_and_invoice</field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,8 @@ from tools.translate import _
|
|||||||
import netsvc
|
import netsvc
|
||||||
logger = netsvc.Logger()
|
logger = netsvc.Logger()
|
||||||
from openerp.osv.orm import Model, fields
|
from openerp.osv.orm import Model, fields
|
||||||
|
from openerp.osv import fields, osv
|
||||||
|
from operator import itemgetter, attrgetter
|
||||||
|
|
||||||
class ErrorTooManyPartner(Exception):
|
class ErrorTooManyPartner(Exception):
|
||||||
def __init__(self, value):
|
def __init__(self, value):
|
||||||
@@ -41,12 +42,11 @@ class AccountStatementProfil(Model):
|
|||||||
|
|
||||||
'rule_ids':fields.many2many('account.statement.completion.rule',
|
'rule_ids':fields.many2many('account.statement.completion.rule',
|
||||||
string='Related statement profiles',
|
string='Related statement profiles',
|
||||||
rel='account_statement_rule_statement_profile_to_rel',
|
rel='as_rul_st_prof_rel',
|
||||||
ids1='profile_id',ids2='rule_id',
|
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
|
|
||||||
def find_values_from_rules(self, cr, uid, ids, line_id, context=None):
|
def find_values_from_rules(self, cr, uid, id, line_id, context=None):
|
||||||
"""This method will execute all rules, in their sequence order,
|
"""This method will execute all rules, in their sequence order,
|
||||||
to match a partner for the given statement.line and return his id.
|
to match a partner for the given statement.line and return his id.
|
||||||
|
|
||||||
@@ -58,15 +58,19 @@ class AccountStatementProfil(Model):
|
|||||||
...
|
...
|
||||||
}
|
}
|
||||||
"""
|
"""
|
||||||
|
|
||||||
if not context:
|
if not context:
|
||||||
context={}
|
context={}
|
||||||
res = {}
|
res = {}
|
||||||
for profile in self.browse(cr, uid, ids, context=context):
|
rule_obj = self.pool.get('account.statement.completion.rule')
|
||||||
for rule in profile.rule_ids:
|
profile = self.browse(cr, uid, id, context=context)
|
||||||
method_to_call = getattr(rule, rule.function_to_call)
|
# We need to respect the sequence order
|
||||||
result = method_to_call(cr,uid,line_id,context)
|
sorted_array = sorted(profile.rule_ids, key=attrgetter('sequence'))
|
||||||
if result:
|
for rule in sorted_array:
|
||||||
return res
|
method_to_call = getattr(rule_obj, rule.function_to_call)
|
||||||
|
result = method_to_call(cr,uid,line_id,context)
|
||||||
|
if result:
|
||||||
|
return result
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
@@ -74,32 +78,89 @@ class AccountStatementCompletionRule(Model):
|
|||||||
"""This will represent all the completion method that we can have to
|
"""This will represent all the completion method that we can have to
|
||||||
fullfill the bank statement. You'll be able to extend them in you own module
|
fullfill the bank statement. You'll be able to extend them in you own module
|
||||||
and choose those to apply for every statement profile.
|
and choose those to apply for every statement profile.
|
||||||
The goal of a rules is to fullfill at least the partner of the line, but
|
The goal of a rule is to fullfill at least the partner of the line, but
|
||||||
if possible also the reference because we'll use it in the reconciliation
|
if possible also the reference because we'll use it in the reconciliation
|
||||||
process. The reference should contain the invoice number or the SO number
|
process. The reference should contain the invoice number or the SO number
|
||||||
|
or any reference that will be matched by the invoice genertaed move.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
_name = "account.statement.completion.rule"
|
_name = "account.statement.completion.rule"
|
||||||
_order = "sequence asc"
|
_order = "sequence asc"
|
||||||
|
|
||||||
def _get_functions(self):
|
def _get_functions(self, cr, uid, context=None):
|
||||||
"""List of available methods for rules. Override this to add you own."""
|
"""List of available methods for rules. Override this to add you own."""
|
||||||
return [
|
return [
|
||||||
|
('get_from_ref_and_invoice', 'From line reference (based on invoice number)'),
|
||||||
|
('get_from_ref_and_so', 'From line reference (based on SO number)'),
|
||||||
('get_from_label_and_partner_field', 'From line label (based on partner field)'),
|
('get_from_label_and_partner_field', 'From line label (based on partner field)'),
|
||||||
('get_from_label_and_partner_name', 'From line label (based on partner name)'),
|
('get_from_label_and_partner_name', 'From line label (based on partner name)'),
|
||||||
]
|
]
|
||||||
|
|
||||||
_columns={
|
_columns={
|
||||||
'sequence': fields.integer('Sequence', help="Lower means paresed first."),
|
'sequence': fields.integer('Sequence', help="Lower means paresed first."),
|
||||||
'name': fields.char('Name'),
|
'name': fields.char('Name', size=128),
|
||||||
'profile_ids': fields.many2many('account.statement.profil',
|
'profile_ids': fields.many2many('account.statement.profil',
|
||||||
rel='account_statement_rule_statement_profile_to_rel',
|
rel='as_rul_st_prof_rel',
|
||||||
ids1='rule_id', ids2='profile_id',
|
|
||||||
string='Related statement profiles'),
|
string='Related statement profiles'),
|
||||||
'function_to_call': fields.selection(_get_functions, 'Method'),
|
'function_to_call': fields.selection(_get_functions, 'Method'),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def get_from_ref_and_invoice(self, cursor, uid, line_id, context=None):
|
||||||
|
"""Match the partner based on the invoice number and the reference of the statement
|
||||||
|
line. Then, call the generic st_line method to complete other values.
|
||||||
|
If more than one partner matched, raise an error.
|
||||||
|
Return:
|
||||||
|
A dict of value that can be passed directly to the write method of
|
||||||
|
the statement line.
|
||||||
|
{'partner_id': value,
|
||||||
|
'account_id' : value,
|
||||||
|
...}
|
||||||
|
"""
|
||||||
|
st_obj = self.pool.get('account.bank.statement.line')
|
||||||
|
st_line = st_obj.browse(cursor,uid,line_id)
|
||||||
|
res = {}
|
||||||
|
if st_line:
|
||||||
|
inv_obj = self.pool.get('account.invoice')
|
||||||
|
inv_id = inv_obj.search(cursor, uid, [('number', '=', st_line.ref)])
|
||||||
|
if inv_id and len(inv_id) == 1:
|
||||||
|
inv = inv_obj.browse(cursor, uid, inv_id[0])
|
||||||
|
res['partner_id'] = inv.partner_id.id
|
||||||
|
elif inv_id and len(inv_id) > 1:
|
||||||
|
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
||||||
|
st_vals = st_obj.get_values_for_line(cursor, uid, profile_id = st_line.statement_id.profile_id.id,
|
||||||
|
partner_id = res.get('partner_id',False), line_type = st_line.type, amount = st_line.amount, context = context)
|
||||||
|
res.update(st_vals)
|
||||||
|
return res
|
||||||
|
|
||||||
def get_from_label_and_partner_field(self, cr, uid, line_id, context=None):
|
def get_from_ref_and_so(self, cursor, uid, line_id, context=None):
|
||||||
|
"""Match the partner based on the SO number and the reference of the statement
|
||||||
|
line. Then, call the generic st_line method to complete other values.
|
||||||
|
If more than one partner matched, raise an error.
|
||||||
|
Return:
|
||||||
|
A dict of value that can be passed directly to the write method of
|
||||||
|
the statement line.
|
||||||
|
{'partner_id': value,
|
||||||
|
'account_id' : value,
|
||||||
|
...}
|
||||||
|
"""
|
||||||
|
st_obj = self.pool.get('account.bank.statement.line')
|
||||||
|
st_line = st_obj.browse(cursor,uid,line_id)
|
||||||
|
res = {}
|
||||||
|
if st_line:
|
||||||
|
so_obj = self.pool.get('sale.order')
|
||||||
|
so_id = so_obj.search(cursor, uid, [('name', '=', st_line.ref)])
|
||||||
|
if so_id and len(so_id) == 1:
|
||||||
|
so = so_obj.browse(cursor, uid, so_id[0])
|
||||||
|
res['partner_id'] = so.partner_id.id
|
||||||
|
elif so_id and len(so_id) > 1:
|
||||||
|
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
||||||
|
st_vals = st_obj.get_values_for_line(cursor, uid, profile_id = st_line.statement_id.profile_id.id,
|
||||||
|
partner_id = res.get('partner_id',False), line_type = st_line.type, amount = st_line.amount, context = context)
|
||||||
|
res.update(st_vals)
|
||||||
|
return res
|
||||||
|
|
||||||
|
|
||||||
|
def get_from_label_and_partner_field(self, cursor, uid, line_id, context=None):
|
||||||
"""Match the partner based on the label field of the statement line
|
"""Match the partner based on the label field of the statement line
|
||||||
and the text defined in the 'bank_statement_label' field of the partner.
|
and the text defined in the 'bank_statement_label' field of the partner.
|
||||||
Remember that we can have values separated with ; Then, call the generic
|
Remember that we can have values separated with ; Then, call the generic
|
||||||
@@ -114,24 +175,24 @@ class AccountStatementCompletionRule(Model):
|
|||||||
"""
|
"""
|
||||||
partner_obj = self.pool.get('res.partner')
|
partner_obj = self.pool.get('res.partner')
|
||||||
st_obj = self.pool.get('account.bank.statement.line')
|
st_obj = self.pool.get('account.bank.statement.line')
|
||||||
st_line = st_obj.browse(cr,uid,line_id)
|
st_line = st_obj.browse(cursor,uid,line_id)
|
||||||
res = {}
|
res = {}
|
||||||
compt = 0
|
compt = 0
|
||||||
if st_line:
|
if st_line:
|
||||||
ids = partner_obj.search(cr, uid, [['bank_statement_label', '!=', False]], context=context)
|
ids = partner_obj.search(cursor, uid, [['bank_statement_label', '!=', False]], context=context)
|
||||||
for partner in self.browse(cr, uid, ids, context=context):
|
for partner in self.browse(cursor, uid, ids, context=context):
|
||||||
for partner_label in partner.bank_statement_label.split(';'):
|
for partner_label in partner.bank_statement_label.split(';'):
|
||||||
if partner_label in st_line.label:
|
if partner_label in st_line.label:
|
||||||
compt += 1
|
compt += 1
|
||||||
res['partner_id'] = partner.id
|
res['partner_id'] = partner.id
|
||||||
if compt > 1:
|
if compt > 1:
|
||||||
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
||||||
st_vals = st_obj.get_values_for_line(cr, uid, profile_id = st_line.statement_id.profile_id.id,
|
st_vals = st_obj.get_values_for_line(cursor, uid, profile_id = st_line.statement_id.profile_id.id,
|
||||||
partner_id = res.get('partner_id',False), line_type = st_line.type, amount = st_line.amount, context = context)
|
partner_id = res.get('partner_id',False), line_type = st_line.type, amount = st_line.amount, context = context)
|
||||||
res.update(st_vals)
|
res.update(st_vals)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
def get_from_label_and_partner_name(self, cr, uid, line_id, context=None):
|
def get_from_label_and_partner_name(self, cursor, uid, line_id, context=None):
|
||||||
"""Match the partner based on the label field of the statement line
|
"""Match the partner based on the label field of the statement line
|
||||||
and the name of the partner.
|
and the name of the partner.
|
||||||
Then, call the generic st_line method to complete other values.
|
Then, call the generic st_line method to complete other values.
|
||||||
@@ -145,17 +206,17 @@ class AccountStatementCompletionRule(Model):
|
|||||||
"""
|
"""
|
||||||
res = {}
|
res = {}
|
||||||
st_obj = self.pool.get('account.bank.statement.line')
|
st_obj = self.pool.get('account.bank.statement.line')
|
||||||
st_line = st_obj.browse(cr,uid,line_id)
|
st_line = st_obj.browse(cursor,uid,line_id)
|
||||||
if st_line:
|
if st_line:
|
||||||
sql = "SELECT id FROM res_partner WHERE name ~* '.*%s.*'"
|
sql = "SELECT id FROM res_partner WHERE name ~* '.*%s.*'"
|
||||||
cr.execute(sql, (st_line.label,))
|
cursor.execute(sql, (st_line.label,))
|
||||||
result = cr.fetchall()
|
result = cursor.fetchall()
|
||||||
if len(result) > 1:
|
if len(result) > 1:
|
||||||
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
raise ErrorTooManyPartner(_('Line named "%s" was matched by more than one partner.')%(st_line.name,st_line.id))
|
||||||
for id in result:
|
for id in result:
|
||||||
res['partner_id'] = id
|
res['partner_id'] = id
|
||||||
st_vals = st_obj.get_values_for_line(cr, uid, profile_id = st_line.statement_id.profile_id.id,
|
st_vals = st_obj.get_values_for_line(cursor, uid, profile_id = st_line.statement_id.profile_id.id,
|
||||||
partner_id = res.get('partner_id',False), line_type = st_line.type, st_line.amount, context)
|
partner_id = res.get('partner_id',False), line_type = st_line.type, amount = st_line.amount, context = context)
|
||||||
res.update(st_vals)
|
res.update(st_vals)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
@@ -167,79 +228,45 @@ class AccountStatementLine(Model):
|
|||||||
_inherit = "account.bank.statement.line"
|
_inherit = "account.bank.statement.line"
|
||||||
|
|
||||||
_columns={
|
_columns={
|
||||||
# 'email_address': fields.char('Email', size=64),
|
|
||||||
# 'order_ref': fields.char('Order Ref', size=64),
|
|
||||||
# 'partner_name': fields.char('Partner Name', size=64),
|
|
||||||
#
|
|
||||||
# Only label for a start, but other module can add their own
|
# Only label for a start, but other module can add their own
|
||||||
'additionnal_bank_fields' : fields.serialized('Additionnal infos from bank', help="Used by completion and import system."),
|
'additionnal_bank_fields' : fields.serialized('Additionnal infos from bank',
|
||||||
|
help="Used by completion and import system. Adds every field that is present in your bank/office \
|
||||||
|
statement file"),
|
||||||
'label': fields.sparse(type='char', string='Label',
|
'label': fields.sparse(type='char', string='Label',
|
||||||
serialization_field='additionnal_bank_fields'),
|
serialization_field='additionnal_bank_fields'),
|
||||||
|
'already_completed': fields.boolean("Auto-Completed",
|
||||||
|
help="When this checkbox is ticked, the auto-completion process/button will ignore it."),
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
_defaults = {
|
||||||
|
'already_completed': False,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def get_line_values_from_rules(self, cr, uid, ids, context=None):
|
def get_line_values_from_rules(self, cr, uid, ids, context=None):
|
||||||
"""
|
"""
|
||||||
We'll try to find out the values related to the line based on what we
|
We'll try to find out the values related to the line based on what we
|
||||||
have and rules setted on the profile..
|
have and rules setted on the profile..
|
||||||
|
|
||||||
|
We ignore line for which already_completed is ticked!
|
||||||
"""
|
"""
|
||||||
profile_obj = self.pool.get('account.statement.profil')
|
profile_obj = self.pool.get('account.statement.profil')
|
||||||
res={}
|
res={}
|
||||||
errors_stack = []
|
errors_stack = []
|
||||||
for line in self.browse(cr,uid, ids, context):
|
for line in self.browse(cr,uid, ids, context):
|
||||||
try:
|
if not line.already_completed:
|
||||||
vals = profile_obj.find_values_from_rules(cr, uid, ids, line.id, context)
|
try:
|
||||||
res[line.id]=vals
|
vals = profile_obj.find_values_from_rules(cr, uid, line.statement_id.profile_id.id, line.id, context)
|
||||||
except ErrorTooManyPartner, exc:
|
res[line.id]=vals
|
||||||
msg = "Line ID %s had following error: %s" % (line.id, str(exc))
|
except ErrorTooManyPartner, exc:
|
||||||
errors_stack.append(msg)
|
msg = "Line ID %s had following error: %s" % (line.id, str(exc))
|
||||||
# if not auto_complete_line
|
errors_stack.append(msg)
|
||||||
# if not line.partner_id or line.account_id.id ==1:
|
|
||||||
# partner_obj = self.pool.get('res.partner')
|
|
||||||
# partner_id=False
|
|
||||||
# if line.order_ref:
|
|
||||||
# partner_id = partner_obj.get_partner_from_order_ref(cr, uid, line.order_ref, context=context)
|
|
||||||
# if not partner_id and line.email_address:
|
|
||||||
# partner_id = partner_obj.get_partner_from_email(cr, uid, line.email_address, context=context)
|
|
||||||
# if not partner_id and line.partner_name:
|
|
||||||
# partner_id = partner_obj.get_partner_from_name(cr, uid, line.partner_name, context=context)
|
|
||||||
# if not partner_id and line.label:
|
|
||||||
# partner_id = partner_obj.get_partner_from_label_based_on_bank_statement_label(cr, uid, line.label, context=context)
|
|
||||||
# if partner_id:
|
|
||||||
# res = {'partner_id': partner_id}
|
|
||||||
# if context['auto_completion']:
|
|
||||||
# #Build the space for expr
|
|
||||||
# space = {
|
|
||||||
# 'self':self,
|
|
||||||
# 'cr':cr,
|
|
||||||
# 'uid':uid,
|
|
||||||
# 'line': line,
|
|
||||||
# 'res': res,
|
|
||||||
# 'context':context,
|
|
||||||
# }
|
|
||||||
# exec context['auto_completion'] in space
|
|
||||||
# if space.get('result', False):
|
|
||||||
# res.update(space['result'])
|
|
||||||
if errors_stack:
|
if errors_stack:
|
||||||
msg = u"\n".join(errors_stack)
|
msg = u"\n".join(errors_stack)
|
||||||
raise ErrorTooManyPartner(msg)
|
raise ErrorTooManyPartner(msg)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
#
|
|
||||||
# class A(object):
|
|
||||||
# def xx_toto():
|
|
||||||
# print 'toto'
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# a = A()
|
|
||||||
# funcs = ['yy_toto', 'xx_toto']
|
|
||||||
# for i in funcs:
|
|
||||||
# if hasattr(a, i):
|
|
||||||
# to_call = getattr(a, i)
|
|
||||||
# to_call()
|
|
||||||
# else:
|
|
||||||
# raise NameError('blblblb')
|
|
||||||
|
|
||||||
class AccountBankSatement(Model):
|
class AccountBankSatement(Model):
|
||||||
"""
|
"""
|
||||||
We add a basic button and stuff to support the auto-completion
|
We add a basic button and stuff to support the auto-completion
|
||||||
@@ -248,6 +275,8 @@ class AccountBankSatement(Model):
|
|||||||
_inherit = "account.bank.statement"
|
_inherit = "account.bank.statement"
|
||||||
|
|
||||||
def button_auto_completion(self, cr, uid, ids, context=None):
|
def button_auto_completion(self, cr, uid, ids, context=None):
|
||||||
|
"""Complete line with values given by rules and tic the already_completed
|
||||||
|
checkbox so we won't compute them again until the user untick it !"""
|
||||||
if not context:
|
if not context:
|
||||||
context={}
|
context={}
|
||||||
stat_line_obj = self.pool.get('account.bank.statement.line')
|
stat_line_obj = self.pool.get('account.bank.statement.line')
|
||||||
@@ -260,8 +289,9 @@ class AccountBankSatement(Model):
|
|||||||
except ErrorTooManyPartner, exc:
|
except ErrorTooManyPartner, exc:
|
||||||
errors_msg = str(exc)
|
errors_msg = str(exc)
|
||||||
for id in line_ids:
|
for id in line_ids:
|
||||||
vals = res[line.id]
|
vals = res.get(id, False)
|
||||||
if vals:
|
if vals:
|
||||||
|
vals['already_completed'] = True
|
||||||
stat_line_obj.write(cr, uid, id, vals, context=ctx)
|
stat_line_obj.write(cr, uid, id, vals, context=ctx)
|
||||||
# cr.commit()
|
# cr.commit()
|
||||||
# TOTEST: I don't know if this is working...
|
# TOTEST: I don't know if this is working...
|
||||||
|
|||||||
@@ -10,11 +10,12 @@
|
|||||||
<field name="type">form</field>
|
<field name="type">form</field>
|
||||||
<field name="arch" type="xml">
|
<field name="arch" type="xml">
|
||||||
<data>
|
<data>
|
||||||
|
<xpath expr="/form/notebook/page/field[@name='line_ids']/tree/field[@name='sequence']" position="before">
|
||||||
|
<field name="already_completed" />
|
||||||
|
</xpath>
|
||||||
<xpath expr="/form/notebook/page/field[@name='line_ids']/form/field[@name='ref']" position="after">
|
<xpath expr="/form/notebook/page/field[@name='line_ids']/form/field[@name='ref']" position="after">
|
||||||
<!-- <field name="partner_name" />
|
<field name="label" />
|
||||||
<field name="order_ref" />
|
<field name="already_completed" />
|
||||||
<field name="email_address" /> -->
|
|
||||||
<field name="label" />
|
|
||||||
</xpath>
|
</xpath>
|
||||||
|
|
||||||
<xpath expr="/form/group[2]" position="attributes">
|
<xpath expr="/form/group[2]" position="attributes">
|
||||||
@@ -29,6 +30,57 @@
|
|||||||
</field>
|
</field>
|
||||||
</record>
|
</record>
|
||||||
|
|
||||||
|
<record id="statement_rules_view_form" model="ir.ui.view">
|
||||||
|
<field name="name">account.statement.profil.view</field>
|
||||||
|
<field name="model">account.statement.profil</field>
|
||||||
|
<field name="inherit_id" ref="account_statement_ext.statement_importer_view_form"/>
|
||||||
|
<field name="type">form</field>
|
||||||
|
<field name="arch" type="xml">
|
||||||
|
<field name="bank_statement_prefix" position="after">
|
||||||
|
<separator colspan="4" string="Auto-Completion Rules"/>
|
||||||
|
<field name="rule_ids" colspan="4" nolabel="1"/>
|
||||||
|
</field>
|
||||||
|
</field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
|
||||||
|
<record id="statement_st_completion_rule_view_form" model="ir.ui.view">
|
||||||
|
<field name="name">account.statement.completion.rule.view</field>
|
||||||
|
<field name="model">account.statement.completion.rule</field>
|
||||||
|
<field name="type">form</field>
|
||||||
|
<field name="arch" type="xml">
|
||||||
|
<form string="Statement Completion Rule">
|
||||||
|
<field name="sequence"/>
|
||||||
|
<field name="name" select="1" />
|
||||||
|
<field name="function_to_call"/>
|
||||||
|
<separator colspan="4" string="Related Profiles"/>
|
||||||
|
<field name="profile_ids" nolabel="1" colspan="4"/>
|
||||||
|
</form>
|
||||||
|
</field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
<record id="statement_st_completion_rule_view_tree" model="ir.ui.view">
|
||||||
|
<field name="name">account.statement.completion.rule.view</field>
|
||||||
|
<field name="model">account.statement.completion.rule</field>
|
||||||
|
<field name="type">tree</field>
|
||||||
|
<field name="arch" type="xml">
|
||||||
|
<tree string="Statement Completion Rule">
|
||||||
|
<field name="sequence"/>
|
||||||
|
<field name="name" select="1" />
|
||||||
|
<field name="profile_ids" />
|
||||||
|
<field name="function_to_call"/>
|
||||||
|
</tree>
|
||||||
|
</field>
|
||||||
|
</record>
|
||||||
|
<record id="action_st_completion_rule_tree" model="ir.actions.act_window">
|
||||||
|
<field name="name">Statement Completion Rule</field>
|
||||||
|
<field name="res_model">account.statement.completion.rule</field>
|
||||||
|
<field name="view_type">form</field>
|
||||||
|
<field name="view_mode">tree,form</field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
<menuitem string="Statement Completion Rule" action="action_st_completion_rule_tree" id="menu_action_st_completion_rule_tree_menu" parent="account.menu_configuration_misc" sequence="30"/>
|
||||||
|
|
||||||
|
|
||||||
</data>
|
</data>
|
||||||
</openerp>
|
</openerp>
|
||||||
|
|||||||
@@ -56,6 +56,8 @@
|
|||||||
'website': 'http://www.camptocamp.com',
|
'website': 'http://www.camptocamp.com',
|
||||||
'init_xml': [],
|
'init_xml': [],
|
||||||
'update_xml': [
|
'update_xml': [
|
||||||
|
"wizard/import_statement_view.xml",
|
||||||
|
"statement_view.xml",
|
||||||
],
|
],
|
||||||
'demo_xml': [],
|
'demo_xml': [],
|
||||||
'test': [],
|
'test': [],
|
||||||
|
|||||||
@@ -23,7 +23,9 @@ import base64
|
|||||||
import csv
|
import csv
|
||||||
import tempfile
|
import tempfile
|
||||||
import datetime
|
import datetime
|
||||||
from . import parser
|
# from . import parser
|
||||||
|
from parser import BankStatementImportParser
|
||||||
|
from parser import UnicodeDictReader
|
||||||
try:
|
try:
|
||||||
import xlrd
|
import xlrd
|
||||||
except:
|
except:
|
||||||
@@ -33,7 +35,7 @@ class FileParser(BankStatementImportParser):
|
|||||||
"""Abstract clall for that help to build a specific parser for all
|
"""Abstract clall for that help to build a specific parser for all
|
||||||
.csv and .xls files"""
|
.csv and .xls files"""
|
||||||
|
|
||||||
def __init__(self, parse_name=None, keys_to_validate={}, ftype='csv', convertion_dict=None, *args, **kwargs):
|
def __init__(self, parse_name, keys_to_validate={}, ftype='csv', convertion_dict=None, *args, **kwargs):
|
||||||
"""
|
"""
|
||||||
:param: convertion_dict : keys and type to convert of every column in the file like
|
:param: convertion_dict : keys and type to convert of every column in the file like
|
||||||
{
|
{
|
||||||
@@ -46,7 +48,7 @@ class FileParser(BankStatementImportParser):
|
|||||||
|
|
||||||
"""
|
"""
|
||||||
|
|
||||||
super(self,FileParser).__init__(parse_name, *args, **kwargs)
|
super(FileParser, self).__init__(parse_name, *args, **kwargs)
|
||||||
if ftype in ('csv', 'xls'):
|
if ftype in ('csv', 'xls'):
|
||||||
self.ftype = ftype
|
self.ftype = ftype
|
||||||
else:
|
else:
|
||||||
@@ -69,7 +71,7 @@ class FileParser(BankStatementImportParser):
|
|||||||
|
|
||||||
def _post(self, *args, **kwargs):
|
def _post(self, *args, **kwargs):
|
||||||
"""Cast row type depending on the file format .csv or .xls"""
|
"""Cast row type depending on the file format .csv or .xls"""
|
||||||
self.result_row_list = self._cast_rows(kwargs)
|
self.result_row_list = self._cast_rows(*args, **kwargs)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def _parse(self, *args, **kwargs):
|
def _parse(self, *args, **kwargs):
|
||||||
@@ -135,7 +137,7 @@ class FileParser(BankStatementImportParser):
|
|||||||
line[rule] = conversion_rules[rule](line[rule])
|
line[rule] = conversion_rules[rule](line[rule])
|
||||||
return result_set
|
return result_set
|
||||||
|
|
||||||
def _cast_rows(self):
|
def _cast_rows(self, *args, **kwargs):
|
||||||
func = getattr(self, '_from_%s'%(self.ftype))
|
func = getattr(self, '_from_%s'%(self.ftype))
|
||||||
res = func(self.result_row_list, self.convertion_dict)
|
res = func(self.result_row_list, self.convertion_dict)
|
||||||
return res
|
return res
|
||||||
|
|||||||
@@ -23,7 +23,8 @@ import base64
|
|||||||
import csv
|
import csv
|
||||||
import tempfile
|
import tempfile
|
||||||
import datetime
|
import datetime
|
||||||
from . import file_parser
|
# from . import file_parser
|
||||||
|
from file_parser import FileParser
|
||||||
try:
|
try:
|
||||||
import xlrd
|
import xlrd
|
||||||
except:
|
except:
|
||||||
@@ -36,7 +37,7 @@ class GenericFileParser(FileParser):
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
def __init__(self, parse_name = None, ftype='csv'):
|
def __init__(self, parse_name, ftype='csv'):
|
||||||
convertion_dict = {
|
convertion_dict = {
|
||||||
'ref': unicode,
|
'ref': unicode,
|
||||||
'label': unicode,
|
'label': unicode,
|
||||||
@@ -48,7 +49,7 @@ class GenericFileParser(FileParser):
|
|||||||
keys_to_validate = ['ref', 'label', 'date', 'amount', 'commission_amount']
|
keys_to_validate = ['ref', 'label', 'date', 'amount', 'commission_amount']
|
||||||
|
|
||||||
|
|
||||||
super(self,GenericFileParser).__init__(parser_for = parse_name, keys_to_validate={}, ftype='csv', convertion_dict=None ):
|
super(GenericFileParser,self).__init__(parse_name, keys_to_validate=keys_to_validate, ftype=ftype, convertion_dict=convertion_dict)
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def parser_for(cls, parser_name):
|
def parser_for(cls, parser_name):
|
||||||
|
|||||||
@@ -19,6 +19,7 @@
|
|||||||
#
|
#
|
||||||
##############################################################################
|
##############################################################################
|
||||||
import base64
|
import base64
|
||||||
|
import csv
|
||||||
|
|
||||||
|
|
||||||
def UnicodeDictReader(utf8_data, **kwargs):
|
def UnicodeDictReader(utf8_data, **kwargs):
|
||||||
@@ -31,7 +32,7 @@ class BankStatementImportParser(object):
|
|||||||
format to import in a bank statement"""
|
format to import in a bank statement"""
|
||||||
|
|
||||||
|
|
||||||
def __init__(self, parser_name = None, *args, **kwargs):
|
def __init__(self, parser_name, *args, **kwargs):
|
||||||
# The name of the parser as it will be called
|
# The name of the parser as it will be called
|
||||||
self.parser_name = parser_name
|
self.parser_name = parser_name
|
||||||
# The result as a list of row
|
# The result as a list of row
|
||||||
@@ -97,12 +98,12 @@ class BankStatementImportParser(object):
|
|||||||
self.filebuffer = filebuffer
|
self.filebuffer = filebuffer
|
||||||
else:
|
else:
|
||||||
raise Exception(_('No buffer file given.'))
|
raise Exception(_('No buffer file given.'))
|
||||||
self._format(args, kwargs)
|
self._format(*args, **kwargs)
|
||||||
self._pre(args, kwargs)
|
self._pre(*args, **kwargs)
|
||||||
self._parse(args, kwargs)
|
self._parse(*args, **kwargs)
|
||||||
self._validate(args, kwargs)
|
self._validate(*args, **kwargs)
|
||||||
self._post(args, kwargs)
|
self._post(*args, **kwargs)
|
||||||
return self.result_row_list,
|
return self.result_row_list
|
||||||
|
|
||||||
def itersubclasses(cls, _seen=None):
|
def itersubclasses(cls, _seen=None):
|
||||||
"""
|
"""
|
||||||
|
|||||||
@@ -24,14 +24,17 @@ import datetime
|
|||||||
import netsvc
|
import netsvc
|
||||||
logger = netsvc.Logger()
|
logger = netsvc.Logger()
|
||||||
from openerp.osv.orm import Model, fields
|
from openerp.osv.orm import Model, fields
|
||||||
|
from openerp.osv import fields, osv
|
||||||
# from account_statement_base_import.parser.file_parser import FileParser
|
# from account_statement_base_import.parser.file_parser import FileParser
|
||||||
from parser import new_bank_statement_parser
|
from parser import new_bank_statement_parser
|
||||||
|
import sys
|
||||||
|
import traceback
|
||||||
|
|
||||||
class AccountStatementProfil(Model):
|
class AccountStatementProfil(Model):
|
||||||
_inherit = "account.statement.profil"
|
_inherit = "account.statement.profil"
|
||||||
|
|
||||||
|
|
||||||
def get_type_selection(self, cr, uid, context=None):
|
def get_import_type_selection(self, cr, uid, context=None):
|
||||||
"""
|
"""
|
||||||
Has to be inherited to add parser
|
Has to be inherited to add parser
|
||||||
"""
|
"""
|
||||||
@@ -50,10 +53,12 @@ class AccountStatementProfil(Model):
|
|||||||
}
|
}
|
||||||
|
|
||||||
def write_logs_after_import(self, cr, uid, ids, statement_id, num_lines, context):
|
def write_logs_after_import(self, cr, uid, ids, statement_id, num_lines, context):
|
||||||
|
if type(ids) is int:
|
||||||
|
ids = [ids]
|
||||||
for id in ids:
|
for id in ids:
|
||||||
log = self.read(cr, uid, id, ['rec_log'], context=context)['rec_log']
|
log = self.read(cr, uid, id, ['rec_log'], context=context)['rec_log']
|
||||||
log_line = log and log.split("\n") or []
|
log_line = log and log.split("\n") or []
|
||||||
import_date = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
import_date = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
||||||
log_line[0:0] = [import_date + ' : '
|
log_line[0:0] = [import_date + ' : '
|
||||||
+ _("Bank Statement ID %s have been imported with %s lines ") %(statement_id, num_lines)]
|
+ _("Bank Statement ID %s have been imported with %s lines ") %(statement_id, num_lines)]
|
||||||
log = "\n".join(log_line)
|
log = "\n".join(log_line)
|
||||||
@@ -62,6 +67,69 @@ class AccountStatementProfil(Model):
|
|||||||
"Bank Statement ID %s have been imported with %s lines "%(statement_id, num_lines))
|
"Bank Statement ID %s have been imported with %s lines "%(statement_id, num_lines))
|
||||||
return True
|
return True
|
||||||
|
|
||||||
|
def create_global_commission_line(self, cr, uid, commission_global_amount,
|
||||||
|
result_row_list, profile, statement_id, context):
|
||||||
|
"""Create the global commission line if there is one. The global commission is computed by
|
||||||
|
summing the commission column of each row. Feel free to override the methode to compute
|
||||||
|
your own commission line from the result_row_list.
|
||||||
|
:params: cr: The DB Cursor
|
||||||
|
:params: uid: int/long ID of the current user in the system
|
||||||
|
:params: commission_global_amount: float
|
||||||
|
:params: result_row_list: [{'key':value}]
|
||||||
|
:params: profile: browserecord of account.statement.profile
|
||||||
|
:params: statement_id : int/long of the current importing statement ID
|
||||||
|
:params: context: global context
|
||||||
|
return: an ID of the statement line that represent the global commission
|
||||||
|
for the statement.
|
||||||
|
"""
|
||||||
|
res = False
|
||||||
|
if commission_global_amount:
|
||||||
|
partner_id = profile.partner_id and profile.partner_id.id or False
|
||||||
|
commission_account_id = profile.commission_account_id and profile.commission_account_id.id or False
|
||||||
|
commission_analytic_id = profile.commission_analytic_id and profile.commission_analytic_id.id or False
|
||||||
|
statement_line_obj = self.pool.get('account.bank.statement.line')
|
||||||
|
comm_values = {
|
||||||
|
'name': 'IN '+ _('Commission line'),
|
||||||
|
'date': datetime.datetime.now().date(),
|
||||||
|
'amount': commission_global_amount,
|
||||||
|
'partner_id': partner_id,
|
||||||
|
'type': 'general',
|
||||||
|
'statement_id': statement_id,
|
||||||
|
'account_id': commission_account_id,
|
||||||
|
'ref': 'commission',
|
||||||
|
'analytic_account_id': commission_analytic_id,
|
||||||
|
# !! We set the already_completed so auto-completion will not update those values !
|
||||||
|
'already_completed': True,
|
||||||
|
}
|
||||||
|
res = statement_line_obj.create(cr, uid,
|
||||||
|
comm_values,
|
||||||
|
context=context)
|
||||||
|
return res
|
||||||
|
|
||||||
|
def prepare_statetement_lines_vals(self, cursor, uid, parser_line,
|
||||||
|
account_payable, account_receivable, statement_id, context):
|
||||||
|
"""Hook to change the values of a line. Overide it to compute or change
|
||||||
|
the account or any other values (e.g. if a line is the global commission)"""
|
||||||
|
values = {
|
||||||
|
'name': parser_line.get('label', parser_line.get('ref','/')),
|
||||||
|
'date': parser_line.get('date', datetime.datetime.now().date()),
|
||||||
|
'amount': parser_line['amount'],
|
||||||
|
'ref': parser_line['ref'],
|
||||||
|
'type': 'customer',
|
||||||
|
'statement_id': statement_id,
|
||||||
|
'label': parser_line.get('label',''),
|
||||||
|
'commission_amount': parser_line.get('commission_amount', 0.0),
|
||||||
|
#'account_id': journal.default_debit_account_id
|
||||||
|
}
|
||||||
|
values['account_id'] = statement_obj.get_account_for_counterpart(
|
||||||
|
cursor,
|
||||||
|
uid,
|
||||||
|
parser_line['amount'],
|
||||||
|
account_receivable,
|
||||||
|
account_payable
|
||||||
|
)
|
||||||
|
return values
|
||||||
|
|
||||||
def statement_import(self, cursor, uid, ids, profile_id, file_stream, ftype="csv", context=None):
|
def statement_import(self, cursor, uid, ids, profile_id, file_stream, ftype="csv", context=None):
|
||||||
"""Create a bank statement with the given profile and parser. It will fullfill the bank statement
|
"""Create a bank statement with the given profile and parser. It will fullfill the bank statement
|
||||||
with the values of the file providen, but will not complete data (like finding the partner, or
|
with the values of the file providen, but will not complete data (like finding the partner, or
|
||||||
@@ -76,69 +144,34 @@ class AccountStatementProfil(Model):
|
|||||||
raise osv.except_osv(
|
raise osv.except_osv(
|
||||||
_("No Profile !"),
|
_("No Profile !"),
|
||||||
_("You must provide a valid profile to import a bank statement !"))
|
_("You must provide a valid profile to import a bank statement !"))
|
||||||
else:
|
|
||||||
prof = prof_obj.browse(cursor,uid,profile_id,context)
|
prof = prof_obj.browse(cursor,uid,profile_id,context)
|
||||||
partner_id = prof.partner_id and prof.partner_id.id or False
|
|
||||||
commission_account_id = prof.commission_account_id and prof.commission_account_id.id or False
|
|
||||||
commission_analytic_id = prof.commission_analytic_id and prof.commission_analytic_id.id or False
|
|
||||||
|
|
||||||
parser = new_bank_statement_parser(parse_name=prof.import_type, ftype=ftype)
|
parser = new_bank_statement_parser(prof.import_type, ftype=ftype)
|
||||||
result_row_list = parser.parse(file_stream)
|
result_row_list = parser.parse(file_stream)
|
||||||
|
|
||||||
# Check all key are present in account.bank.statement.line !!
|
# Check all key are present in account.bank.statement.line !!
|
||||||
parsed_cols = self.result_row_list[0].keys()
|
parsed_cols = result_row_list[0].keys()
|
||||||
for col in parsed_cols:
|
for col in parsed_cols:
|
||||||
if col not in statement_line_obj.__columns__:
|
if col not in statement_line_obj._columns:
|
||||||
raise osv.except_osv(
|
raise osv.except_osv(
|
||||||
_("Missing column !"),
|
_("Missing column !"),
|
||||||
_("Column %s you try to import is not present in the bank statement line !") %(col))
|
_("Column %s you try to import is not present in the bank statement line !") %(col))
|
||||||
|
|
||||||
statement_id = statement_obj.create(cursor,uid,{'profile_id':prof.id,},context)
|
statement_id = statement_obj.create(cursor,uid,{'profile_id':prof.id,},context)
|
||||||
account_receivable, account_payable = self.get_default_pay_receiv_accounts(cursor, uid, context)
|
account_receivable, account_payable = statement_obj.get_default_pay_receiv_accounts(cursor, uid, context)
|
||||||
commission_global_amount = 0.0
|
commission_global_amount = 0.0
|
||||||
try:
|
try:
|
||||||
# Record every line in the bank statement and compute the global commission
|
# Record every line in the bank statement and compute the global commission
|
||||||
# based on the commission_amount column
|
# based on the commission_amount column
|
||||||
for line in result_row_list:
|
for line in result_row_list:
|
||||||
line_partner_id = False
|
|
||||||
line_to_reconcile = False
|
|
||||||
|
|
||||||
commission_global_amount += line.get('commission_amount', 0.0)
|
commission_global_amount += line.get('commission_amount', 0.0)
|
||||||
values = {
|
values = self.prepare_statetement_lines_vals(cursor, uid, line, account_payable,
|
||||||
'name': line.get('label', line.get('ref','/')),
|
account_receivable, statement_id, context)
|
||||||
'date': line.get('date', datetime.datetime.now().date()),
|
|
||||||
'amount': line['amount'],
|
|
||||||
'ref': line['ref'],
|
|
||||||
'type': 'customer',
|
|
||||||
'statement_id': statement_id,
|
|
||||||
#'account_id': journal.default_debit_account_id
|
|
||||||
}
|
|
||||||
values['account_id'] = self.get_account_for_counterpart(
|
|
||||||
cursor,
|
|
||||||
uid,
|
|
||||||
line['amount'],
|
|
||||||
account_receivable,
|
|
||||||
account_payable
|
|
||||||
)
|
|
||||||
# we finally create the line in system
|
# we finally create the line in system
|
||||||
statement_line_obj.create(cursor, uid, values, context=context)
|
statement_line_obj.create(cursor, uid, values, context=context)
|
||||||
|
|
||||||
# we create commission line
|
# we create commission line
|
||||||
if commission_global_amount:
|
self.create_global_commission_line(cursor, uid, commission_global_amount,
|
||||||
comm_values = {
|
result_row_list, prof, statement_id, context)
|
||||||
'name': 'IN '+ _('Commission line'),
|
|
||||||
'date': datetime.datetime.now().date(),
|
|
||||||
'amount': commission_global_amount,
|
|
||||||
'partner_id': partner_id,
|
|
||||||
'type': 'general',
|
|
||||||
'statement_id': statement_id,
|
|
||||||
'account_id': commission_account_id,
|
|
||||||
'ref': 'commission',
|
|
||||||
'analytic_account_id': commission_analytic_id
|
|
||||||
}
|
|
||||||
statement_line_obj.create(cursor, uid,
|
|
||||||
comm_values,
|
|
||||||
context=context)
|
|
||||||
|
|
||||||
attachment_obj.create(
|
attachment_obj.create(
|
||||||
cursor,
|
cursor,
|
||||||
@@ -158,16 +191,17 @@ class AccountStatementProfil(Model):
|
|||||||
self.button_auto_completion(cursor, uid, statement_id, context)
|
self.button_auto_completion(cursor, uid, statement_id, context)
|
||||||
|
|
||||||
# Write the needed log infos on profile
|
# Write the needed log infos on profile
|
||||||
self.write_logs_after_import(self, cr, uid, prof.id, statement_id,
|
self.write_logs_after_import(cursor, uid, prof.id, statement_id,
|
||||||
len(result_row_list), context)
|
len(result_row_list), context)
|
||||||
|
|
||||||
except Exception, exc:
|
except Exception, exc:
|
||||||
logger.notifyChannel("Statement import",
|
|
||||||
netsvc.LOG_ERROR,
|
|
||||||
_("Statement can not be created %s") %(exc,))
|
|
||||||
|
|
||||||
statement_obj.unlink(cursor, uid, [statement_id])
|
statement_obj.unlink(cursor, uid, [statement_id])
|
||||||
raise exc
|
error_type, error_value, trbk = sys.exc_info()
|
||||||
|
st = "Error: %s\nDescription: %s\nTraceback:" % (error_type.__name__, error_value)
|
||||||
|
st += ''.join(traceback.format_tb(trbk, 30))
|
||||||
|
raise osv.except_osv(
|
||||||
|
_("Statement import error"),
|
||||||
|
_("The statement cannot be created : %s") %(st))
|
||||||
return statement_id
|
return statement_id
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -10,22 +10,22 @@
|
|||||||
<field name="type">form</field>
|
<field name="type">form</field>
|
||||||
<field name="arch" type="xml">
|
<field name="arch" type="xml">
|
||||||
<field name="bank_statement_prefix" position="after">
|
<field name="bank_statement_prefix" position="after">
|
||||||
<separator colspan="4" String="Import related infos"/>
|
<separator colspan="4" string="Import related infos"/>
|
||||||
<field name="launch_import_completion"/>
|
<field name="launch_import_completion"/>
|
||||||
<field name="last_import_date"/>
|
<field name="last_import_date"/>
|
||||||
|
<field name="import_type"/>
|
||||||
<button name="%(account_statement_base_import.statement_importer_action)d"
|
<button name="%(account_statement_base_import.statement_importer_action)d"
|
||||||
string="Import Bank Statement"
|
string="Import Bank Statement"
|
||||||
type="action" icon="gtk-ok"
|
type="action" icon="gtk-ok"
|
||||||
colspan = "2"/>
|
colspan = "2"/>
|
||||||
<!-- <button icon="gtk-ok" name="launch_import_bank_statement" string="Import Bank Statement" type="object"/> -->
|
<separator colspan="4" string="Import Logs"/>
|
||||||
<separator colspan="4" String="Import Logs"/>
|
|
||||||
<field name="rec_log" colspan="4" nolabel="1"/>
|
<field name="rec_log" colspan="4" nolabel="1"/>
|
||||||
</field>
|
</field>
|
||||||
</field>
|
</field>
|
||||||
</record>
|
</record>
|
||||||
|
|
||||||
<record id="bank_statement_view_form" model="ir.ui.view">
|
<record id="bank_statement_view_form" model="ir.ui.view">
|
||||||
<field name="name">account_bank_statement_import_base.bank_statement.view_form</field>
|
<field name="name">account_bank_statement.bank_statement.view_form</field>
|
||||||
<field name="model">account.bank.statement</field>
|
<field name="model">account.bank.statement</field>
|
||||||
<field name="inherit_id" ref="account.view_bank_statement_form" />
|
<field name="inherit_id" ref="account.view_bank_statement_form" />
|
||||||
<field name="type">form</field>
|
<field name="type">form</field>
|
||||||
|
|||||||
@@ -40,7 +40,8 @@ class CreditPartnerStatementImporter(osv.osv_memory):
|
|||||||
res = context['active_ids']
|
res = context['active_ids']
|
||||||
if len(res) > 1:
|
if len(res) > 1:
|
||||||
raise Exception (_('You cannot use this on more than one profile !'))
|
raise Exception (_('You cannot use this on more than one profile !'))
|
||||||
return res[0]
|
return res[0]
|
||||||
|
return res
|
||||||
|
|
||||||
_columns = {
|
_columns = {
|
||||||
|
|
||||||
@@ -93,7 +94,7 @@ class CreditPartnerStatementImporter(osv.osv_memory):
|
|||||||
return res
|
return res
|
||||||
|
|
||||||
def _check_extension(self, filename):
|
def _check_extension(self, filename):
|
||||||
(shortname, ftype) = os.path.splitext(file_name)
|
(shortname, ftype) = os.path.splitext(filename)
|
||||||
if not ftype:
|
if not ftype:
|
||||||
#We do not use osv exception we do not want to have it logged
|
#We do not use osv exception we do not want to have it logged
|
||||||
raise Exception(_('Please use a file with an extention'))
|
raise Exception(_('Please use a file with an extention'))
|
||||||
@@ -107,7 +108,7 @@ class CreditPartnerStatementImporter(osv.osv_memory):
|
|||||||
importer = self.browse(cursor, uid, req_id, context)
|
importer = self.browse(cursor, uid, req_id, context)
|
||||||
ftype = self._check_extension(importer.file_name)
|
ftype = self._check_extension(importer.file_name)
|
||||||
sid = self.pool.get(
|
sid = self.pool.get(
|
||||||
'account.bank.statement').statement_import(
|
'account.statement.profil').statement_import(
|
||||||
cursor,
|
cursor,
|
||||||
uid,
|
uid,
|
||||||
False,
|
False,
|
||||||
@@ -115,7 +116,7 @@ class CreditPartnerStatementImporter(osv.osv_memory):
|
|||||||
importer.input_statement,
|
importer.input_statement,
|
||||||
ftype.replace('.',''),
|
ftype.replace('.',''),
|
||||||
context=context
|
context=context
|
||||||
)
|
)
|
||||||
# obj_data = self.pool.get('ir.model.data')
|
# obj_data = self.pool.get('ir.model.data')
|
||||||
# act_obj = self.pool.get('ir.actions.act_window')
|
# act_obj = self.pool.get('ir.actions.act_window')
|
||||||
# result = obj_data.get_object_reference(cursor, uid, 'account_statement_import', 'action_treasury_statement_tree')
|
# result = obj_data.get_object_reference(cursor, uid, 'account_statement_import', 'action_treasury_statement_tree')
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import datetime
|
|||||||
import netsvc
|
import netsvc
|
||||||
logger = netsvc.Logger()
|
logger = netsvc.Logger()
|
||||||
from openerp.osv.orm import Model, fields
|
from openerp.osv.orm import Model, fields
|
||||||
|
from openerp.osv import fields, osv
|
||||||
|
|
||||||
class AccountStatementProfil(Model):
|
class AccountStatementProfil(Model):
|
||||||
"""A Profile will contain all infos related to the type of
|
"""A Profile will contain all infos related to the type of
|
||||||
@@ -493,7 +494,7 @@ class AccountBankSatementLine(Model):
|
|||||||
res = {}
|
res = {}
|
||||||
obj_partner = self.pool.get('res.partner')
|
obj_partner = self.pool.get('res.partner')
|
||||||
obj_stat = self.pool.get('account.bank.statement')
|
obj_stat = self.pool.get('account.bank.statement')
|
||||||
receiv_account, pay_account, account_id = False
|
receiv_account = pay_account = account_id = False
|
||||||
# If profil has a receivable_account_id, we return it in any case
|
# If profil has a receivable_account_id, we return it in any case
|
||||||
if profile_id:
|
if profile_id:
|
||||||
profile = self.pool.get("account.statement.profil").browse(cr,uid,profile_id)
|
profile = self.pool.get("account.statement.profil").browse(cr,uid,profile_id)
|
||||||
|
|||||||
@@ -188,13 +188,14 @@
|
|||||||
|
|
||||||
</field>
|
</field>
|
||||||
</record>
|
</record>
|
||||||
|
|
||||||
|
|
||||||
<act_window id="act_bank_statement_from_profile"
|
<act_window id="act_bank_statement_from_profile"
|
||||||
name="Open Statements"
|
name="Open Statements"
|
||||||
res_model="account.bank.statement"
|
res_model="account.bank.statement"
|
||||||
src_model="account.statement.profil"
|
src_model="account.statement.profil"
|
||||||
context="{'search_default_profile_id': [active_id]}"
|
domain="[('profile_id','=',active_id),]"
|
||||||
view_type="tree"/>
|
view_type="form"/>
|
||||||
|
|
||||||
|
|
||||||
</data>
|
</data>
|
||||||
|
|||||||
Reference in New Issue
Block a user