[MRG] Port of credit control to version 7.0

This commit is contained in:
unknown
2013-09-18 13:37:52 +02:00
committed by Joel Grand-Guillaume
42 changed files with 5162 additions and 2172 deletions

View File

@@ -18,11 +18,13 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from . import mail
from . import run
from . import line
from . import account
from . import partner
from . import policy
from . import company
import wizard
import report
from . import wizard
from . import report
from . import invoice

View File

@@ -18,13 +18,14 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
{'name' : 'Account Credit Control',
'version' : '0.1',
'author' : 'Camptocamp',
{'name': 'Account Credit Control',
'version': '0.1',
'author': 'Camptocamp',
'maintainer': 'Camptocamp',
'category': 'Finance',
'complexity': "normal",
'depends' : ['base', 'account', 'email_template', 'report_webkit'],
'depends': ['base', 'account',
'email_template', 'report_webkit'],
'description': """
Credit Control
==============
@@ -57,24 +58,21 @@ On each generated line, you have many choices:
* Change the state (so you can ignore or reopen lines)
""",
'website': 'http://www.camptocamp.com',
'init_xml': ["data.xml",
],
'update_xml': ["line_view.xml",
"account_view.xml",
"partner_view.xml",
"policy_view.xml",
"run_view.xml",
"company_view.xml",
"wizard/credit_control_emailer_view.xml",
"wizard/credit_control_marker_view.xml",
"wizard/credit_control_printer_view.xml",
"report/report.xml",
"security/ir.model.access.csv",
],
'data': ["report/report.xml",
"data.xml",
"line_view.xml",
"account_view.xml",
"partner_view.xml",
"policy_view.xml",
"run_view.xml",
"company_view.xml",
"wizard/credit_control_emailer_view.xml",
"wizard/credit_control_marker_view.xml",
"wizard/credit_control_printer_view.xml",
"security/ir.model.access.csv"],
'demo_xml': ["credit_control_demo.xml"],
'tests': [],
'installable': False,
'installable': True,
'license': 'AGPL-3',
'application': True
}
}

View File

@@ -18,56 +18,58 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv.orm import Model, fields
from openerp.osv import orm, fields
class AccountAccount(Model):
class AccountAccount(orm.Model):
"""Add a link to a credit control policy on account.account"""
_inherit = "account.account"
_columns = {
'credit_control_line_ids': fields.one2many('credit.control.line',
'account_id',
string='Credit Lines',
readonly=True)
}
'credit_control_line_ids':
fields.one2many('credit.control.line',
'account_id',
string='Credit Lines',
readonly=True),
}
def copy_data(self, cr, uid, id, default=None, context=None):
if default is None:
default = {}
else:
default = default.copy()
default['credit_control_line_ids'] = False
return super(AccountAccount, self).copy_data(
cr, uid, id, default=default, context=context)
class AccountInvoice(Model):
class AccountInvoice(orm.Model):
"""Add a link to a credit control policy on account.account"""
_inherit = "account.invoice"
_columns = {
'credit_policy_id': fields.many2one('credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy "
"used for this invoice. "
"If nothing is defined, "
"it will use the account "
"setting or the partner "
"setting.")),
'credit_control_line_ids': fields.one2many('credit.control.line',
'invoice_id',
string='Credit Lines',
readonly=True)
}
def action_move_create(self, cr, uid, ids, context=None):
""" Write the id of the invoice in the generated moves. """
res = super(AccountInvoice, self).action_move_create(cr, uid, ids, context=context)
for inv in self.browse(cr, uid, ids, context=context):
if inv.move_id:
for line in inv.move_id.line_id:
line.write({'invoice_id': inv.id})
return res
class AccountMoveLine(Model):
_inherit = "account.move.line"
_columns = {'invoice_id': fields.many2one('account.invoice', 'Invoice')}
'credit_policy_id':
fields.many2one('credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy used for this "
"invoice. If nothing is defined, it will "
"use the account setting or the partner "
"setting.")
),
'credit_control_line_ids':
fields.one2many('credit.control.line',
'invoice_id',
string='Credit Lines',
readonly=True),
}
def copy_data(self, cr, uid, id, default=None, context=None):
if default is None:
default = {}
else:
default = default.copy()
default = default.copy()
default['credit_control_line_ids'] = False
return super(AccountInvoice, self).copy_data(
cr, uid, id, default=default, context=context)

View File

@@ -17,10 +17,13 @@
<field name="arch" type="xml">
<notebook position="inside">
<page string="Credit Control"
groups="account_credit_control.group_account_credit_control_manager,account_credit_control.group_account_credit_control_user,group_account_credit_control_info">
<field name="credit_policy_id" widget="selection"/>
groups="account_credit_control.group_account_credit_control_manager,account_credit_control.group_account_credit_control_user,account_credit_control.group_account_credit_control_info">
<label string="Force credit control policy:" />
<field name="credit_policy_id" widget="selection"
groups="account_credit_control.group_account_credit_control_manager,account_credit_control.group_account_credit_control_user,account_credit_control.group_account_credit_control_info"/>
<newline/>
<field name="credit_control_line_ids" colspan="4" nolabel="1"/>
<field name="credit_control_line_ids" colspan="4" nolabel="1"
groups="account_credit_control.group_account_credit_control_manager,account_credit_control.group_account_credit_control_user,account_credit_control.group_account_credit_control_info"/>
</page>
</notebook>
</field>

View File

@@ -18,23 +18,21 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv.orm import Model, fields
from openerp.osv import orm, fields
class ResCompany(Model):
class ResCompany(orm.Model):
"""Add credit control parameters"""
_inherit = 'res.company'
_columns = {
'credit_control_tolerance': fields.float('Credit Control Tolerance'),
# This is not a property on the partner because we cannot search
# on fields.property (subclass fields.function).
'credit_policy_id': fields.many2one(
'credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy used on partners by default. This "
"setting can be overriden on partners or invoices.")),
}
_columns = {'credit_control_tolerance': fields.float('Credit Control Tolerance'),
# This is not a property on the partner because we cannot search
# on fields.property (subclass fields.function).
'credit_policy_id': fields.many2one('credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy used on partners"
" by default. This setting can be overriden"
" on partners or invoices.")),
}
_defaults = {"credit_control_tolerance": 0.1}

View File

@@ -4,73 +4,17 @@
<record id="email_template_credit_control_base" model="email.template">
<field name="name">Credit Control Email</field>
<field name="email_from">noreply@localhost</field>
<field name="subject">Credit Control: (${object.current_policy_level.name or 'n/a' })</field>
<field name="subject">Credit Control: (${object.current_policy_level.name or 'n/a'})</field>
<field name="email_to">${object.get_email() or ''}</field>
<field name="model_id" ref="model_credit_control_communication"/>
<field name="auto_delete" eval="True"/>
<field name="lang">${object.get_contact_address().lang or 'en_US'}</field>
<field name="report_template" ref="report_webkit_html"/>
<field name="body_html"><![CDATA[
<%page args="object, user=None, ctx=None, quote=None, format_exception=True, mode='email'" />
%if mode != 'pdf':
<!-- your css here -->
<style type="text/css">
</style>
%endif
<div>
<p>Dear ${object.partner_id.name or ''},</p>
<pre class="custom_text">${object.current_policy_level.custom_text}</pre>
<table style="border: 1px solid" width="100%">
<caption><b>Summary</b></caption>
<tr>
<th>date due</th>
<th>Amount due</th>
<th>Amount balance</th>
<th>Invoice number</th>
</tr>
%for line in object.credit_control_line_ids:
<tr>
<td>${line.date_due}</td>
<td>${line.amount_due}</td>
<td>${line.balance_due}</td>
%if line.invoice_id:
<td>${line.invoice_id.number}</td>
%else:
<td>n/a</td>
%endif
%endfor
</table>
Dear ${object.get_contact_address().name or ''}
<br/>
<br/>
<p>If you have any question, do not hesitate to contact us.</p>
<p>Thank you for choosing ${object.company_id.name}! </p>
-- more info here --
<p>${object.user_id.name} ${object.user_id.user_email and '<%s>'%(object.user_id.user_email) or ''}<br/>
${object.company_id.name}<br/>
% if object.company_id.street:
${object.company_id.street or ''}<br/>
% endif
% if object.company_id.street2:
${object.company_id.street2}<br/>
% endif
% if object.company_id.city or object.company_id.zip:
${object.company_id.zip or ''} ${object.company_id.city or ''}<br/>
% endif
% if object.company_id.country_id:
${object.company_id.state_id and ('%s, ' % object.company_id.state_id.name) or ''} ${object.company_id.country_id.name or ''}<br/>
% endif
% if object.company_id.phone:
Phone: ${object.company_id.phone}<br/>
% endif
% if object.company_id.website:
${object.company_id.website or ''}<br/>
% endif
${object.current_policy_level.custom_mail_text}
]]></field>
</record>
@@ -96,17 +40,22 @@
<field name="email_template_id" ref="email_template_credit_control_base"/>
<field name="policy_id" ref="credit_control_3_time"/>
<field name="channel">email</field>
<field name="custom_text">Dear Sir or Madam,
Our records indicate that we have not received the payment of the
above mentioned invoice (copy attached for your convenience). If it
has already been sent, please disregard this notice. If not, please
proceed with payment within 10 days.
<field name="custom_text">Our records indicate that we have not received the payment of the above mentioned invoice.
If it has already been sent, please disregard this notice. If not, please proceed with payment within 10 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards,
</field>
Best regards
</field>
<field name="custom_mail_text">Our records indicate that we have not received the payment of the above mentioned invoice (copy attached for your convenience).
If it has already been sent, please disregard this notice. If not, please proceed with payment within 10 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
</record>
<record model="credit.control.policy.level"
@@ -118,17 +67,20 @@ Best regards,
<field name="email_template_id" ref="email_template_credit_control_base"/>
<field name="policy_id" ref="credit_control_3_time"/>
<field name="channel">email</field>
<field name="custom_text">Dear Sir or Madam,
Our records indicate that we have not yet received the payment of the
above mentioned invoice (copy attached for your convenience) despite
our first reminder. If it has already been sent, please disregard
this notice. If not, please proceed with payment within 5 days.
<field name="custom_text">Our records indicate that we have not yet received the payment of the above mentioned invoice despite our first reminder.
If it has already been sent, please disregard this notice. If not, please proceed with payment within 5 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards,
</field>
Best regards
</field>
<field name="custom_mail_text">Our records indicate that we have not yet received the payment of the above mentioned invoice (copy attached for your convenience) despite our first reminder.
If it has already been sent, please disregard this notice. If not, please proceed with payment within 5 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
</record>
<record model="credit.control.policy.level"
@@ -140,22 +92,30 @@ Best regards,
<field name="email_template_id" ref="email_template_credit_control_base"/>
<field name="policy_id" ref="credit_control_3_time"/>
<field name="channel">letter</field>
<field name="custom_text">Dear Sir or Madam,
<field name="custom_text">
Our records indicate that we still have not received the payment of the above mentioned invoice despite our two reminders.
If payment have already been sent, please disregard this notice. If not, please proceed with payment.
If your payment has not been received in the next 5 days, your file will be transfered to our debt collection agency.
Our records indicate that we still have not received the payment of
the above mentioned invoice (copy attached) despite our two reminders.
If payment have already been sent, please disregard this notice. If
not, please proceed with payment. If your payment has not been
received in the next 5 days, your file will be transfered to our debt
collection agency.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Thank you in advance for your anticipated cooperation in this matter.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
Best regards,
</field>
<field name="custom_mail_text">Our records indicate that we still have not received the payment of the above mentioned invoice (copy attached) despite our two reminders.
If payment have already been sent, please disregard this notice. If not, please proceed with payment.
If your payment has not been received in the next 5 days, your file will be transfered to our debt collection agency.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
</record>
<!-- policy 2 -->
@@ -173,17 +133,20 @@ Best regards,
<field name="email_template_id" ref="email_template_credit_control_base"/>
<field name="policy_id" ref="credit_control_2_time"/>
<field name="channel">email</field>
<field name="custom_text">Dear Sir or Madam,
<field name="custom_text">Our records indicate that we have not received the payment of the above mentioned invoice.
If it has already been sent, please disregard this notice. If not, please proceed with payment within 10 days.
Our records indicate that we have not received the payment of the
above mentioned invoice (copy attached for your convenience). If it
has already been sent, please disregard this notice. If not, please
proceed with payment within 10 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
<field name="custom_mail_text">Our records indicate that we have not received the payment of the above mentioned invoice (copy attached for your convenience).
If it has already been sent, please disregard this notice. If not, please proceed with payment within 10 days.
Thank you in advance for your anticipated cooperation in this matter.
Best regards,
</field>
Best regards
</field>
</record>
<record model="credit.control.policy.level"
@@ -195,41 +158,51 @@ Best regards,
<field name="email_template_id" ref="email_template_credit_control_base"/>
<field name="policy_id" ref="credit_control_2_time"/>
<field name="channel">letter</field>
<field name="custom_text">Dear Sir or Madam,
<field name="custom_text">Our records indicate that we still have not received the payment of the above mentioned invoice despite our reminder.
Our records indicate that we still have not received the payment of
the above mentioned invoice (copy attached) despite our reminder.
If payment have already been sent, please disregard this notice. If
not, please proceed with payment. If your payment has not been
received in the next 5 days, your file will be transfered to our debt
collection agency.
If payment have already been sent, please disregard this notice. If not, please proceed with payment.
If your payment has not been received in the next 5 days, your file will be transfered to our debt
collection agency.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Thank you in advance for your anticipated cooperation in this matter.
Thank you in advance for your anticipated cooperation in this matter.
Best regards,
</field>
Best regards
</field>
<field name="custom_mail_text">Our records indicate that we still have not received the payment of the above mentioned invoice (copy attached) despite our reminder.
If payment have already been sent, please disregard this notice. If not, please proceed with payment.
If your payment has not been received in the next 5 days, your file will be transfered to our debt
collection agency.
Should you need us to arrange a payment plan for you, please advise.
A customer account statement is enclosed for you convenience.
Thank you in advance for your anticipated cooperation in this matter.
Best regards
</field>
</record>
<record id="group_account_credit_control_manager" model="res.groups">
<field name="name">Credit Control Manager</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
<field name="name">Credit Control Manager</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
</record>
<record id="group_account_credit_control_user" model="res.groups" context="{'noadmin':True}">
<field name="name">Credit Control User</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
<field name="name">Credit Control User</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
</record>
<record id="group_account_credit_control_info" model="res.groups" context="{'noadmin':True}">
<field name="name">Credit Control Info</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
<field name="name">Credit Control Info</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
</record>
<record id="base.main_company" model="res.company">
<field name="credit_policy_id" ref="credit_control_3_time"/>
<field name="credit_policy_id" ref="credit_control_3_time"/>
</record>
</data>

View File

@@ -1,787 +0,0 @@
# Translation of OpenERP Server.
# This file contains the translation of the following modules:
# * account_credit_control
#
msgid ""
msgstr ""
"Project-Id-Version: OpenERP Server 6.1\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2012-11-07 13:23+0000\n"
"PO-Revision-Date: 2012-11-07 13:23+0000\n"
"Last-Translator: <>\n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: \n"
"Plural-Forms: \n"
#. module: account_credit_control
#: model:credit.control.policy.level,custom_text:account_credit_control.2_time_1
#: model:credit.control.policy.level,custom_text:account_credit_control.3_time_1
msgid "Dear Sir or Madam,\n"
"\n"
"Our records indicate that we have not received the payment of the\n"
"above mentioned invoice (copy attached for your convenience). If it\n"
"has already been sent, please disregard this notice. If not, please\n"
"proceed with payment within 10 days.\n"
"\n"
"Thank you in advance for your anticipated cooperation in this matter.\n"
"\n"
"Best regards,\n"
""
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy.level,custom_text:0
msgid "Custom Message"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_mailer
msgid "Mass credit line mailer"
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "More..."
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "Group By..."
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,name:account_credit_control.credit_control_run
#: model:ir.ui.menu,name:account_credit_control.credit_control_run_menu
msgid "Credit Control Run"
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy.level,computation_mode:0
msgid "Compute Mode"
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_emailer_wizard
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_emailer_wizard_menu_action
msgid "Send By Email"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_line
msgid "A credit control line"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,move_line_id:0
msgid "Move line"
msgstr ""
#. module: account_credit_control
#: model:res.groups,name:account_credit_control.group_account_credit_control_info
msgid "Credit Control Info"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_emailer
msgid "Mass credit line emailer"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,account_id:0
#: view:credit.control.lines:0
#: model:ir.model,name:account_credit_control.model_account_account
msgid "Account"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.policy.level,computation_mode:0
msgid "Due Date"
msgstr ""
#. module: account_credit_control
#: field:credit.control.communication,current_policy_level:0
#: field:credit.control.line,level:0
#: view:credit.control.lines:0
#: field:credit.control.policy.level,level:0
msgid "Level"
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy.level,delay_days:0
msgid "Delay (in days)"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_communication
msgid "credit control communication"
msgstr ""
#. module: account_credit_control
#: sql_constraint:account.move.line:0
msgid "Wrong credit or debit value in accounting entry !"
msgstr ""
#. module: account_credit_control
#: constraint:account.account:0
msgid "Error ! You can not create recursive accounts."
msgstr ""
#. module: account_credit_control
#: view:credit.control.emailer:0
msgid "Send emails for the selected lines"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_marker
msgid "Mass marker"
msgstr ""
#. module: account_credit_control
#: field:account.invoice,credit_policy_id:0
#: field:res.company,credit_policy_id:0
#: field:res.partner,credit_policy_id:0
msgid "Credit Control Policy"
msgstr ""
#. module: account_credit_control
#: view:account.invoice:0
msgid "Credit control"
msgstr ""
#. module: account_credit_control
#: constraint:account.move.line:0
msgid "The date of your Journal Entry is not in the defined period! You should change the date or remove this constraint from the journal."
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "New lines"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,date_sent:0
msgid "Sent date"
msgstr ""
#. module: account_credit_control
#: view:credit.control.policy:0
#: field:credit.control.policy,account_ids:0
msgid "Accounts"
msgstr ""
#. module: account_credit_control
#: field:credit.control.communication,partner_id:0
#: field:credit.control.line,partner_id:0
#: view:credit.control.lines:0
#: model:ir.model,name:account_credit_control.model_res_partner
msgid "Partner"
msgstr ""
#. module: account_credit_control
#: view:credit.control.emailer:0
msgid "Send the emails"
msgstr ""
#. module: account_credit_control
#: view:credit.control.marker:0
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_marker_wizard
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_marker_wizard_menu_action
msgid "Change Lines' State"
msgstr ""
#. module: account_credit_control
#: model:credit.control.policy.level,custom_text:account_credit_control.3_time_2
msgid "Dear Sir or Madam,\n"
"\n"
"Our records indicate that we have not yet received the payment of the\n"
"above mentioned invoice (copy attached for your convenience) despite\n"
"our first reminder. If it has already been sent, please disregard\n"
"this notice. If not, please proceed with payment within 5 days.\n"
"\n"
"Thank you in advance for your anticipated cooperation in this matter.\n"
"\n"
"Best regards,\n"
""
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy.level,policy_id:0
msgid "Related Policy"
msgstr ""
#. module: account_credit_control
#: sql_constraint:account.account:0
msgid "The code of the account must be unique per company !"
msgstr ""
#. module: account_credit_control
#: constraint:res.company:0
msgid "Error! You can not create recursive companies."
msgstr ""
#. module: account_credit_control
#: view:credit.control.policy:0
#: view:credit.control.policy.level:0
msgid "Mail and reporting"
msgstr ""
#. module: account_credit_control
#: view:credit.control.printer:0
msgid "Print"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,channel:0
#: selection:credit.control.policy.level,channel:0
msgid "Email"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,channel:0
#: view:credit.control.lines:0
#: field:credit.control.policy.level,channel:0
msgid "Channel"
msgstr ""
#. module: account_credit_control
#: help:credit.control.run,manual_ids:0
msgid "If a credit control line has been generated on a policy and the policy has been changed meantime, it has to be handled manually"
msgstr ""
#. module: account_credit_control
#: field:credit.control.printer,state:0
msgid "state"
msgstr ""
#. module: account_credit_control
#: field:credit.control.run,report:0
msgid "Report"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.policy.level,computation_mode:0
msgid "Due Date, End Of Month"
msgstr ""
#. module: account_credit_control
#: field:credit.control.marker,name:0
msgid "Mark as"
msgstr ""
#. module: account_credit_control
#: model:credit.control.policy.level,custom_text:account_credit_control.2_time_2
msgid "Dear Sir or Madam,\n"
"\n"
"Our records indicate that we still have not received the payment of\n"
"the above mentioned invoice (copy attached) despite our reminder.\n"
"If payment have already been sent, please disregard this notice. If\n"
"not, please proceed with payment. If your payment has not been\n"
"received in the next 5 days, your file will be transfered to our debt\n"
"collection agency.\n"
"\n"
"Should you need us to arrange a payment plan for you, please advise.\n"
"A customer account statement is enclosed for you convenience.\n"
"\n"
"Thank you in advance for your anticipated cooperation in this matter.\n"
"\n"
"Best regards,\n"
""
msgstr ""
#. module: account_credit_control
#: view:credit.control.run:0
#: field:credit.control.run,policy_ids:0
msgid "Policies"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,date_due:0
msgid "Due date"
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy,do_nothing:0
msgid "Do nothing"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,currency_id:0
msgid "Currency"
msgstr ""
#. module: account_credit_control
#: constraint:account.account:0
msgid "Configuration Error! \n"
"You can not define children to an account with internal type different of \"View\"! "
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_printer
msgid "Mass printer"
msgstr ""
#. module: account_credit_control
#: field:credit.control.communication,company_id:0
#: field:credit.control.line,company_id:0
#: field:credit.control.policy,company_id:0
msgid "Company"
msgstr ""
#. module: account_credit_control
#: view:credit.control.marker:0
#: model:ir.actions.act_window,help:account_credit_control.open_credit_line_marker_wizard
msgid "Change the state of the selected lines."
msgstr ""
#. module: account_credit_control
#: view:credit.control.printer:0
msgid "Print the selected lines"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,state:0
#: view:credit.control.lines:0
#: selection:credit.control.marker,name:0
#: selection:credit.control.run,state:0
msgid "Draft"
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "Credit policy"
msgstr ""
#. module: account_credit_control
#: view:credit.control.policy:0
#: view:credit.control.policy.level:0
msgid "Delay Setting"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,balance_due:0
msgid "Due balance"
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "Credit policy level"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_run
msgid "Credit control line generator"
msgstr ""
#. module: account_credit_control
#: field:credit.control.communication,user_id:0
msgid "User"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,channel:0
#: selection:credit.control.policy.level,channel:0
msgid "Letter"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_account_move_line
msgid "Journal Items"
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,help:account_credit_control.open_credit_line_printer_wizard
msgid "Print selected lines"
msgstr ""
#. module: account_credit_control
#: constraint:account.move.line:0
msgid "You can not create journal items on an account of type view."
msgstr ""
#. module: account_credit_control
#: field:credit.control.emailer,line_ids:0
#: field:credit.control.marker,line_ids:0
#: field:credit.control.printer,line_ids:0
#: model:ir.actions.act_window,name:account_credit_control.credit_control_line_action
#: model:ir.ui.menu,name:account_credit_control.credit_control_line_action_menu
#: field:res.partner,credit_control_line_ids:0
msgid "Credit Control Lines"
msgstr ""
#. module: account_credit_control
#: model:credit.control.policy.level,custom_text:account_credit_control.3_time_3
msgid "Dear Sir or Madam,\n"
"\n"
"Our records indicate that we still have not received the payment of\n"
"the above mentioned invoice (copy attached) despite our two reminders.\n"
"If payment have already been sent, please disregard this notice. If\n"
"not, please proceed with payment. If your payment has not been\n"
"received in the next 5 days, your file will be transfered to our debt\n"
"collection agency.\n"
"\n"
"Should you need us to arrange a payment plan for you, please advise.\n"
"A customer account statement is enclosed for you convenience.\n"
"\n"
"Thank you in advance for your anticipated cooperation in this matter.\n"
"\n"
"Best regards,\n"
""
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_printer_wizard
#: model:ir.actions.act_window,name:account_credit_control.open_credit_line_printer_wizard_menu_action
msgid "Print Lines"
msgstr ""
#. module: account_credit_control
#: field:credit.control.run,date:0
msgid "Controlling Date"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_policy
msgid "Define a reminder policy"
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy.level,email_template_id:0
msgid "Email Template"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,state:0
#: view:credit.control.lines:0
#: selection:credit.control.marker,name:0
msgid "Ready To Send"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_res_company
msgid "Companies"
msgstr ""
#. module: account_credit_control
#: field:credit.control.printer,mark_as_sent:0
msgid "Mark letter lines as sent"
msgstr ""
#. module: account_credit_control
#: view:credit.control.run:0
msgid "Compute Credit Control Lines"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.policy.level,computation_mode:0
msgid "Previous Reminder"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,state:0
#: view:credit.control.lines:0
msgid "Error"
msgstr ""
#. module: account_credit_control
#: sql_constraint:account.invoice:0
msgid "Invoice Number must be unique per Company!"
msgstr ""
#. module: account_credit_control
#: view:credit.control.run:0
msgid "Report and Errors"
msgstr ""
#. module: account_credit_control
#: constraint:account.account:0
msgid "Configuration Error! \n"
"You can not select an account type with a deferral method different of \"Unreconciled\" for accounts with internal type \"Payable/Receivable\"! "
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,state:0
#: field:credit.control.run,state:0
msgid "State"
msgstr ""
#. module: account_credit_control
#: help:credit.control.policy,do_nothing:0
msgid "For policies which should not generate lines or are obsolete"
msgstr ""
#. module: account_credit_control
#: field:account.account,credit_control_line_ids:0
#: field:account.invoice,credit_control_line_ids:0
#: field:credit.control.communication,credit_control_line_ids:0
#: model:ir.actions.act_window,name:account_credit_control.act_account_credit_relation_relation
#: model:ir.actions.act_window,name:account_credit_control.act_partner_credit_relation_relation
msgid "Credit Lines"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,state:0
#: selection:credit.control.marker,name:0
#: selection:credit.control.run,state:0
msgid "Done"
msgstr ""
#. module: account_credit_control
#: field:account.move.line,invoice_id:0
#: field:credit.control.line,invoice_id:0
#: view:credit.control.lines:0
#: model:ir.model,name:account_credit_control.model_account_invoice
msgid "Invoice"
msgstr ""
#. module: account_credit_control
#: view:credit.control.emailer:0
#: view:credit.control.marker:0
#: view:credit.control.printer:0
msgid "Cancel"
msgstr ""
#. module: account_credit_control
#: view:credit.control.printer:0
msgid "Close"
msgstr ""
#. module: account_credit_control
#: selection:credit.control.line,state:0
msgid "Emailing Error"
msgstr ""
#. module: account_credit_control
#: help:account.invoice,credit_policy_id:0
msgid "The Credit Control Policy used for this invoice. If nothing is defined, it will use the account setting or the partner setting."
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "Run date"
msgstr ""
#. module: account_credit_control
#: model:res.groups,name:account_credit_control.group_account_credit_control_user
msgid "Credit Control User"
msgstr ""
#. module: account_credit_control
#: model:email.template,body_html:account_credit_control.email_template_credit_control_base
msgid "\n"
" <%page args=\"object, user=None, ctx=None, quote=None, format_exception=True, mode='mail'\" />\n"
" %if mode != 'pdf':\n"
" <!-- your css here -->\n"
" <style type=\"text/css\">\n"
" </style>\n"
" %endif\n"
" <div>\n"
"\n"
" <p>Dear ${object.partner_id.name or ''},</p>\n"
"\n"
" <pre class=\"custom_text\">${object.current_policy_level.custom_text}</pre>\n"
"\n"
" <table style=\"border: 1px solid\" width=\"100%\">\n"
" <caption><b>Summary</b></caption>\n"
" <tr>\n"
" <th>date due</th>\n"
" <th>Amount due</th>\n"
" <th>Amount balance</th>\n"
" <th>Invoice number</th>\n"
" </tr>\n"
"%for line in object.credit_control_line_ids:\n"
" <tr>\n"
" <td>${line.date_due}</td>\n"
" <td>${line.amount_due}</td>\n"
" <td>${line.balance_due}</td>\n"
" %if line.invoice_id:\n"
" <td>${line.invoice_id.number}</td>\n"
" %else:\n"
" <td>n/a</td>\n"
" %endif\n"
"%endfor\n"
" </table>\n"
" <br/>\n"
" <br/>\n"
"\n"
" <p>If you have any question, do not hesitate to contact us.</p>\n"
"\n"
" <p>Thank you for choosing ${object.company_id.name}! </p>\n"
"\n"
" -- more info here --\n"
" <p>${object.user_id.name} ${object.user_id.user_email and '<%s>'%(object.user_id.user_email) or ''}<br/>\n"
" ${object.company_id.name}<br/>\n"
" % if object.company_id.street:\n"
" ${object.company_id.street or ''}<br/>\n"
"\n"
" % endif\n"
"\n"
" % if object.company_id.street2:\n"
" ${object.company_id.street2}<br/>\n"
" % endif\n"
" % if object.company_id.city or object.company_id.zip:\n"
" ${object.company_id.zip or ''} ${object.company_id.city or ''}<br/>\n"
" % endif\n"
" % if object.company_id.country_id:\n"
" ${object.company_id.state_id and ('%s, ' % object.company_id.state_id.name) or ''} ${object.company_id.country_id.name or ''}<br/>\n"
" % endif\n"
" % if object.company_id.phone:\n"
" Phone: ${object.company_id.phone}<br/>\n"
" % endif\n"
" % if object.company_id.website:\n"
" ${object.company_id.website or ''}<br/>\n"
" % endif\n"
" "
msgstr ""
#. module: account_credit_control
#: constraint:account.move.line:0
msgid "Company must be the same for its related account and period."
msgstr ""
#. module: account_credit_control
#: field:credit.control.run,manual_ids:0
msgid "Lines to handle manually"
msgstr ""
#. module: account_credit_control
#: model:ir.ui.menu,name:account_credit_control.base_credit_control_configuration_menu
#: model:ir.ui.menu,name:account_credit_control.base_credit_control_menu
msgid "Credit Control"
msgstr ""
#. module: account_credit_control
#: view:credit.control.policy:0
#: field:credit.control.policy,level_ids:0
msgid "Policy Levels"
msgstr ""
#. module: account_credit_control
#: constraint:account.move.line:0
msgid "The selected account of your Journal Entry forces to provide a secondary currency. You should remove the secondary currency on the account or select a multi-currency view on the journal."
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,policy_id:0
msgid "Policy"
msgstr ""
#. module: account_credit_control
#: model:email.template,subject:account_credit_control.email_template_credit_control_base
msgid "Credit Control: (${object.current_policy_level.name or 'n/a' })"
msgstr ""
#. module: account_credit_control
#: field:credit.control.printer,report_file:0
msgid "Generated Report"
msgstr ""
#. module: account_credit_control
#: view:credit.control.run:0
msgid "Move lines To be treated manually"
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,name:account_credit_control.credit_policy_configuration_action
#: model:ir.ui.menu,name:account_credit_control.credit_policy_configuration_action_menu
msgid "Credit Control Policies"
msgstr ""
#. module: account_credit_control
#: model:ir.actions.act_window,help:account_credit_control.open_credit_line_emailer_wizard
msgid "Send an email for the selected lines."
msgstr ""
#. module: account_credit_control
#: view:credit.control.lines:0
msgid "Sent"
msgstr ""
#. module: account_credit_control
#: constraint:credit.control.policy.level:0
msgid "The smallest level can not be of type Previous Reminder"
msgstr ""
#. module: account_credit_control
#: help:credit.control.policy,account_ids:0
msgid "This policy will be active only for the selected accounts"
msgstr ""
#. module: account_credit_control
#: help:credit.control.printer,mark_as_sent:0
msgid "Only letter lines will be marked."
msgstr ""
#. module: account_credit_control
#: view:credit.control.line:0
#: view:credit.control.lines:0
msgid "Control Credit Lines"
msgstr ""
#. module: account_credit_control
#: model:res.groups,name:account_credit_control.group_account_credit_control_manager
msgid "Credit Control Manager"
msgstr ""
#. module: account_credit_control
#: sql_constraint:res.company:0
msgid "The company name must be unique !"
msgstr ""
#. module: account_credit_control
#: field:credit.control.policy,name:0
#: field:credit.control.policy.level,name:0
msgid "Name"
msgstr ""
#. module: account_credit_control
#: help:res.partner,credit_policy_id:0
msgid "The Credit Control Policyused for this partner. This setting can be forced on the invoice. If nothing is defined, it will use the company setting."
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,mail_message_id:0
msgid "Sent Email"
msgstr ""
#. module: account_credit_control
#: model:ir.model,name:account_credit_control.model_credit_control_policy_level
msgid "A credit control policy level"
msgstr ""
#. module: account_credit_control
#: model:ir.actions.report.xml,name:account_credit_control.report_webkit_html
msgid "Credit Summary"
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,date:0
msgid "Controlling date"
msgstr ""
#. module: account_credit_control
#: constraint:account.move.line:0
msgid "You can not create journal items on closed account."
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,amount_due:0
msgid "Due Amount Tax incl."
msgstr ""
#. module: account_credit_control
#: field:res.company,credit_control_tolerance:0
msgid "Credit Control Tolerance"
msgstr ""
#. module: account_credit_control
#: help:res.company,credit_policy_id:0
msgid "The Credit Control Policy used on partners by default. This setting can be overriden on partners or invoices."
msgstr ""
#. module: account_credit_control
#: field:credit.control.line,policy_level_id:0
msgid "Overdue Level"
msgstr ""

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,54 @@
# -*- coding: utf-8 -*-
##############################################################################
#
# Author: Vincent Renaville
# Copyright 2013 Camptocamp SA
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv import orm
from openerp.tools.translate import _
class AccountInvoice(orm.Model):
"""Check on cancelling of an invoice"""
_inherit = 'account.invoice'
def action_cancel(self, cr, uid, ids, context=None):
# We will search if this invoice is linked with credit
cc_line_obj = self.pool.get('credit.control.line')
for invoice_id in ids:
cc_nondraft_line_ids = cc_line_obj.search(
cr, uid,
[('invoice_id', '=', invoice_id),
('state', '<>', 'draft')],
context=context)
if cc_nondraft_line_ids:
raise orm.except_orm(_('Error!'),
_('You cannot cancel this invoice.\n'
'A payment reminder has already been '
'sent to the customer.\n'
'You must create a credit note and '
'issue a new invoice.'))
cc_draft_line_ids = cc_line_obj.search(
cr, uid,
[('invoice_id', '=', invoice_id),
('state', '=', 'draft')],
context=context)
cc_line_obj.unlink(cr, uid,
cc_draft_line_ids,
context=context)
return super(AccountInvoice, self).action_cancel(cr, uid, ids,
context=context)

View File

@@ -19,16 +19,15 @@
#
##############################################################################
import logging
import pooler
from openerp.osv.orm import Model, fields
from openerp.osv import orm, fields
from openerp.osv import osv
from openerp.tools.translate import _
logger = logging.getLogger('credit.line.control')
class CreditControlLine(Model):
class CreditControlLine(orm.Model):
"""A credit control line describes an amount due by a customer for a due date.
A line is created once the due date of the payment is exceeded.
@@ -49,6 +48,10 @@ class CreditControlLine(Model):
readonly=True,
states={'draft': [('readonly', False)]}),
'date_entry': fields.related('move_line_id', 'date', type='date',
string='Entry date',
store=True, readonly=True),
'date_sent': fields.date('Sent date',
readonly=True,
states={'draft': [('readonly', False)]}),
@@ -67,16 +70,16 @@ class CreditControlLine(Model):
"generated again on the next run.")),
'channel': fields.selection([('letter', 'Letter'),
('email', 'Email')],
'Channel', required=True,
readonly=True,
states={'draft': [('readonly', False)]}),
('email', 'Email')],
'Channel', required=True,
readonly=True,
states={'draft': [('readonly', False)]}),
'invoice_id': fields.many2one('account.invoice', 'Invoice', readonly=True),
'partner_id': fields.many2one('res.partner', "Partner", required=True),
'amount_due': fields.float('Due Amount Tax incl.', required=True, readonly=True),
'balance_due': fields.float('Due balance', required=True, readonly=True),
'mail_message_id': fields.many2one('mail.message', 'Sent Email', readonly=True),
'mail_message_id': fields.many2one('mail.mail', 'Sent Email', readonly=True),
'move_line_id': fields.many2one('account.move.line', 'Move line',
required=True, readonly=True),
@@ -127,7 +130,7 @@ class CreditControlLine(Model):
data['date_due'] = move_line.date_maturity
data['state'] = 'draft'
data['channel'] = level.channel
data['invoice_id'] = move_line.invoice_id.id if move_line.invoice_id else False
data['invoice_id'] = move_line.invoice.id if move_line.invoice else False
data['partner_id'] = move_line.partner_id.id
data['amount_due'] = (move_line.amount_currency or move_line.debit or
move_line.credit)
@@ -187,10 +190,9 @@ class CreditControlLine(Model):
def unlink(self, cr, uid, ids, context=None, check=True):
for line in self.browse(cr, uid, ids, context=context):
if line.state != 'draft':
raise osv.except_osv(
raise orm.except_orm(
_('Error !'),
_('You are not allowed to delete a credit control line that '
'is not in draft state.'))
return super(CreditControlLine, self).unlink(cr, uid, ids, context=context)

View File

@@ -28,7 +28,7 @@
<record id="credit_control_line_search" model="ir.ui.view">
<field name="name">Credit Control Lines</field>
<field name="model">credit.control.lines</field>
<field name="model">credit.control.line</field>
<field name="type">search</field>
<field name="arch" type="xml">
<search string="Control Credit Lines">

View File

@@ -0,0 +1,28 @@
# -*- coding: utf-8 -*-
##############################################################################
#
# Author: Nicolas Bessi, Guewen Baconnier
# Copyright 2012 Camptocamp SA
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv import orm, fields
class Mail(orm.Model):
_inherit = 'mail.mail'
# use HTML fields instead of text
_columns = {'body_html': fields.html('Rich-text Contents',
help="Rich-text/HTML message"),}

View File

@@ -18,27 +18,35 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv.orm import Model, fields
from openerp.osv import orm, fields
class ResPartner(Model):
class ResPartner(orm.Model):
"""Add a settings on the credit control policy to use on the partners,
and links to the credit control lines."""
_inherit = "res.partner"
_columns = {
'credit_policy_id': fields.many2one('credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy"
"used for this partner. This "
"setting can be forced on the "
"invoice. If nothing is defined, "
"it will use the company "
"setting.")),
'credit_control_line_ids': fields.one2many('credit.control.line',
'invoice_id',
string='Credit Control Lines',
readonly=True)
'credit_policy_id':
fields.many2one('credit.control.policy',
'Credit Control Policy',
help=("The Credit Control Policy used for this "
"partner. This setting can be forced on the "
"invoice. If nothing is defined, it will use "
"the company setting.")),
'credit_control_line_ids':
fields.one2many('credit.control.line',
'invoice_id',
string='Credit Control Lines',
readonly=True)
}
def copy_data(self, cr, uid, id, default=None, context=None):
if default is None:
default = {}
else:
default = default.copy()
default['credit_control_line_ids'] = False
return super(ResPartner, self).copy_data(
cr, uid, id, default=default, context=context)

View File

@@ -30,21 +30,21 @@ class CreditControlPolicy(Model):
_columns = {'name': fields.char('Name', required=True, size=128),
'level_ids': fields.one2many('credit.control.policy.level',
'policy_id',
'Policy Levels'),
'policy_id',
'Policy Levels'),
'do_nothing': fields.boolean('Do nothing',
help=('For policies which should not '
'generate lines or are obsolete')),
help='For policies which should not '
'generate lines or are obsolete'),
'company_id': fields.many2one('res.company', 'Company'),
'account_ids': fields.many2many(
'account.account',
string='Accounts',
required=True,
domain="[('reconcile', '=', True)]",
help='This policy will be active only for the selected accounts'),
'account_ids': fields.many2many('account.account',
string='Accounts',
required=True,
domain="[('reconcile', '=', True)]",
help="This policy will be active only"
" for the selected accounts"),
}
def _move_lines_domain(self, cr, uid, policy, controlling_date, context=None):
@@ -71,13 +71,12 @@ class CreditControlPolicy(Model):
if user.company_id.credit_policy_id.id != policy.id:
return set()
return set(move_l_obj.search(
cr, uid,
self._move_lines_domain(cr, uid, policy, controlling_date, context=context),
context=context))
domain_line = self._move_lines_domain(cr, uid, policy,
controlling_date, context=context)
return set(move_l_obj.search(cr, uid, domain_line, context=context))
def _move_lines_subset(self, cr, uid, policy, controlling_date,
model, move_relation_field, context=None):
model, move_relation_field, context=None):
""" Get the move lines related to one model for a policy.
Do not use direct SQL in order to respect security rules.
@@ -139,9 +138,8 @@ class CreditControlPolicy(Model):
:return: set of ids to add in the process, set of ids to remove from
the process
"""
return self._move_lines_subset(
cr, uid, policy, controlling_date,
'res.partner', 'partner_id', context=context)
return self._move_lines_subset(cr, uid, policy, controlling_date,
'res.partner', 'partner_id', context=context)
def _get_invoice_related_lines(self, cr, uid, policy, controlling_date, context=None):
""" Get the move lines for a policy related to an invoice.
@@ -154,9 +152,8 @@ class CreditControlPolicy(Model):
:return: set of ids to add in the process, set of ids to remove from
the process
"""
return self._move_lines_subset(
cr, uid, policy, controlling_date,
'account.invoice', 'invoice', context=context)
return self._move_lines_subset(cr, uid, policy, controlling_date,
'account.invoice', 'invoice', context=context)
def _get_move_lines_to_process(self, cr, uid, policy_id, controlling_date, context=None):
"""Build a list of move lines ids to include in a run for a policy at a given date.
@@ -173,13 +170,14 @@ class CreditControlPolicy(Model):
policy = self.browse(cr, uid, policy_id, context=context)
# there is a priority between the lines, depicted by the calls below
# warning, side effect method called on lines
lines = self._due_move_lines(
cr, uid, policy, controlling_date, context=context)
add_ids, remove_ids = self._get_partner_related_lines(
cr, uid, policy, controlling_date, context=context)
lines = self._due_move_lines(cr, uid, policy, controlling_date, context=context)
add_ids, remove_ids = self._get_partner_related_lines(cr, uid, policy,
controlling_date,
context=context)
lines = lines.union(add_ids).difference(remove_ids)
add_ids, remove_ids = self._get_invoice_related_lines(
cr, uid, policy, controlling_date, context=context)
add_ids, remove_ids = self._get_invoice_related_lines(cr, uid, policy,
controlling_date,
context=context)
lines = lines.union(add_ids).difference(remove_ids)
return lines
@@ -195,8 +193,8 @@ class CreditControlPolicy(Model):
if isinstance(policy_id, list):
policy_id = policy_id[0]
cr.execute("SELECT move_line_id FROM credit_control_line"
" WHERE policy_id != %s and move_line_id in %s",
(policy_id, tuple(lines)))
" WHERE policy_id != %s and move_line_id in %s",
(policy_id, tuple(lines)))
res = cr.fetchall()
if res:
different_lines.update([x[0] for x in res])
@@ -213,7 +211,8 @@ class CreditControlPolicyLevel(Model):
_columns = {
'policy_id': fields.many2one('credit.control.policy',
'Related Policy', required=True),
'name': fields.char('Name', size=128, required=True),
'name': fields.char('Name', size=128, required=True,
translate=True),
'level': fields.integer('Level', required=True),
'computation_mode': fields.selection([('net_days', 'Due Date'),
@@ -224,11 +223,14 @@ class CreditControlPolicyLevel(Model):
'delay_days': fields.integer('Delay (in days)', required='True'),
'email_template_id': fields.many2one('email.template', 'Email Template',
required=True),
required=True),
'channel': fields.selection([('letter', 'Letter'),
('email', 'Email')],
'Channel', required=True),
('email', 'Email')],
'Channel', required=True),
'custom_text': fields.text('Custom Message', required=True, translate=True),
'custom_mail_text': fields.text('Custom Mail Message',
required=True, translate=True),
}
def _check_level_mode(self, cr, uid, rids, context=None):
@@ -314,9 +316,11 @@ class CreditControlPolicyLevel(Model):
# lines from a previous level with a draft or ignored state
# have to be generated again for the previous level
" AND state not in ('draft', 'ignored'))")
sql += " AND" + self._get_sql_date_boundary_for_computation_mode(
cr, uid, level, controlling_date, context)
data_dict = {'controlling_date': controlling_date, 'line_ids': tuple(lines),
sql += " AND"
sql += self._get_sql_date_boundary_for_computation_mode(cr, uid, level,
controlling_date, context)
data_dict = {'controlling_date': controlling_date,
'line_ids': tuple(lines),
'delay': level.delay_days}
cr.execute(sql, data_dict)
@@ -343,14 +347,15 @@ class CreditControlPolicyLevel(Model):
# have to be generated again for the previous level
" AND cr_line.state not in ('draft', 'ignored')\n"
" AND mv_line.id in %(line_ids)s\n")
sql += " AND " + self._get_sql_date_boundary_for_computation_mode(
cr, uid, level, controlling_date, context)
previous_level_id = self._previous_level(
cr, uid, level, context=context)
previous_level = self.browse(
cr, uid, previous_level_id, context=context)
data_dict = {'controlling_date': controlling_date, 'line_ids': tuple(lines),
'delay': level.delay_days, 'previous_level': previous_level.level}
sql += " AND "
sql += self._get_sql_date_boundary_for_computation_mode(cr, uid, level,
controlling_date, context)
previous_level_id = self._previous_level(cr, uid, level, context=context)
previous_level = self.browse(cr, uid, previous_level_id, context=context)
data_dict = {'controlling_date': controlling_date,
'line_ids': tuple(lines),
'delay': level.delay_days,
'previous_level': previous_level.level}
# print cr.mogrify(sql, data_dict)
cr.execute(sql, data_dict)
@@ -371,9 +376,7 @@ class CreditControlPolicyLevel(Model):
method = self._get_first_level_move_line_ids
else:
method = self._get_other_level_move_line_ids
matching_lines.update(
method(cr, uid, level, controlling_date, lines, context=context))
matching_lines.update(method(cr, uid, level,
controlling_date, lines,
context=context))
return matching_lines

View File

@@ -6,14 +6,14 @@
<field name="model">credit.control.policy</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Credit control policy">
<field name="name"/>
<field name="do_nothing"/>
<field name="company_id"/>
<notebook colspan="4">
<page string="Policy Levels">
<page string="Policy levels">
<field name="level_ids" nolabel="1" colspan="4" >
<tree>
<tree string="Credit control policy Level">
<field name="name"/>
<field name="level"/>
<field name="channel"/>
@@ -21,7 +21,7 @@
<field name="computation_mode"/>
<field name="email_template_id"/>
</tree>
<form>
<form string="Policy level">
<field name="name"/>
<notebook colspan="4">
<page string="Delay Setting">
@@ -32,7 +32,10 @@
</page>
<page string="Mail and reporting">
<field name="email_template_id"/>
<field name="custom_text"/>
<newline/>
<field name="custom_text" colspan="4"/>
<newline/>
<field name="custom_mail_text" colspan="4"/>
</page>
</notebook>
</form>
@@ -51,7 +54,7 @@
<field name="model">credit.control.policy</field>
<field name="type">tree</field>
<field name="arch" type="xml">
<tree>
<tree string="Credit control policy">
<field name="name"/>
<field name="do_nothing"/>
</tree>
@@ -84,7 +87,7 @@
<field name="model">credit.control.policy.level</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Policy level">
<field name="name"/>
<notebook colspan="4">
<page string="Delay Setting">
@@ -107,7 +110,7 @@
<field name="model">credit.control.policy.level</field>
<field name="type">tree</field>
<field name="arch" type="xml">
<tree>
<tree string="Credit control policy level">
<field name="name"/>
<field name="level"/>
<field name="channel"/>

View File

@@ -2,18 +2,239 @@
<head>
<style type="text/css">
${css}
body {
font-family: helvetica;
font-size: 12px;
}
.custom_text {
font-family: helvetica;
font-size: 12px;
}
table {
font-family: helvetica;
font-size: 12px;
}
.header {
margin-left: 0px;
text-align: left;
width: 300px;
font-size: 12px;
}
.title {
font-size: 16px;
font-weight: bold;
}
.basic_table{
text-align: center;
border: 1px solid lightGrey;
border-collapse: collapse;
font-family: helvetica;
font-size: 12px;
}
.basic_table th {
border: 1px solid lightGrey;
font-size: 11px;
font-weight: bold;
}
.basic_table td {
border: 1px solid lightGrey;
font-size: 12px;
}
.list_table {
border-color: black;
text-align: center;
border-collapse: collapse;
}
.list_table td {
border-color: gray;
border-top: 1px solid gray;
text-align: left;
font-size: 12px;
padding-right: 3px;
padding-left: 3px;
padding-top: 3px;
padding-bottom:3px;
}
.list_table th {
border-bottom: 2px solid black;
text-align: left;
font-size: 11px;
font-weight: bold;
padding-right: 3px
padding-left: 3px
}
.list_table thead {
display: table-header-group;
}
.address table {
font-size: 11px;
border-collapse: collapse;
margin: 0px;
padding: 0px;
}
.address .shipping {
}
.address .invoice {
margin-top: 10px;
}
.address .recipient {
font-size: 13px;
margin-right: 120px;
margin-left: 350px;
float: right;
}
table .address_title {
font-weight: bold;
}
.address td.name {
font-weight: bold;
}
td.amount, th.amount {
text-align: right;
padding-right:2px;
}
h1 {
font-size: 16px;
font-weight: bold;
}
tr.line .note {
border-style: none;
font-size: 9px;
padding-left: 10px;
}
tr.line {
margin-bottom: 10px;
}
</style>
</head>
<body>
%for comm in objects :
<%
setLang(comm.partner_id.lang)
current_uri = '%s_policy_template' % (comm.partner_id.lang)
if not context.lookup.has_template(current_uri):
context.lookup.put_string(current_uri, comm.current_policy_level.email_template_id.body_html)
%>
<%include file="${current_uri}" args="object=comm,user=user,ctx=ctx,quote=quote,format_exception=format_exception,mode='pdf'"/>
<% setLang(comm.get_contact_address().lang) %>
<div class="address">
<table class="recipient">
<%
add = comm.get_contact_address()
%>
%if comm.partner_id.id == add.id:
<tr><td class="name">${comm.partner_id.title and comm.partner_id.title.name or ''} ${comm.partner_id.name }</td></tr>
<% address_lines = comm.partner_id.contact_address.split("\n") %>
%else:
<tr><td class="name">${comm.partner_id.name or ''}</td></tr>
<tr><td>${add.title and add.title.name or ''} ${add.name}</td></tr>
<% address_lines = add.contact_address.split("\n")[1:] %>
%endif
%for part in address_lines:
%if part:
<tr><td>${part}</td></tr>
%endif
%endfor
</table>
<br/>
<br/>
<br/>
<br/>
</div>
<br/>
<br/>
<br/>
<div>
<h3 style="clear: both; padding-top: 20px;">
${_('Reminder')}: ${comm.current_policy_level.name or '' }
</h3>
<p>${_('Dear')},</p>
<p class="custom_text" width="95%">${comm.current_policy_level.custom_text.replace('\n', '<br />')}</p>
<br/>
<br/>
<p><b>${_('Summary')}<br/></b></p>
<table class="basic_table" style="width: 100%;">
<tr>
<th width="200">${_('Invoice number')}</th>
<th>${_('Invoice date')}</th>
<th>${_('Date due')}</th>
<th>${_('Invoiced amount')}</th>
<th>${_('Open amount')}</th>
<th>${_('Currency')}</th>
</tr>
%for line in comm.credit_control_line_ids:
<tr>
%if line.invoice_id:
<td width="200">${line.invoice_id.number}
%if line.invoice_id.name:
<br/>
${line.invoice_id.name}
%endif
</td>
%else:
<td width="200">${line.move_line_id.name}</td>
%endif
<td class="date">${line.date_entry}</td>
<td class="date">${line.date_due}</td>
<td class="amount">${line.amount_due}</td>
<td class="amount">${line.balance_due}</td>
<td class="amount">${line.currency_id.name or comm.company_id.currency_id.name}</td>
</tr>
%endfor
</table>
<br/>
<br/>
<%doc>
<!-- uncomment to have info after summary -->
<p>${_('If you have any question, do not hesitate to contact us.')}</p>
<p>${comm.user_id.name} ${comm.user_id.email and '<%s>'%(comm.user_id.email) or ''}<br/>
${comm.company_id.name}<br/>
% if comm.company_id.street:
${comm.company_id.street or ''}<br/>
% endif
% if comm.company_id.street2:
${comm.company_id.street2}<br/>
% endif
% if comm.company_id.city or comm.company_id.zip:
${comm.company_id.zip or ''} ${comm.company_id.city or ''}<br/>
% endif
% if comm.company_id.country_id:
${comm.company_id.state_id and ('%s, ' % comm.company_id.state_id.name) or ''} ${comm.company_id.country_id.name or ''}<br/>
% endif
% if comm.company_id.phone:
Phone: ${comm.company_id.phone}<br/>
% endif
% if comm.company_id.website:
${comm.company_id.website or ''}<br/>
% endif
</%doc>
<p style="page-break-after:always"></p>
%endfor

View File

@@ -1,12 +1,16 @@
<openerp>
<data>
<report auto="False"
id="report_webkit_html"
model="credit.control.communication"
name="credit_control_summary"
file="account_credit_control/report/credit_control_summary.html.mako"
string="Credit Summary"
report_type="webkit"
webkit_header="report_webkit.ir_header_webkit_basesample0"/>
<report auto="False"
id="report_webkit_html"
model="credit.control.communication"
name="credit_control_summary"
file="account_credit_control/report/credit_control_summary.html.mako"
string="Credit Summary"
report_type="webkit"
webkit_header="report_webkit.ir_header_webkit_basesample0"/>
<record model="ir.actions.report.xml" id="report_webkit_html">
<field name="precise_mode" eval="True"/>
</record>
</data>
</openerp>

View File

@@ -20,14 +20,13 @@
##############################################################################
import logging
from openerp.osv.orm import Model, fields
from openerp.osv import orm, fields
from openerp.tools.translate import _
from openerp.osv.osv import except_osv
logger = logging.getLogger('credit.control.run')
class CreditControlRun(Model):
class CreditControlRun(orm.Model):
"""Credit Control run generate all credit control lines and reject"""
_name = "credit.control.run"
@@ -35,40 +34,50 @@ class CreditControlRun(Model):
_description = """Credit control line generator"""
_columns = {
'date': fields.date('Controlling Date', required=True),
'policy_ids': fields.many2many('credit.control.policy',
rel="credit_run_policy_rel",
id1='run_id', id2='policy_id',
string='Policies',
readonly=True,
states={'draft': [('readonly', False)]}),
'policy_ids':
fields.many2many('credit.control.policy',
rel="credit_run_policy_rel",
id1='run_id', id2='policy_id',
string='Policies',
readonly=True,
states={'draft': [('readonly', False)]}),
'report': fields.text('Report', readonly=True),
'state': fields.selection([('draft', 'Draft'),
('done', 'Done'),
],
string='State',
required=True,
readonly=True),
('done', 'Done')],
string='State',
required=True,
readonly=True),
'manual_ids': fields.many2many(
'account.move.line',
rel="credit_runreject_rel",
string='Lines to handle manually',
help=('If a credit control line has been generated on a policy '
'and the policy has been changed meantime, '
'it has to be handled manually'),
readonly=True),
}
'manual_ids':
fields.many2many('account.move.line',
rel="credit_runreject_rel",
string='Lines to handle manually',
help=('If a credit control line has been generated'
'on a policy and the policy has been changed '
'in the meantime, it has to be handled '
'manually'),
readonly=True),
}
def copy_data(self, cr, uid, id, default=None, context=None):
if default is None:
default = {}
else:
default = default.copy()
default.update({
'report': False,
'manual_ids': False,
})
return super(CreditControlRun, self).copy_data(
cr, uid, id, default=default, context=context)
def _get_policies(self, cr, uid, context=None):
return self.pool.get('credit.control.policy').\
search(cr, uid, [], context=context)
return self.pool['credit.control.policy'].search(cr, uid, [], context=context)
_defaults = {
'state': 'draft',
'policy_ids': _get_policies,
}
_defaults = {'state': 'draft',
'policy_ids': _get_policies}
def _check_run_date(self, cr, uid, ids, controlling_date, context=None):
"""Ensure that there is no credit line in the future using controlling_date"""
@@ -77,16 +86,16 @@ class CreditControlRun(Model):
order='date DESC', limit=1, context=context)
if lines:
line = line_obj.browse(cr, uid, lines[0], context=context)
raise except_osv(
_('Error'),
_('A run has already been executed more recently than %s') % (line.date))
raise orm.except_orm(_('Error'),
_('A run has already been executed more '
'recently than %s') % (line.date))
return True
def _generate_credit_lines(self, cr, uid, run_id, context=None):
""" Generate credit control lines. """
cr_line_obj = self.pool.get('credit.control.line')
assert not (isinstance(run_id, list) and len(run_id) > 1), \
"run_id: only one id expected"
"run_id: only one id expected"
if isinstance(run_id, list):
run_id = run_id[0]
@@ -97,9 +106,8 @@ class CreditControlRun(Model):
policies = run.policy_ids
if not policies:
raise except_osv(
_('Error'),
_('Please select a policy'))
raise orm.except_orm(_('Error'),
_('Please select a policy'))
report = ''
for policy in policies:
@@ -110,9 +118,8 @@ class CreditControlRun(Model):
manual_lines = policy._lines_different_policy(lines, context=context)
lines.difference_update(manual_lines)
manually_managed_lines.update(manual_lines)
policy_generated_ids = []
if lines:
policy_generated_ids = []
# policy levels are sorted by level so iteration is in the correct order
for level in reversed(policy.level_ids):
level_lines = level.get_level_lines(run.date, lines, context=context)
@@ -140,14 +147,12 @@ class CreditControlRun(Model):
"""
try:
cr.execute('SELECT id FROM credit_control_run'
' LIMIT 1 FOR UPDATE NOWAIT' )
except Exception, exc:
' LIMIT 1 FOR UPDATE NOWAIT')
except Exception as exc:
# in case of exception openerp will do a rollback for us and free the lock
raise except_osv(
_('Error'),
_('A credit control run is already running'
' in background, please try later.'), str(exc))
raise orm.except_orm(_('Error'),
_('A credit control run is already running'
' in background, please try later.'))
self._generate_credit_lines(cr, uid, run_id, context)
return True

View File

@@ -6,7 +6,7 @@
<field name="model">credit.control.run</field>
<field name="type">tree</field>
<field name="arch" type="xml">
<tree> <!-- editable="bottom" -->
<tree string="Credit control run"> <!-- editable="bottom" -->
<field name="date"/>
<field name="state"/>
</tree>
@@ -18,7 +18,7 @@
<field name="model">credit.control.run</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Credit control run">
<field name="date"/>
<newline/>
<notebook colspan="4">

View File

@@ -0,0 +1,52 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2009 Camptocamp SA
#
##############################################################################
##############################################################################
# Branch # Module # Processes # System
@account_credit_control @account_credit_control_setup
Feature: General parameters in order to test the credit control module
@deactivate_journal_control
Scenario: Journal setup to vaoid unfixed voucher bug
Given I execute the SQL commands
"""
UPDATE account_journal SET allow_date = false;
"""
@account_credit_control_setup_install_modules
Scenario: MODULES INSTALLATION
Given I do not want all demo data to be loaded on install
Given I install the required modules with dependencies:
| name |
| account_credit_control |
Then my modules should have been installed and models reloaded
@email_params_mailtrap
Scenario: E-MAIL PARAMS WITH EMAIL EATER (http://mailtrap.railsware.com/)
Given I need a "ir.mail_server" with name: mailstrap_testings
And having:
| name | value |
| smtp_host | mailtrap.railsware.com |
| sequence | 1 |
| smtp_port | 2525 |
| smtp_user | camptocamp1 |
| smtp_pass | 20468fa2f2879cb9 |
@account_credit_control_policy_2_times
Scenario: Configure the credit control policy in 2 times
Given I configure the following accounts on the credit control policy with oid: "account_credit_control.credit_control_2_time":
| account code |
| 4111 |
| 4112 |
@account_credit_control_policy_3_times
Scenario: Configure the credit control policy in 3 times
Given I configure the following accounts on the credit control policy with oid: "account_credit_control.credit_control_3_time":
| account code |
| 4111 |
| 4112 |

View File

@@ -0,0 +1,105 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2009 Camptocamp SA
#
##############################################################################
##############################################################################
# Branch # Module # Processes # System
@account_credit_control @account_credit_control_add_policy @account_credit_control_setup
Feature: I add policy to partners already created
@account_credit_control_partner_1
Scenario: Partner_1
Given I need a "res.partner" with oid: scen.partner_1
And having:
| name | value |
| name | partner_1 |
| credit_policy_id | by name: No follow |
@account_credit_control_customer_1
Scenario: Customer_1
Given I need a "res.partner" with oid: scen.customer_1
And having:
| name | value |
| name | customer_1 |
| credit_policy_id | by name: 2 time policy |
@account_credit_control_customer_2
Scenario: Customer_2
Given I need a "res.partner" with oid: scen.customer_2
And having:
| name | value |
| name | customer_2 |
| credit_policy_id | by name: 2 time policy |
@account_credit_control_customer_3
Scenario: Customer_3
Given I need a "res.partner" with oid: scen.customer_3
And having:
| name | value |
| name | customer_3 |
| credit_policy_id | by name: 2 time policy |
@account_credit_control_customer_4
Scenario: Customer_4
Given I need a "res.partner" with oid: scen.customer_4
And having:
| name | value |
| name | customer_4 |
# the credit policy must be 3 time policy (inherited from company)
@account_credit_control_customer_5
Scenario: Customer_5
Given I need a "res.partner" with oid: scen.customer_5
And having:
| name | value |
| name | customer_5_usd |
| credit_policy_id | by name: 3 time policy |
@account_credit_control_customer_6
Scenario: Customer_6
Given I need a "res.partner" with oid: scen.customer_6
And having:
| name | value |
| name | customer_6 |
| credit_policy_id | by name: 3 time policy |
@account_credit_control_customer_partial_pay
Scenario: A customer who like to do partial payments
Given I need a "res.partner" with oid: scen.customer_partial_pay
And having:
| name | value |
| name | Scrooge McDuck |
| zip | 1000 |
| city | Duckburg |
| email | openerp@locahost.dummy |
| phone | |
| street | Duckstreet |
@account_credit_control_customer_multiple_payterm
Scenario: A customer who use payment terms in 2 times
Given I need a "res.partner" with oid: scen.customer_multiple_payterm
And having:
| name | value |
| name | Donald Duck |
| zip | 1100 |
| city | Duckburg |
| email | openerp@locahost.dummy |
| phone | |
| street | Duckstreet |
@account_credit_control_customer_multiple_payterm2
Scenario: A customer who use payment terms in 2 times
Given I need a "res.partner" with oid: scen.customer_multiple_payterm2
And having:
| name | value |
| name | Gus Goose |
| type | default |
| name | Gus Goose |
| zip | 1100 |
| city | Duckburg |
| email | openerp@locahost.dummy |
| phone | |
| street | Duckstreet |

View File

@@ -0,0 +1,588 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
@account_credit_control @account_credit_control_setup @account_credit_control_base_data @account_credit_control_invoices
Feature: Invoices creation
##################### Partner 1 ##########################################################
@inv_1
Scenario: Create invoice 1
Given I need a "account.invoice" with oid: scen._inv_1
And having:
| name | value |
| name | SI_1 |
| date_invoice | %Y-01-15 |
| partner_id | by oid: scen.partner_1 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv1_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_1 |
Given I find a "account.invoice" with oid: scen._inv_1
Given I need a "account.invoice.line" with oid: scen._inv1_line2
And having:
| name | value |
| name | invoice line 2 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_1 |
Given I find a "account.invoice" with oid: scen._inv_1
And I open the credit invoice
@inv_2
Scenario: Create invoice 2
Given I need a "account.invoice" with oid: scen._inv_2
And having:
| name | value |
| name | SI_2 |
| date_invoice | %Y-02-15 |
| partner_id | by oid: scen.partner_1 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv2_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1200 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_2 |
Given I find a "account.invoice" with oid: scen._inv_2
And I open the credit invoice
@inv_3
Scenario: Create invoice 3
Given I need a "account.invoice" with oid: scen._inv_3
And having:
| name | value |
| name | SI_3 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.partner_1 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv3_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_3 |
Given I find a "account.invoice" with oid: scen._inv_3
And I open the credit invoice
##################### Customer 2 ##########################################################
@inv_4
Scenario: Create invoice 4
Given I need a "account.invoice" with oid: scen._inv_4
And having:
| name | value |
| name | SI_4 |
| date_invoice | %Y-01-18 |
| partner_id | by oid: scen.customer_2 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv4_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_4 |
Given I find a "account.invoice" with oid: scen._inv_4
And I open the credit invoice
@inv_5
Scenario: Create invoice 5
Given I need a "account.invoice" with oid: scen._inv_5
And having:
| name | value |
| name | SI_5 |
| date_invoice | %Y-02-15 |
| partner_id | by oid: scen.customer_2 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv5_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1200 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_5 |
Given I find a "account.invoice" with oid: scen._inv_5
And I open the credit invoice
@inv_6
Scenario: Create invoice 6
Given I need a "account.invoice" with oid: scen._inv_6
And having:
| name | value |
| name | SI_6 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_2 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Days End of Month |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv6_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_6 |
Given I find a "account.invoice" with oid: scen._inv_6
And I open the credit invoice
##################### Customer 3 ##########################################################
@inv_7
Scenario: Create invoice 7
Given I need a "account.invoice" with oid: scen._inv_7
And having:
| name | value |
| name | SI_7 |
| date_invoice | %Y-01-18 |
| partner_id | by oid: scen.customer_3 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv7_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_7 |
Given I find a "account.invoice" with oid: scen._inv_7
And I open the credit invoice
@inv_8
Scenario: Create invoice 8
Given I need a "account.invoice" with oid: scen._inv_8
And having:
| name | value |
| name | SI_8 |
| date_invoice | %Y-02-15 |
| partner_id | by oid: scen.customer_3 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv8_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1200 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_8 |
Given I find a "account.invoice" with oid: scen._inv_8
And I open the credit invoice
@inv_9
Scenario: Create invoice 9
Given I need a "account.invoice" with oid: scen._inv_9
And having:
| name | value |
| name | SI_9 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_3 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv9_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_9 |
Given I find a "account.invoice" with oid: scen._inv_9
And I open the credit invoice
##################### Customer 4 ##########################################################
@inv_10
Scenario: Create invoice 10
Given I need a "account.invoice" with oid: scen._inv_10
And having:
| name | value |
| name | SI_10 |
| date_invoice | %Y-01-18 |
| partner_id | by oid: scen.customer_4 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30% Advance End 30 Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv10_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_10 |
Given I find a "account.invoice" with oid: scen._inv_10
And I open the credit invoice
@inv_11
Scenario: Create invoice 11
Given I need a "account.invoice" with oid: scen._inv_11
And having:
| name | value |
| name | SI_11 |
| date_invoice | %Y-02-15 |
| partner_id | by oid: scen.customer_4 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30% Advance End 30 Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv11_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1200 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_11 |
Given I find a "account.invoice" with oid: scen._inv_11
And I open the credit invoice
@inv_12
Scenario: Create invoice 12
Given I need a "account.invoice" with oid: scen._inv_12
And having:
| name | value |
| name | SI_12 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_4 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30% Advance End 30 Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv12_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_12 |
Given I find a "account.invoice" with oid: scen._inv_12
And I open the credit invoice
##################### Customer 5 ##########################################################
@inv_13
Scenario: Create invoice 13
Given I need a "account.invoice" with oid: scen._inv_13
And having:
| name | value |
| name | SI_13 |
| date_invoice | %Y-01-18 |
| partner_id | by oid: scen.customer_5 |
| account_id | by name: Debtors USD |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv13_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1000 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_13 |
Given I find a "account.invoice" with oid: scen._inv_13
And I open the credit invoice
@inv_14
Scenario: Create invoice 14
Given I need a "account.invoice" with oid: scen._inv_14
And having:
| name | value |
| name | SI_14 |
| date_invoice | %Y-02-15 |
| partner_id | by oid: scen.customer_5 |
| account_id | by name: Debtors USD |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv14_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1200 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_14 |
Given I find a "account.invoice" with oid: scen._inv_14
And I open the credit invoice
@inv_15
Scenario: Create invoice 15
Given I need a "account.invoice" with oid: scen._inv_15
And having:
| name | value |
| name | SI_15 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_5 |
| account_id | by name: Debtors USD |
| journal_id | by name: Sales |
| currency_id | by name: USD |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
Given I need a "account.invoice.line" with oid: scen._inv15_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_15 |
Given I find a "account.invoice" with oid: scen._inv_15
And I open the credit invoice
@inv_16
Scenario: Create invoice 16
Given I need a "account.invoice" with oid: scen._inv_16
And having:
| name | value |
| name | SI_16 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_4 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv16_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_16 |
Then I find a "account.invoice" with oid: scen._inv_16
And I open the credit invoice
@inv_17
Scenario: Create invoice 17
Given I need a "account.invoice" with oid: scen._inv_17
And having:
| name | value |
| name | SI_17 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_partial_pay |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv17_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_17 |
Then I find a "account.invoice" with oid: scen._inv_17
And I open the credit invoice
@inv_18
Scenario: Create invoice 18
Given I need a "account.invoice" with oid: scen._inv_18
And having:
| name | value |
| name | SI_18 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_multiple_payterm |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30% Advance End 30 Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv18_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_18 |
Then I find a "account.invoice" with oid: scen._inv_18
And I open the credit invoice
@inv_19
Scenario: Create invoice 19
Given I need a "account.invoice" with oid: scen._inv_19
And having:
| name | value |
| name | SI_19 |
| date_invoice | %Y-03-15 |
| partner_id | by oid: scen.customer_multiple_payterm2 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30% Advance End 30 Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv19_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 1500 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_19 |
Then I find a "account.invoice" with oid: scen._inv_19
And I open the credit invoice
@inv_20
Scenario: Create invoice 20
Given I need a "account.invoice" with oid: scen._inv_20
And having:
| name | value |
| name | SI_20_test_tolerance |
| date_invoice | %Y-03-23 |
| partner_id | by oid: scen.customer_6 |
| account_id | by name: Debtors |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv20_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 0.09 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_20 |
Then I find a "account.invoice" with oid: scen._inv_20
And I open the credit invoice
@inv_20
Scenario: Create invoice 21 (this receivable account must not be chased-> no credit line creation)
Given I need a "account.invoice" with oid: scen._inv_21
And having:
| name | value |
| name | SI_21_test_receivable_account_excluded |
| date_invoice | %Y-03-25 |
| partner_id | by oid: scen.customer_6 |
| account_id | by name: Debtors GBP |
| journal_id | by name: Sales |
| currency_id | by name: EUR |
| payment_term | by name: 30 Net Days |
| type | out_invoice |
And I need a "account.invoice.line" with oid: scen._inv21_line1
And having:
| name | value |
| name | invoice line 1 |
| quantity | 1 |
| price_unit | 6666 |
| account_id | by name: Sales |
| invoice_id | by oid: scen._inv_21 |
Then I find a "account.invoice" with oid: scen._inv_21
And I open the credit invoice

View File

@@ -0,0 +1,29 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_jan
Feature: Ensure that mail credit line generation first pass is correct
Scenario: clean data
Given I clean all the credit lines
#Given I unreconcile and clean all move line
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run1
And having:
| name | value |
| date | %Y-01-31 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 300 | %Y-01-18 | Debtors | 3 time policy | %Y-01-31 | customer_4 | email | 1 | SI_10 | 10 days net | draft | 300 | |

View File

@@ -0,0 +1,33 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_feb
Feature: Ensure that mail credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run2
And having:
| name | value |
| date | %Y-02-28 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 360 | %Y-02-15 | Debtors | 3 time policy | %Y-02-28 | customer_4 | email | 1 | SI_11 | 10 days net | draft | 360 | USD |
| 1000 | %Y-02-17 | Debtors USD | 3 time policy | %Y-02-28 | customer_5_usd | email | 1 | SI_13 | 10 days net | draft | 1000 | USD |
| 300 | %Y-01-18 | Debtors | 3 time policy | %Y-02-28 | customer_4 | email | 2 | SI_10 | 30 days end of month | draft | 300 | |

View File

@@ -0,0 +1,62 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_mar
Feature: Ensure that email credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@pay_invoice_si_19_part1
Scenario: I pay a part of the first part of the invoice SI 19,
Given I need a "account.bank.statement" with oid: scen.state_control_eur_1
And having:
| name | value |
| name | Bk.St.si_19_part1 |
| date | %Y-03-31 |
| journal_id | by oid: scen.eur_journal |
And I import invoice "SI_19" using import invoice button
And I should have a "account.bank.statement.line" with name: "SI_19" and amount: "450"
And I set the voucher paid amount to "300"
And I save the voucher
And I should have a "account.bank.statement.line" with name: "SI_19" and amount: "1050"
And I set the voucher paid amount to "0"
And I save the voucher
Then I modify the line amount to "0"
Given I need a "account.bank.statement" with oid: scen.state_control_eur_1
And I set bank statement end-balance
When I confirm bank statement
Then My invoice "SI_19" is in state "open" reconciled with a residual amount of "1200.0"
@account_credit_control_run_month_mar
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run3
And having:
| name | value |
| date | %Y-03-31 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 1000 | %Y-02-28 | Debtors | 2 time policy | %Y-03-31 | customer_2 | email | 1 | SI_4 | 30 days end of month | draft | 1000 | |
| 1000 | %Y-02-17 | Debtors | 2 time policy | %Y-03-31 | customer_3 | email | 1 | SI_7 | 30 days end of month | draft | 1000 | |
| 700 | %Y-02-28 | Debtors | 3 time policy | %Y-03-31 | customer_4 | email | 1 | SI_10 | 10 days net | draft | 700 | |
| 450 | %Y-03-15 | Debtors | 3 time policy | %Y-03-31 | customer_4 | email | 1 | SI_12 | 10 days net | draft | 450 | |
| 1200 | %Y-03-17 | Debtors USD | 3 time policy | %Y-03-31 | customer_5_usd | email | 1 | SI_14 | 10 days net | draft | 1200 | USD |
| 360 | %Y-02-15 | Debtors | 3 time policy | %Y-03-31 | customer_4 | email | 2 | SI_11 | 30 days end of month | draft | 360 | USD |
| 1000 | %Y-02-17 | Debtors USD | 3 time policy | %Y-03-31 | customer_5_usd | email | 2 | SI_13 | 30 days end of month | draft | 1000 | USD |
| 300 | %Y-01-18 | Debtors | 3 time policy | %Y-03-31 | customer_4 | letter | 3 | SI_10 | 10 days last reminder | draft | 300 | |
| 450 | %Y-03-15 | Debtors | 3 time policy | %Y-03-31 | Donald Duck | email | 1 | SI_18 | 10 days net | draft | 450 | |
| 150 | %Y-03-15 | Debtors | 3 time policy | %Y-03-31 | Gus Goose | email | 1 | SI_19 | 10 days net | draft | 450 | |

View File

@@ -0,0 +1,44 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_apr
Feature: Ensure that email credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run4
And having:
| name | value |
| date | %Y-04-30 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 360 | %Y-02-15 | Debtors | 3 time policy | %Y-04-30 | customer_4 | letter | 3 | SI_11 | 10 days last reminder | draft | 360 | USD |
| 1200 | %Y-03-31 | Debtors | 2 time policy | %Y-04-30 | customer_2 | email | 1 | SI_5 | 30 days end of month | draft | 1200 | USD |
| 1200 | %Y-03-17 | Debtors | 2 time policy | %Y-04-30 | customer_3 | email | 1 | SI_8 | 30 days end of month | draft | 1200 | USD |
| 700 | %Y-02-28 | Debtors | 3 time policy | %Y-04-30 | customer_4 | email | 2 | SI_10 | 30 days end of month | draft | 700 | |
| 840 | %Y-03-31 | Debtors | 3 time policy | %Y-04-30 | customer_4 | email | 1 | SI_11 | 10 days net | draft | 840 | USD |
| 450 | %Y-03-15 | Debtors | 3 time policy | %Y-04-30 | customer_4 | email | 2 | SI_12 | 30 days end of month | draft | 450 | USD |
| 1500 | %Y-04-14 | Debtors USD | 3 time policy | %Y-04-30 | customer_5_usd | email | 1 | SI_15 | 10 days net | draft | 1500 | USD |
| 1200 | %Y-03-17 | Debtors USD | 3 time policy | %Y-04-30 | customer_5_usd | email | 2 | SI_14 | 30 days end of month | draft | 1200 | USD |
| 1500 | %Y-04-14 | Debtors USD | 3 time policy | %Y-04-30 | customer_5_usd | email | 1 | SI_15 | 10 days net | draft | 1500 | USD |
| 1500 | %Y-04-14 | Debtors | 3 time policy | %Y-04-30 | customer_4 | email | 1 | SI_16 | 10 days net | draft | 1500 | |
| 1500 | %Y-04-14 | Debtors | 3 time policy | %Y-04-30 | Scrooge McDuck | email | 1 | SI_17 | 10 days net | draft | 1500 | |
| 450 | %Y-03-15 | Debtors | 3 time policy | %Y-04-30 | Donald Duck | email | 2 | SI_18 | 30 days end of month | draft | 450 | |
| 150 | %Y-03-15 | Debtors | 3 time policy | %Y-04-30 | Gus Goose | email | 2 | SI_19 | 30 days end of month | draft | 450 | |

View File

@@ -0,0 +1,97 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_may
Feature: Ensure that email credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@pay_invoice_si_16
Scenario: I pay entirely the invoice SI 16, so it should no longer appear in the credit control lines
Given I need a "account.bank.statement" with oid: scen.voucher_statement_si_16
And having:
| name | value |
| name | Bk.St.si_16 |
| date | %Y-05-30 |
| journal_id | by oid: scen.eur_journal |
And I import invoice "SI_16" using import invoice button
And I set bank statement end-balance
When I confirm bank statement
Then My invoice "SI_16" is in state "paid" reconciled with a residual amount of "0.0"
@pay_invoice_si_17
Scenario: I pay entirely the invoice SI 17, so it should no longer appear in the credit control lines
Given I need a "account.bank.statement" with oid: scen.voucher_statement_si_17
And having:
| name | value |
| name | Bk.St.si_17 |
| date | %Y-05-30 |
| journal_id | by oid: scen.eur_journal |
And I import invoice "SI_17" using import invoice button
And I should have a "account.bank.statement.line" with name: "SI_17" and amount: "1500"
And I set the voucher paid amount to "1000"
And I save the voucher
And I modify the line amount to "1000"
And I need a "account.bank.statement" with oid: scen.voucher_statement_si_17
And I set bank statement end-balance
When I confirm bank statement
Then My invoice "SI_17" is in state "open" reconciled with a residual amount of "500.0"
@pay_invoice_si_18_part1
Scenario: I pay the first part of the invoice SI 18, so it should no longer appear in the credit control lines however, the second move lines should still appears
Given I need a "account.bank.statement" with oid: scen.voucher_statement_si_18
And having:
| name | value |
| name | Bk.St.si_18_part1 |
| date | %Y-05-30 |
| journal_id | by oid: scen.eur_journal |
And I import invoice "SI_18" using import invoice button
And I should have a "account.bank.statement.line" with name: "SI_18" and amount: "450"
And I set the voucher paid amount to "450"
And I save the voucher
And I modify the line amount to "450"
And I should have a "account.bank.statement.line" with name: "SI_18" and amount: "1050"
And I set the voucher paid amount to "0"
And I save the voucher
Then I modify the line amount to "0"
And I need a "account.bank.statement" with oid: scen.voucher_statement_si_18
And I set bank statement end-balance
When I confirm bank statement
Then My invoice "SI_18" is in state "open" reconciled with a residual amount of "1050.0"
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run5
And having:
| name | value |
| date | %Y-05-31 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 1500 | %Y-04-30 | Debtors | 2 time policy | %Y-05-31 | customer_2 | email | 1 | SI_6 | 30 days end of month | draft | 1500 | USD |
| 1000 | %Y-02-28 | Debtors | 2 time policy | %Y-05-31 | customer_2 | letter | 2 | SI_4 | 60 days last reminder | draft | 1000 | |
| 1000 | %Y-02-17 | Debtors | 2 time policy | %Y-05-31 | customer_3 | letter | 2 | SI_7 | 60 days last reminder | draft | 1000 | |
| 1500 | %Y-04-14 | Debtors | 2 time policy | %Y-05-31 | customer_3 | email | 1 | SI_9 | 30 days end of month | draft | 1500 | |
| 840 | %Y-03-31 | Debtors | 3 time policy | %Y-05-31 | customer_4 | email | 2 | SI_11 | 30 days end of month | draft | 840 | USD |
| 1500 | %Y-04-14 | Debtors USD | 3 time policy | %Y-05-31 | customer_5_usd | email | 2 | SI_15 | 30 days end of month | draft | 1500 | USD |
| 700 | %Y-02-28 | Debtors | 3 time policy | %Y-05-31 | customer_4 | letter | 3 | SI_10 | 10 days last reminder | draft | 700 | |
| 450 | %Y-03-15 | Debtors | 3 time policy | %Y-05-31 | customer_4 | letter | 3 | SI_12 | 10 days last reminder | draft | 450 | USD |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-05-31 | customer_4 | email | 1 | SI_12 | 10 days net | draft | 1050 | USD |
| 1200 | %Y-03-17 | Debtors USD | 3 time policy | %Y-05-31 | customer_5_usd | letter | 3 | SI_14 | 10 days last reminder | draft | 1200 | USD |
| 500 | %Y-04-14 | Debtors | 3 time policy | %Y-05-31 | Scrooge McDuck | email | 2 | SI_17 | 30 days end of month | draft | 1500 | |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-05-31 | Donald Duck | email | 1 | SI_18 | 10 days net | draft | 1050 | |
| 150 | %Y-03-15 | Debtors | 3 time policy | %Y-05-31 | Gus Goose | letter | 3 | SI_19 | 10 days last reminder | draft | 450 | |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-05-31 | Gus Goose | email | 1 | SI_19 | 10 days net | draft | 1050 | |

View File

@@ -0,0 +1,38 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_jun
Feature: Ensure that email credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run6
And having:
| name | value |
| date | %Y-06-30 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 1200 | %Y-03-31 | Debtors | 2 time policy | %Y-06-30 | customer_2 | letter | 2 | SI_5 | 60 days last reminder | draft | 1200 | USD |
| 1200 | %Y-03-17 | Debtors | 2 time policy | %Y-06-30 | customer_3 | letter | 2 | SI_8 | 60 days last reminder | draft | 1200 | USD |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-06-30 | customer_4 | email | 2 | SI_12 | 30 days end of month | draft | 1050 | USD |
| 840 | %Y-03-31 | Debtors | 3 time policy | %Y-06-30 | customer_4 | letter | 3 | SI_11 | 10 days last reminder | draft | 840 | USD |
| 1500 | %Y-04-14 | Debtors USD | 3 time policy | %Y-06-30 | customer_5_usd | letter | 3 | SI_15 | 10 days last reminder | draft | 1500 | USD |
| 500 | %Y-04-14 | Debtors | 3 time policy | %Y-06-30 | Scrooge McDuck | letter | 3 | SI_17 | 10 days last reminder | draft | 1500 | |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-06-30 | Donald Duck | email | 2 | SI_18 | 30 days end of month | draft | 1050 | |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-06-30 | Gus Goose | email | 2 | SI_19 | 30 days end of month | draft | 1050 | |

View File

@@ -0,0 +1,35 @@
###############################################################################
#
# OERPScenario, OpenERP Functional Tests
# Copyright 2012 Camptocamp SA
# Author Nicolas Bessi
##############################################################################
# Features Generic tags (none for all)
##############################################################################
@account_credit_control @account_credit_control_run @account_credit_control_run_jul
Feature: Ensure that email credit line generation first pass is correct
@account_credit_control_mark
Scenario: mark lines
Given there is "draft" credit lines
And I mark all draft email to state "to_be_sent"
Then the draft line should be in state "to_be_sent"
@account_credit_control_run_month
Scenario: Create run
Given I need a "credit.control.run" with oid: credit_control.run7
And having:
| name | value |
| date | %Y-07-31 |
When I launch the credit run
Then my credit run should be in state "done"
And the generated credit lines should have the following values:
| balance | date due | account | policy | date | partner | channel | level | move line | policy level | state | amount due | currency |
| 1500 | %Y-04-30 | Debtors | 2 time policy | %Y-07-31 | customer_2 | letter | 2 | SI_6 | 60 days last reminder | draft | 1500 | USD |
| 1500 | %Y-04-14 | Debtors | 2 time policy | %Y-07-31 | customer_3 | letter | 2 | SI_9 | 60 days last reminder | draft | 1500 | USD |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-07-31 | customer_4 | letter | 3 | SI_12 | 10 days last reminder | draft | 1050 | USD |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-07-31 | Donald Duck | letter | 3 | SI_18 | 10 days last reminder | draft | 1050 | |
| 1050 | %Y-04-30 | Debtors | 3 time policy | %Y-07-31 | Gus Goose | letter | 3 | SI_19 | 10 days last reminder | draft | 1050 | |

View File

@@ -0,0 +1,120 @@
import time
from behave import given, when
from support import model
@given(u'I configure the following accounts on the credit control policy with oid: "{policy_oid}"')
def impl(ctx, policy_oid):
policy = model('credit.control.policy').get(policy_oid)
assert policy, 'No policy % found' % policy_oid
acc_obj = model('account.account')
accounts = []
for row in ctx.table:
acc = acc_obj.get(['code = %s' % row['account code']])
assert acc, "Account with code %s not found" % row['account code']
accounts.append(acc)
policy.write({'account_ids': [x.id for x in accounts]})
@when(u'I launch the credit run')
def impl(ctx):
assert ctx.found_item
# Must be a cleaner way to do it
assert 'credit.control.run' == ctx.found_item._model._name
ctx.found_item.generate_credit_lines()
@given(u'I clean all the credit lines')
def impl(ctx):
model('credit.control.line').browse([]).unlink()
@then(u'my credit run should be in state "done"')
def impl(ctx):
assert ctx.found_item
# Must be a cleaner way to do it
assert model("credit.control.run").get(ctx.found_item.id).state == 'done'
@then(u'the generated credit lines should have the following values')
def impl(ctx):
def _row_to_dict(row):
return dict((name, row[name]) for name in row.headings if row[name])
rows = map(_row_to_dict, ctx.table)
def _parse_date(value):
return time.strftime(value) if '%' in value else value
for row in rows:
account = model('account.account').get(['name = %s' % row['account']])
assert account, "no account named %s found" % row['account']
policy = model('credit.control.policy').get(['name = %s' % row['policy']])
assert policy, "No policy %s found" % row['policy']
partner = model('res.partner').get(['name = %s' % row['partner']])
assert partner, "No partner %s found" % row['partner']
maturity_date = _parse_date(row['date due'])
move_line = model('account.move.line').get(['name = %s' % row['move line'],
'date_maturity = %s' % maturity_date])
assert move_line, "No move line %s found" % row['move line']
level = model('credit.control.policy.level').get(['name = %s' % row['policy level'],
'policy_id = %s' % policy.id])
assert level, "No level % found" % row['policy level']
domain = [['account_id', '=', account.id],
['policy_id', '=', policy.id],
['partner_id', '=', partner.id],
['policy_level_id', '=', level.id],
['amount_due', '=', row.get('amount due', 0.0)],
['state', '=', row['state']],
['level', '=', row.get('level', 0.0)],
['channel', '=', row['channel']],
['balance_due', '=', row.get('balance', 0.0)],
['date_due', '=', _parse_date(row['date due'])],
['date', '=', _parse_date(row['date'])],
['move_line_id', '=', move_line.id],
]
if row.get('currency'):
curreny = model('res.currency').get(['name = %s' % row['currency']])
assert curreny, "No currency %s found" % row['currency']
domain.append(('currency_id', '=', curreny.id))
lines = model('credit.control.line').search(domain)
assert lines, "no line found for %s" % repr(row)
assert len(lines) == 1, "Too many lines found for %s" % repr(row)
date_lines = model('credit.control.line').search([('date', '=', ctx.found_item.date)])
assert len(date_lines) == len(ctx.table.rows), "Too many lines generated"
def open_invoice(ctx):
assert ctx.found_item
ctx.found_item._send('invoice_open')
# _send refresh object
assert ctx.found_item.state == 'open'
@then(u'I open the credit invoice')
def impl(ctx):
open_invoice(ctx)
@given(u'I open the credit invoice')
def impl(ctx):
open_invoice(ctx)
@given(u'there is "{state}" credit lines')
def impl(ctx, state):
assert model('credit.control.line').search(['state = %s' % state])
@given(u'I mark all draft email to state "{state}"')
def impl(ctx, state):
wiz = model('credit.control.marker').create({'name': state})
lines = model('credit.control.line').search([('state', '=', 'draft')])
assert lines
ctx.lines = lines
wiz.write({'line_ids': lines})
wiz.mark_lines()
@then(u'the draft line should be in state "{state}"')
def impl(ctx, state):
assert ctx.lines
lines = model('credit.control.line').search([('state', '!=', state),
('id', 'in', ctx.lines)])
assert not lines

View File

@@ -0,0 +1,97 @@
from support import *
import datetime
@step('I import invoice "{inv_name}" using import invoice button')
def impl(ctx, inv_name):
invoice = model('account.invoice').get([('name', '=', inv_name)])
assert invoice
bank_statement = ctx.found_item
for line in bank_statement.line_ids:
line.unlink()
lines = model('account.move.line').browse([('move_id', '=', invoice.move_id.id),
('account_id', '=', invoice.account_id.id)])
wizard = model('account.statement.from.invoice.lines').create({'line_ids': lines})
wizard.populate_statement({'statement_id': bank_statement.id})
@given(u'I should have a "account.bank.statement.line" with name: "{name}" and amount: "{amount}"')
def impl(ctx, name, amount):
assert ctx.found_item
line = model('account.bank.statement.line').get([('name', '=', name),
('amount', '=', amount),
('statement_id', '=', ctx.found_item.id)])
assert line
ctx.line = line
@given(u'I set the voucher paid amount to "{amount}"')
def impl(ctx, amount):
assert ctx.line
voucher = model('account.voucher').get(ctx.line.voucher_id.id)
assert voucher
vals = voucher.onchange_amount(float(amount),
voucher.payment_rate,
voucher.partner_id.id,
voucher.journal_id.id if voucher.journal_id else False,
voucher.currency_id.id if voucher.currency_id else False,
voucher.type,
voucher.date,
voucher.payment_rate,
voucher.company_id.id if voucher.company_id else false)
vals = vals['value']
vals.update({'amount': ctx.line.voucher_id.amount})
voucher_line_ids = []
voucher_line_dr_ids = []
v_l_obj = model('account.voucher.line')
for v_line_vals in vals.get('line_cr_ids', []) or []:
v_line_vals['voucher_id'] = voucher.id
voucher_line_ids.append(v_l_obj.create(v_line_vals).id)
vals['line_cr_ids'] = voucher_line_ids
for v_line_vals in vals.get('line_dr_ids', []) or []:
v_line_vals['voucher_id'] = voucher.id
voucher_line_dr_ids.append(v_l_obj.create(v_line_vals).id)
vals['line_dr_ids'] = voucher_line_ids
voucher.write(vals)
ctx.vals = vals
ctx.voucher = voucher
@given(u'I save the voucher')
def impl(ctx):
assert True
@given(u'I modify the line amount to "{amount}"')
@then(u'I modify the line amount to "{amount}"')
def impl(ctx, amount):
assert ctx.line
# we have to change voucher amount before chaning statement line amount
if ctx.line.voucher_id:
model('account.voucher').write([ctx.line.voucher_id.id],
{'amount': float(amount)})
ctx.line.write({'amount': float(amount)})
@step('My invoice "{inv_name}" is in state "{state}" reconciled with a residual amount of "{amount:f}"')
def impl(ctx, inv_name, state, amount):
invoice = model('account.invoice').get([('name', '=', inv_name)])
assert_almost_equal(invoice.residual, amount)
assert_equal(invoice.state, state)
@step('I modify the bank statement line amount to {amount:f}')
def impl(ctx, amount):
line = ctx.found_item.voucher_id.line_cr_ids[0]
#ctx.voucher = model('account.voucher').get(ctx.found_item.voucher_id.id)
ctx.found_item.on_change('onchange_amount', 'amount', (), amount)
@then(u'I set bank statement end-balance')
@given(u'I set bank statement end-balance')
def impl(ctx):
assert ctx.found_item, "No statement found"
ctx.found_item.write({'balance_end_real': ctx.found_item.balance_end})
assert ctx.found_item.balance_end == ctx.found_item.balance_end_real
@when(u'I confirm bank statement')
def impl(ctx):
assert ctx.found_item
assert_equal(ctx.found_item._model._name, 'account.bank.statement')
ctx.found_item.button_confirm_bank()

View File

@@ -16,3 +16,6 @@
"account_credit_control.ir_model_access_287",1,1,"group_account_credit_control_manager","credit_control_manager_level","account_credit_control.model_credit_control_policy_level",1,1
"account_credit_control.ir_model_access_288",0,0,"group_account_credit_control_user","credit_control_user_level","account_credit_control.model_credit_control_policy_level",1,0
"account_credit_control.ir_model_access_289",0,0,"group_account_credit_control_info","credit_control_info_level","account_credit_control.model_credit_control_policy_level",1,0
"account_credit_control.ir_model_access_290",0,0,"account.group_account_user","credit_control_fin_user_line","account_credit_control.model_credit_control_line",1,0
"account_credit_control.ir_model_access_291",0,0,"account.group_account_invoice","credit_control_fin_invoice_line","account_credit_control.model_credit_control_line",1,0
"account_credit_control.ir_model_access_292",1,1,"account.group_account_manager","credit_control_fin_manager_line","account_credit_control.model_credit_control_line",1,1
1 id perm_create perm_unlink group_id/id name model_id/id perm_read perm_write
16 account_credit_control.ir_model_access_287 1 1 group_account_credit_control_manager credit_control_manager_level account_credit_control.model_credit_control_policy_level 1 1
17 account_credit_control.ir_model_access_288 0 0 group_account_credit_control_user credit_control_user_level account_credit_control.model_credit_control_policy_level 1 0
18 account_credit_control.ir_model_access_289 0 0 group_account_credit_control_info credit_control_info_level account_credit_control.model_credit_control_policy_level 1 0
19 account_credit_control.ir_model_access_290 0 0 account.group_account_user credit_control_fin_user_line account_credit_control.model_credit_control_line 1 0
20 account_credit_control.ir_model_access_291 0 0 account.group_account_invoice credit_control_fin_invoice_line account_credit_control.model_credit_control_line 1 0
21 account_credit_control.ir_model_access_292 1 1 account.group_account_manager credit_control_fin_manager_line account_credit_control.model_credit_control_line 1 1

View File

@@ -20,15 +20,13 @@
##############################################################################
import netsvc
import logging
from openerp.osv.orm import TransientModel, fields
from openerp.osv.osv import except_osv
from openerp.tools.translate import _
from openerp.osv.orm import TransientModel, fields
logger = logging.getLogger('credit.control.line.mailing')
class CreditCommunication(TransientModel):
"""Shell calss used to provide a base model to email template and reporting.
"""Shell class used to provide a base model to email template and reporting.
Il use this approche in version 7 a browse record will exist even if not saved"""
_name = "credit.control.communication"
_description = "credit control communication"
@@ -51,36 +49,24 @@ class CreditCommunication(TransientModel):
cr, uid, 'credit.control.policy', context=c),
'user_id': lambda s, cr, uid, c: uid}
def get_address(self, cr, uid, com_id, context=None):
"""Return a valid address for customer"""
assert not (isinstance(com_id, list) and len(com_id) > 1), \
"com_id: only one id expected"
if isinstance(com_id, list):
com_id = com_id[0]
form = self.browse(cr, uid, com_id, context=context)
part_obj = self.pool.get('res.partner')
adds = part_obj.address_get(cr, uid, [form.partner_id.id],
adr_pref=['invoice', 'default'])
add = adds.get('invoice', adds.get('default'))
add_obj = self.pool.get('res.partner.address')
if add:
return add_obj.browse(cr, uid, add, context=context)
else:
return False
def get_email(self, cr, uid, com_id, context=None):
"""Return a valid email for customer"""
assert not (isinstance(com_id, list) and len(com_id) > 1), \
"com_id: only one id expected"
if isinstance(com_id, list):
assert len(com_id) == 1, "get_email only support one id as parameter"
com_id = com_id[0]
form = self.browse(cr, uid, com_id, context=context)
contact = form.get_contact_address()
return contact.email
def get_contact_address(self, cr, uid, com_id, context=None):
pmod = self.pool['res.partner']
if isinstance(com_id, list):
com_id = com_id[0]
form = self.browse(cr, uid, com_id, context=context)
address = form.get_address()
email = ''
if address and address.email:
email = address.email
return email
part = form.partner_id
add_ids = part.address_get(adr_pref=['invoice']) or {}
add_id = add_ids.get('invoice', add_ids.get('default', False))
return pmod.browse(cr, uid, add_id, context)
def _get_credit_lines(self, cr, uid, line_ids, partner_id, level_id, context=None):
"""Return credit lines related to a partner and a policy level"""
@@ -124,15 +110,13 @@ class CreditCommunication(TransientModel):
"""Generate email message using template related to level"""
cr_line_obj = self.pool.get('credit.control.line')
email_temp_obj = self.pool.get('email.template')
email_message_obj = self.pool.get('mail.message')
email_message_obj = self.pool.get('mail.mail')
att_obj = self.pool.get('ir.attachment')
email_ids = []
essential_fields = [
'subject',
'body_html',
'email_from',
'email_to'
]
essential_fields = ['subject',
'body_html',
'email_from',
'email_to']
for comm in comms:
# we want to use a local cr in order to send the maximum
@@ -141,9 +125,11 @@ class CreditCommunication(TransientModel):
email_values = {}
cl_ids = [cl.id for cl in comm.credit_control_line_ids]
email_values = email_temp_obj.generate_email(cr, uid,
template,
comm.id,
context=context)
template,
comm.id,
context=context)
email_values['body_html'] = email_values['body']
email_values['type'] = 'email'
email_id = email_message_obj.create(cr, uid, email_values, context=context)
@@ -160,7 +146,22 @@ class CreditCommunication(TransientModel):
{'mail_message_id': email_id,
'state': state},
context=context)
att_ids = []
for att in email_values.get('attachments', []):
attach_fname = att[0]
attach_datas = att[1]
data_attach = {
'name': attach_fname,
'datas': attach_datas,
'datas_fname': attach_fname,
'res_model': 'mail.mail',
'res_id': email_id,
'type': 'binary',
}
att_ids.append(att_obj.create(cr, uid, data_attach, context=context))
email_message_obj.write(cr, uid, [email_id],
{'attachment_ids': [(6, 0, att_ids)]},
context=context)
email_ids.append(email_id)
return email_ids
@@ -178,4 +179,3 @@ class CreditCommunication(TransientModel):
l_obj = self.pool.get('credit.control.line')
l_obj.write(cr, uid, line_ids, {'state': 'sent'}, context=context)
return line_ids

View File

@@ -19,12 +19,11 @@
#
##############################################################################
from openerp.osv.orm import TransientModel, fields
from openerp.osv.osv import except_osv
from openerp.osv import orm, fields
from openerp.tools.translate import _
class CreditControlEmailer(TransientModel):
class CreditControlEmailer(orm.TransientModel):
"""Send emails for each selected credit control lines."""
_name = "credit.control.emailer"
@@ -71,7 +70,7 @@ class CreditControlEmailer(TransientModel):
form = self.browse(cr, uid, wiz_id, context)
if not form.line_ids:
raise except_osv(_('Error'), _('No credit control lines selected.'))
raise orm.except_orm(_('Error'), _('No credit control lines selected.'))
line_ids = [l.id for l in form.line_ids]
filtered_ids = self._filter_line_ids(

View File

@@ -6,7 +6,7 @@
<field name="model">credit.control.emailer</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Mailer">
<separator string="Send emails for the selected lines" colspan="4"/>
<newline/>
<field name="line_ids" colspan="4" nolabel="1" />

View File

@@ -18,12 +18,11 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
from openerp.osv.orm import TransientModel, fields
from openerp.osv.osv import except_osv
from openerp.osv import orm, fields
from openerp.tools.translate import _
class CreditControlMarker(TransientModel):
class CreditControlMarker(orm.TransientModel):
"""Change the state of lines in mass"""
_name = 'credit.control.marker'
@@ -81,7 +80,7 @@ class CreditControlMarker(TransientModel):
form = self.browse(cr, uid, wiz_id, context)
if not form.line_ids:
raise except_osv(_('Error'), _('No credit control lines selected.'))
raise orm.except_orm(_('Error'), _('No credit control lines selected.'))
line_ids = [l.id for l in form.line_ids]

View File

@@ -6,7 +6,7 @@
<field name="model">credit.control.marker</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Lines marker">
<separator string="Change the state of the selected lines." colspan="4"/>
<label string="Warning: you will maybe not be able to revert this operation." colspan="4"></label>
<newline/>

View File

@@ -20,11 +20,10 @@
##############################################################################
import base64
from openerp.osv.orm import TransientModel, fields
from openerp.osv.osv import except_osv
from openerp.osv import orm, fields
from openerp.tools.translate import _
class CreditControlPrinter(TransientModel):
class CreditControlPrinter(orm.TransientModel):
"""Print lines"""
_name = "credit.control.printer"
@@ -65,25 +64,30 @@ class CreditControlPrinter(TransientModel):
def print_lines(self, cr, uid, wiz_id, context=None):
assert not (isinstance(wiz_id, list) and len(wiz_id) > 1), \
"wiz_id: only one id expected"
"wiz_id: only one id expected"
comm_obj = self.pool.get('credit.control.communication')
if isinstance(wiz_id, list):
wiz_id = wiz_id[0]
form = self.browse(cr, uid, wiz_id, context)
if not form.line_ids and not form.print_all:
raise except_osv(_('Error'), _('No credit control lines selected.'))
raise orm.except_orm(_('Error'), _('No credit control lines selected.'))
line_ids = [l.id for l in form.line_ids]
comms = comm_obj._generate_comm_from_credit_line_ids(
cr, uid, line_ids, context=context)
comms = comm_obj._generate_comm_from_credit_line_ids(cr, uid, line_ids,
context=context)
report_file = comm_obj._generate_report(cr, uid, comms, context=context)
form.write({'report_file': base64.b64encode(report_file), 'state': 'done'})
if form.mark_as_sent:
filtered_ids = self._filter_line_ids(cr, uid, line_ids, context)
comm_obj._mark_credit_line_as_sent(cr, uid, comms, context=context)
return False # do not close the window, we need it to download the report
return {'type': 'ir.actions.act_window',
'res_model': 'credit.control.printer',
'view_mode': 'form',
'view_type': 'form',
'res_id': form.id,
'views': [(False, 'form')],
'target': 'new',
}

View File

@@ -6,7 +6,7 @@
<field name="model">credit.control.printer</field>
<field name="type">form</field>
<field name="arch" type="xml">
<form>
<form string="Lines report">
<separator colspan="4" string="Print the selected lines"/>
<newline/>
<field name="mark_as_sent" colspan="4" attrs="{'invisible': [('state', '=', 'done')]}"/>