[MERGE]: Merged with lp:openobject-addons

bzr revid: atp@tinyerp.com-20120925050759-xueuicxhp36ahpe9
This commit is contained in:
Atul Patel (OpenERP)
2012-09-25 10:37:59 +05:30
124 changed files with 138790 additions and 207503 deletions
+10 -2
View File
@@ -63,6 +63,8 @@ for a particular financial year and for preparation of vouchers there is a modul
'wizard/account_use_model_view.xml',
'account_installer.xml',
'wizard/account_period_close_view.xml',
'wizard/account_reconcile_view.xml',
'wizard/account_unreconcile_view.xml',
'account_view.xml',
'account_report.xml',
'account_financial_report_data.xml',
@@ -85,14 +87,12 @@ for a particular financial year and for preparation of vouchers there is a modul
'wizard/account_journal_select_view.xml',
'wizard/account_change_currency_view.xml',
'wizard/account_validate_move_view.xml',
'wizard/account_unreconcile_view.xml',
'wizard/account_report_general_ledger_view.xml',
'wizard/account_invoice_state_view.xml',
'wizard/account_report_partner_balance_view.xml',
'wizard/account_report_account_balance_view.xml',
'wizard/account_report_aged_partner_balance_view.xml',
'wizard/account_report_partner_ledger_view.xml',
'wizard/account_reconcile_view.xml',
'wizard/account_reconcile_partner_process_view.xml',
'wizard/account_automatic_reconcile_view.xml',
'wizard/account_financial_report_view.xml',
@@ -126,6 +126,14 @@ for a particular financial year and for preparation of vouchers there is a modul
'res_config_view.xml',
'account_pre_install.yml'
],
'js': [
'static/src/js/account_move_reconciliation.js',
],
'qweb' : [
"static/src/xml/account_move_reconciliation.xml",
],
'css':['static/src/css/account_move_reconciliation.css'
],
'demo': [
'demo/account_demo.xml',
'project/project_demo.xml',
+5 -4
View File
@@ -601,7 +601,7 @@ class account_account(osv.osv):
if not default:
default = {}
default = default.copy()
default['code'] = (account['code'] or '') + '(copy)'
default.update(code=_("%s (copy)") % (account['code'] or ''))
if not local:
done_list = []
if account.id in done_list:
@@ -782,9 +782,10 @@ class account_journal(osv.osv):
if not default:
default = {}
default = default.copy()
default['code'] = (journal['code'] or '') + '(copy)'
default['name'] = (journal['name'] or '') + '(copy)'
default['sequence_id'] = False
default.update(
code=_("%s (copy)") % (journal['code'] or ''),
name=_("%s (copy)") % (journal['name'] or ''),
sequence_id=False)
return super(account_journal, self).copy(cr, uid, id, default, context=context)
def write(self, cr, uid, ids, vals, context=None):
+17 -15
View File
@@ -708,7 +708,9 @@ class account_move_line(osv.osv):
context = {}
if context and context.get('next_partner_only', False):
if not context.get('partner_id', False):
partner = self.get_next_partner_only(cr, uid, offset, context)
partner = self.list_partners_to_reconcile(cr, uid, context=context)
if partner:
partner = partner[0]
else:
partner = context.get('partner_id', False)
if not partner:
@@ -716,26 +718,26 @@ class account_move_line(osv.osv):
args.append(('partner_id', '=', partner[0]))
return super(account_move_line, self).search(cr, uid, args, offset, limit, order, context, count)
def get_next_partner_only(self, cr, uid, offset=0, context=None):
def list_partners_to_reconcile(self, cr, uid, context=None):
cr.execute(
"""
SELECT p.id
FROM res_partner p
RIGHT JOIN (
SELECT l.partner_id AS partner_id, SUM(l.debit) AS debit, SUM(l.credit) AS credit
SELECT partner_id
FROM (
SELECT l.partner_id, p.last_reconciliation_date, SUM(l.debit) AS debit, SUM(l.credit) AS credit
FROM account_move_line l
LEFT JOIN account_account a ON (a.id = l.account_id)
LEFT JOIN res_partner p ON (l.partner_id = p.id)
RIGHT JOIN account_account a ON (a.id = l.account_id)
RIGHT JOIN res_partner p ON (l.partner_id = p.id)
WHERE a.reconcile IS TRUE
AND l.reconcile_id IS NULL
AND (p.last_reconciliation_date IS NULL OR l.date > p.last_reconciliation_date)
AND l.state <> 'draft'
GROUP BY l.partner_id
) AS s ON (p.id = s.partner_id)
GROUP BY l.partner_id, p.last_reconciliation_date
) AS s
WHERE debit > 0 AND credit > 0
ORDER BY p.last_reconciliation_date LIMIT 1 OFFSET %s""", (offset, )
)
return cr.fetchone()
ORDER BY last_reconciliation_date""")
ids = cr.fetchall()
ids = len(ids) and [x[0] for x in ids] or []
return self.pool.get('res.partner').name_get(cr, uid, ids, context=context)
def reconcile_partial(self, cr, uid, ids, type='auto', context=None, writeoff_acc_id=False, writeoff_period_id=False, writeoff_journal_id=False):
move_rec_obj = self.pool.get('account.move.reconcile')
@@ -915,8 +917,8 @@ class account_move_line(osv.osv):
if lines and lines[0]:
partner_id = lines[0].partner_id and lines[0].partner_id.id or False
if partner_id and context and context.get('stop_reconcile', False):
partner_obj.write(cr, uid, [partner_id], {'last_reconciliation_date': time.strftime('%Y-%m-%d %H:%M:%S')})
if not partner_obj.has_something_to_reconcile(cr, uid, partner_id, context=context):
partner_obj.mark_as_reconciled(cr, uid, [partner_id], context=context)
return r_id
def view_header_get(self, cr, user, view_id, view_type, context=None):
+2 -2
View File
@@ -1551,12 +1551,12 @@
</record>
<record id="action_account_manual_reconcile" model="ir.actions.act_window">
<field name="context">{'search_default_next_partner':1,'view_mode':True}</field>
<field name="context">{'search_default_unreconciled': 1,'view_mode':True}</field>
<field name="name">Journal Items to Reconcile</field>
<field name="res_model">account.move.line</field>
<field name="view_id" ref="view_move_line_tree_reconcile"/>
<field name="view_type">form</field>
<field name="view_mode">tree,form</field>
<field name="view_mode">account_reconciliation_list</field>
<field name="help" type="html">
<p>
Good job!
+20 -2
View File
@@ -122,6 +122,14 @@
<field name="type">other</field>
<field name="user_type" ref="data_account_type_income"/>
</record>
<record id="usd_bnk" model="account.account">
<field name="code">X11007</field>
<field name="name">USD Bank Account - (test)</field>
<field ref="cas" name="parent_id"/>
<field name="type">liquidity</field>
<field name="user_type" ref="data_account_type_asset"/>
<field name="currency_id" ref="base.USD"/>
</record>
<record model="account.account" id="liabilities_view">
<field name="name">Liabilities - (test)</field>
@@ -360,8 +368,8 @@
<field name="type">bank</field>
<field name="view_id" ref="account_journal_bank_view"/>
<field name="sequence_id" ref="sequence_bank_journal"/>
<field model="account.account" name="default_debit_account_id" ref="cash"/>
<field model="account.account" name="default_credit_account_id" ref="cash"/>
<field model="account.account" name="default_debit_account_id" ref="bnk"/>
<field model="account.account" name="default_credit_account_id" ref="bnk"/>
<field name="analytic_journal_id" ref="sit"/>
<field name="user_id" ref="base.user_root"/>
</record>
@@ -412,6 +420,16 @@
<field eval="True" name="centralisation"/>
<field name="user_id" ref="base.user_root"/>
</record>
<record id="bank_journal_usd" model="account.journal">
<field name="name">USD Bank Journal - (test)</field>
<field name="code">TUBK</field>
<field name="type">bank</field>
<field name="view_id" ref="account_journal_bank_view"/>
<field model="account.account" name="usd_debit_account_id" ref="usd_bnk"/>
<field model="account.account" name="usd_credit_account_id" ref="usd_bnk"/>
<field name="currency_id" ref="base.USD"/>
</record>
<!--
Product income and expense accounts, default parameters
-->
+25 -2
View File
@@ -20,8 +20,8 @@
##############################################################################
from operator import itemgetter
from osv import fields, osv
import time
class account_fiscal_position(osv.osv):
_name = 'account.fiscal.position'
@@ -145,6 +145,29 @@ class res_partner(osv.osv):
def _debit_search(self, cr, uid, obj, name, args, context=None):
return self._asset_difference_search(cr, uid, obj, name, 'payable', args, context=context)
def has_something_to_reconcile(self, cr, uid, partner_id, context=None):
'''
at least a debit, a credit and a line older than the last reconciliation date of the partner
'''
cr.execute('''
SELECT l.partner_id, SUM(l.debit) AS debit, SUM(l.credit) AS credit
FROM account_move_line l
RIGHT JOIN account_account a ON (a.id = l.account_id)
RIGHT JOIN res_partner p ON (l.partner_id = p.id)
WHERE a.reconcile IS TRUE
AND p.id = %s
AND l.reconcile_id IS NULL
AND (p.last_reconciliation_date IS NULL OR l.date > p.last_reconciliation_date)
AND l.state <> 'draft'
GROUP BY l.partner_id''', (partner_id,))
res = cr.dictfetchone()
if res:
return bool(res['debit'] and res['credit'])
return False
def mark_as_reconciled(self, cr, uid, ids, context=None):
return self.write(cr, uid, ids, {'last_reconciliation_date': time.strftime('%Y-%m-%d %H:%M:%S')}, context=context)
_columns = {
'credit': fields.function(_credit_debit_get,
fnct_search=_credit_search, string='Total Receivable', multi='dc', help="Total amount this customer owes you."),
@@ -185,7 +208,7 @@ class res_partner(osv.osv):
help="This payment term will be used instead of the default one for the current partner"),
'ref_companies': fields.one2many('res.company', 'partner_id',
'Companies that refers to partner'),
'last_reconciliation_date': fields.datetime('Latest Reconciliation Date', help='Date on which the partner accounting entries were reconciled last time')
'last_reconciliation_date': fields.datetime('Latest Reconciliation Date', help='Date on which the partner accounting entries were fully reconciled last time. It differs from the date of the last reconciliation made for this partner, as here we depict the fact that nothing more was to be reconciled at this date. This can be achieved in 2 ways: either the last debit/credit entry was reconciled, either the user pressed the button "Fully Reconciled" in the manual reconciliation process')
}
res_partner()
+44 -33
View File
@@ -1,5 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<openerp><data>
<openerp>
<data>
<record id="group_account_invoice" model="res.groups">
<field name="name">Invoicing &amp; Payments</field>
@@ -7,11 +8,13 @@
<field name="users" eval="[(4, ref('base.user_root'))]"/>
<field name="implied_ids" eval="[(4, ref('base.group_user'))]"/>
</record>
<record id="group_account_user" model="res.groups">
<field name="name">Accountant</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
<field name="implied_ids" eval="[(4, ref('group_account_invoice'))]"/>
</record>
<record id="group_account_manager" model="res.groups">
<field name="name">Manager</field>
<field name="category_id" ref="base.module_category_accounting_and_finance"/>
@@ -25,100 +28,107 @@
<record id="account_move_comp_rule" model="ir.rule">
<field name="name">Account Entry</field>
<field ref="model_account_move" name="model_id"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_move"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="account_move_line_comp_rule" model="ir.rule">
<field name="name">Entry lines</field>
<field model="ir.model" name="model_id" ref="model_account_move_line"/>
<field eval="True" name="global"/>
<field name="name">Entry lines</field>
<field name="model_id" ref="model_account_move_line"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="journal_period_comp_rule" model="ir.rule">
<field name="name">Journal Period</field>
<field model="ir.model" name="model_id" ref="model_account_journal_period"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_journal_period"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="journal_comp_rule" model="ir.rule">
<field name="name">Journal multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_journal"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_journal"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="analytic_journal_comp_rule" model="ir.rule">
<field name="name">Analytic journal multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_analytic_journal"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_analytic_journal"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="period_comp_rule" model="ir.rule">
<field name="name">Period multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_period"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_period"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="fiscal_year_comp_rule" model="ir.rule">
<field name="name">Fiscal year multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_fiscalyear"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_fiscalyear"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="account_comp_rule" model="ir.rule">
<field name="name">Account multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_account"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_account"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="tax_comp_rule" model="ir.rule">
<field name="name">Tax multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_tax"/>
<field eval="True" name="global"/>
<field name="name">Tax multi-company</field>
<field name="model_id" ref="model_account_tax"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="tax_code_comp_rule" model="ir.rule">
<field name="name">Tax code multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_tax_code"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_tax_code"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="invoice_comp_rule" model="ir.rule">
<field name="name">Invoice multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_invoice"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_invoice"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="invoice_analysis_comp_rule" model="ir.rule">
<field name="name">Invoice Analysis multi-company</field>
<field model="ir.model" name="model_id" ref="model_account_invoice_report"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_invoice_report"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="entry_analysis_comp_rule" model="ir.rule">
<field name="name">Entries Analysis multi-company</field>
<field name="model_id" ref="model_account_entries_report"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="account_fiscal_position_comp_rule" model="ir.rule">
<field name="name">Account fiscal Mapping company rule</field>
<field model="ir.model" name="model_id" ref="model_account_fiscal_position"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_fiscal_position"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
<record id="account_model_comp_rule" model="ir.rule">
<field name="name">Account model company rule</field>
<field model="ir.model" name="model_id" ref="model_account_model"/>
<field eval="True" name="global"/>
<field name="model_id" ref="model_account_model"/>
<field name="global" eval="True"/>
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
@@ -143,4 +153,5 @@
<field name="domain_force">['|',('company_id','=',False),('company_id','child_of',[user.company_id.id])]</field>
</record>
</data></openerp>
</data>
</openerp>
@@ -0,0 +1,19 @@
.openerp .oe_account_reconciliation {
border-bottom: 1px solid #CACACA;
padding: 5px;
}
.openerp .oe_account_reconciliation button {
margin: 3px;
}
.openerp .oe_account_reconciliation>div {
display: table;
width: 100%;
}
.openerp .oe_account_reconciliation>div>div {
display: table-cell;
width: 50%:
}
@@ -0,0 +1,124 @@
openerp.account = function (instance) {
var _t = instance.web._t,
_lt = instance.web._lt;
var QWeb = instance.web.qweb;
instance.web.account = {};
instance.web.views.add('account_reconciliation_list', 'instance.web.account.ReconciliationListView');
instance.web.account.ReconciliationListView = instance.web.ListView.extend({
init: function() {
this._super.apply(this, arguments);
var self = this;
this.current_partner = null;
this.do_select.add(function() {
if (self.get_selected_ids().length === 0) {
self.$(".oe_account_recon_reconcile").attr("disabled", "");
} else {
self.$(".oe_account_recon_reconcile").removeAttr("disabled");
}
});
},
on_loaded: function() {
var self = this;
var tmp = this._super.apply(this, arguments);
if (this.partners) {
this.$el.prepend(QWeb.render("AccountReconciliation", {widget: this}));
this.$(".oe_account_recon_previous").click(function() {
self.current_partner = (self.current_partner - 1) % self.partners.length;
self.search_by_partner();
});
this.$(".oe_account_recon_next").click(function() {
self.current_partner = (self.current_partner + 1) % self.partners.length;
self.search_by_partner();
});
this.$(".oe_account_recon_reconcile").click(function() {
self.reconcile();
});
this.$(".oe_account_recom_mark_as_reconciled").click(function() {
self.mark_as_reconciled();
});
}
return tmp;
},
do_search: function(domain, context, group_by) {
var self = this;
this.last_domain = domain;
this.last_context = context;
this.last_group_by = group_by;
this.old_search = _.bind(this._super, this);
var mod = new instance.web.Model("account.move.line", context, domain);
return mod.call("list_partners_to_reconcile", []).pipe(function(result) {
var current = self.current_partner !== null ? self.partners[self.current_partner][0] : null;
self.partners = result;
var index = _.find(_.range(self.partners.length), function(el) {
if (current === self.partners[el][0])
return true;
});
if (index !== undefined)
self.current_partner = index;
else
self.current_partner = self.partners.length == 0 ? null : 0;
self.search_by_partner();
});
},
search_by_partner: function() {
var self = this;
var fct = function() {
return self.old_search(new instance.web.CompoundDomain(self.last_domain,
[["partner_id", "in", self.current_partner === null ? [] :
[self.partners[self.current_partner][0]] ]]), self.last_context, self.last_group_by);
};
if (self.current_partner === null) {
self.last_reconciliation_date = _t("Never");
return fct();
} else {
return new instance.web.Model("res.partner").call("read",
[self.partners[self.current_partner][0], ["last_reconciliation_date"]]).pipe(function(res) {
self.last_reconciliation_date =
instance.web.format_value(res.last_reconciliation_date, {"type": "datetime"}, _t("Never"));
return fct();
});
}
},
reconcile: function() {
var self = this;
var ids = this.get_selected_ids();
if (ids.length === 0) {
instance.web.dialog($("<div />").text(_t("You must choose at least one record.")), {
title: _t("Warning"),
modal: true
});
return false;
}
new instance.web.Model("ir.model.data").call("get_object_reference", ["account", "action_view_account_move_line_reconcile"]).pipe(function(result) {
var additional_context = _.extend({
active_id: ids[0],
active_ids: ids,
active_model: self.model
});
return self.rpc("/web/action/load", {
action_id: result[1],
context: additional_context
}, function (result) {
result = result.result;
result.context = _.extend(result.context || {}, additional_context);
result.flags = result.flags || {};
result.flags.new_window = true;
return self.do_action(result, function () {
self.do_search(self.last_domain, self.last_context, self.last_group_by);
});
});
});
},
mark_as_reconciled: function() {
var self = this;
var id = self.partners[self.current_partner][0];
new instance.web.Model("res.partner").call("mark_as_reconciled", [[id]]).pipe(function() {
self.do_search(self.last_domain, self.last_context, self.last_group_by);
});
},
});
};
@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="UTF-8"?>
<templates id="template" xml:space="preserve">
<t t-name="AccountReconciliation">
<div class="oe_account_reconciliation">
<t t-if="widget.current_partner === null">
There is no pending reconciliation.
</t>
<t t-if="widget.current_partner !== null">
<div>
<div>
<button class="oe_account_recon_previous oe_button" href="javascript:void(0)">&lt;</button>
<t t-esc="'' + widget.partners[widget.current_partner][1] + ' (' + (widget.current_partner + 1) + '/' + widget.partners.length + ')'"/>
<button class="oe_account_recon_next oe_button" href="javascript:void(0)">&gt;</button>
</div>
<div>
Last Reconciliation: <t t-esc="widget.last_reconciliation_date" />
</div>
</div>
<div>
<button class="oe_account_recon_reconcile oe_button oe_highlight" href="javascript:void(0)"
disabled="">Reconcile</button>
<button class="oe_account_recom_mark_as_reconciled oe_button" href="javascript:void(0)">Nothing to reconcile</button>
</div>
</t>
</div>
</t>
</templates>
@@ -86,19 +86,6 @@ class account_move_line_reconcile(osv.osv_memory):
ids = period_obj.find(cr, uid, dt=date, context=context)
if ids:
period_id = ids[0]
#stop the reconciliation process by partner (manual reconciliation) only if there is nothing more to reconcile for this partner
if 'active_ids' in context and context['active_ids']:
tmp_ml_id = account_move_line_obj.browse(cr, uid, context['active_ids'], context)[0]
partner_id = tmp_ml_id.partner_id and tmp_ml_id.partner_id.id or False
debit_ml_ids = account_move_line_obj.search(cr, uid, [('partner_id', '=', partner_id), ('account_id.reconcile', '=', True), ('reconcile_id', '=', False), ('debit', '>', 0)], context=context)
credit_ml_ids = account_move_line_obj.search(cr, uid, [('partner_id', '=', partner_id), ('account_id.reconcile', '=', True), ('reconcile_id', '=', False), ('credit', '>', 0)], context=context)
for ml_id in context['active_ids']:
if ml_id in debit_ml_ids:
debit_ml_ids.remove(ml_id)
if ml_id in credit_ml_ids:
credit_ml_ids.remove(ml_id)
if not debit_ml_ids and credit_ml_ids:
context.update({'stop_reconcile': True})
account_move_line_obj.reconcile(cr, uid, context['active_ids'], 'manual', account_id,
period_id, journal_id, context=context)
return {'type': 'ir.actions.act_window_close'}
@@ -166,7 +153,6 @@ class account_move_line_reconcile_writeoff(osv.osv_memory):
if ids:
period_id = ids[0]
context.update({'stop_reconcile': True})
account_move_line_obj.reconcile(cr, uid, context['active_ids'], 'manual', account_id,
period_id, journal_id, context=context)
return {'type': 'ir.actions.act_window_close'}
@@ -57,10 +57,10 @@ class account_partner_reconcile_process(osv.osv_memory):
def _get_partner(self, cr, uid, context=None):
move_line_obj = self.pool.get('account.move.line')
partner = move_line_obj.get_next_partner_only(cr, uid, offset=1, context=context)
partner = move_line_obj.list_partners_to_reconcile(cr, uid, context=context)
if not partner:
return False
return partner[0]
return partner[0][0]
def data_get(self, cr, uid, to_reconcile, today_reconciled, context=None):
return {'progress': (100 / (float(to_reconcile + today_reconciled) or 1.0)) * today_reconciled}
@@ -100,4 +100,4 @@ class account_partner_reconcile_process(osv.osv_memory):
account_partner_reconcile_process()
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+6 -5
View File
@@ -107,11 +107,12 @@ class coda_bank_account(osv.osv):
if not default:
default = {}
default = default.copy()
default.update({'journal_id': None})
default['description1'] = cba['description1'] or ''
default['description2'] = cba['description2'] or ''
default['name'] = (cba['name'] or '') + ' (copy)'
default['state'] = cba['state']
default.update(
journal_id=None,
description1=cba['description1'] or '',
description2=cba['description2'] or '',
name=_("%s (copy)") % (cba['name'] or ''),
state=cba['state'])
return super(coda_bank_account, self).copy(cr, uid, id, default, context)
def onchange_state(self, cr, uid, ids, state):
+8 -5
View File
@@ -140,7 +140,7 @@ class account_analytic_account(osv.osv):
'name': fields.char('Account/Contract Name', size=128, required=True),
'complete_name': fields.function(_complete_name_calc, type='char', string='Full Account Name'),
'code': fields.char('Reference', size=24, select=True),
'type': fields.selection([('view','Analytic View'), ('normal','Analytic Account'),('contract','Contract or Project'),('template','Template of Project')], 'Type of Account', required=True,
'type': fields.selection([('view','Analytic View'), ('normal','Analytic Account'),('contract','Contract or Project'),('template','Template of Project')], 'Type of Account', required=True,
help="If you select the View Type, it means you won\'t allow to create journal entries using that account.\n"\
"The type 'Analytic account' stands for usual accounts that you only want to use in accounting.\n"\
"If you select Contract or Project, it offers you the possibility to manage the validity and the invoicing options for this account.\n"\
@@ -168,7 +168,7 @@ class account_analytic_account(osv.osv):
'res.company': (_get_analytic_account, ['currency_id'], 10),
}, string='Currency', type='many2one', relation='res.currency'),
}
def on_change_template(self, cr, uid, ids, template_id, context=None):
if not template_id:
return {}
@@ -179,7 +179,7 @@ class account_analytic_account(osv.osv):
res['value']['quantity_max'] = template.quantity_max
res['value']['description'] = template.description
return res
def on_change_partner_id(self, cr, uid, ids,partner_id, name, context={}):
res={}
if partner_id:
@@ -222,8 +222,11 @@ class account_analytic_account(osv.osv):
def copy(self, cr, uid, id, default=None, context=None):
if not default:
default = {}
default['code'] = False
default['line_ids'] = []
analytic = self.browse(cr, uid, id, context=context)
default.update(
code=False,
line_ids=[],
name=_("%s (copy)") % (analytic['name']))
return super(account_analytic_account, self).copy(cr, uid, id, default, context=context)
def on_change_company(self, cr, uid, id, company_id):
+1 -1
View File
@@ -209,7 +209,7 @@ class document_file(osv.osv):
default = {}
if 'name' not in default:
name = self.read(cr, uid, [id], ['name'])[0]['name']
default.update({'name': name + " " + _("(copy)")})
default.update(name=_("%s (copy)") % (name))
return super(document_file, self).copy(cr, uid, id, default, context=context)
def write(self, cr, uid, ids, vals, context=None):
+1 -1
View File
@@ -231,7 +231,7 @@ class document_directory(osv.osv):
if not default:
default ={}
name = self.read(cr, uid, [id])[0]['name']
default.update({'name': name+ " (copy)"})
default.update(name=_("%s (copy)") % (name))
return super(document_directory,self).copy(cr, uid, id, default, context=context)
def _check_duplication(self, cr, uid, vals, ids=[], op='create'):
+5 -2
View File
@@ -215,7 +215,10 @@ class email_template(osv.osv):
if default is None:
default = {}
default = default.copy()
default['name'] = template.name + _('(copy)')
default.update(
name=_("%s (copy)") % (template.name),
ref_ir_act_window=False,
ref_ir_value=False)
return super(email_template, self).copy(cr, uid, id, default, context)
def build_expression(self, field_name, sub_field_name, null_value):
@@ -335,7 +338,7 @@ class email_template(osv.osv):
:param bool force_send: if True, the generated mail.message is
immediately sent after being created, as if the scheduler
was executed for this message only.
:returns: id of the mail.message that was created
:returns: id of the mail.message that was created
"""
if context is None: context = {}
mail_mail = self.pool.get('mail.mail')
+5 -6
View File
@@ -81,10 +81,9 @@ class hr_payroll_structure(osv.osv):
"""
if not default:
default = {}
default.update({
'code': self.browse(cr, uid, id, context=context).code + "(copy)",
'company_id': self.pool.get('res.users').browse(cr, uid, uid, context=context).company_id.id
})
default.update(
code=_("%s (copy)") % (self.browse(cr, uid, id, context=context).code),
company_id=self.pool.get('res.users').browse(cr, uid, uid, context=context).company_id.id)
return super(hr_payroll_structure, self).copy(cr, uid, id, default, context=context)
def get_all_rules(self, cr, uid, structure_ids, context=None):
@@ -305,7 +304,7 @@ class hr_payslip(osv.osv):
return False
return True
_constraints = [(_check_dates, "Payslip 'Date From' must be before 'Date To'.", ['date_from', 'date_to'])]
_constraints = [(_check_dates, "Payslip 'Date From' must be before 'Date To'.", ['date_from', 'date_to'])]
def copy(self, cr, uid, id, default=None, context=None):
if not default:
@@ -851,7 +850,7 @@ result = rules.NET > categories.NET * 0.10''',
"""
:param rule_id: id of rule to compute
:param localdict: dictionary containing the environement in which to compute the rule
:return: returns a tuple build as the base/amount computed, the quantity and the rate
:return: returns a tuple build as the base/amount computed, the quantity and the rate
:rtype: (float, float, float)
"""
rule = self.browse(cr, uid, rule_id, context=context)
+1
View File
@@ -19,6 +19,7 @@
<field name="user_id" ref="base.user_root"/>
<field name="update_posted" eval="True" />
<field name="entry_posted" eval="True" />
<field name="currency" model="res.currency" ref="base.CHF" />
</record>
<record id="bank_euro_journal" model="account.journal">
+1 -1
View File
@@ -356,7 +356,7 @@ class mrp_bom(osv.osv):
if default is None:
default = {}
bom_data = self.read(cr, uid, id, [], context=context)
default.update({'name': bom_data['name'] + ' ' + _('Copy'), 'bom_id':False})
default.update(name=_("%s (copy)") % (bom_data['name']), bom_id=False)
return super(mrp_bom, self).copy_data(cr, uid, id, default, context=context)
def create(self, cr, uid, vals, context=None):
@@ -12,7 +12,7 @@
<record id="portal_stock_picking_user_rule" model="ir.rule">
<field name="name">Portal Personal Delivery Orders</field>
<field ref="stock.model_stock_picking" name="model_id"/>
<field name="model_id" ref="stock.model_stock_picking"/>
<field name="domain_force">[('partner_id','child_of',[user.partner_id.id])]</field>
<field name="groups" eval="[(4, ref('portal.group_portal'))]"/>
</record>
+41 -2
View File
@@ -511,7 +511,7 @@ class product_product(osv.osv):
for obj in self.browse(cr, uid, ids, context=context):
result[obj.id] = tools.image_get_resized_images(obj.image, avoid_resize_medium=True)
return result
def _set_image(self, cr, uid, id, name, value, args, context=None):
return self.write(cr, uid, [id], {'image': tools.image_resize_image_big(value)}, context=context)
@@ -727,7 +727,7 @@ class product_product(osv.osv):
context_wo_lang.pop('lang', None)
product = self.read(cr, uid, id, ['name'], context=context_wo_lang)
default = default.copy()
default['name'] = product['name'] + ' (copy)'
default.update(name=_("%s (copy)") % (product['name']))
if context.get('variant',False):
fields = ['product_tmpl_id', 'active', 'variants', 'default_code',
@@ -897,4 +897,43 @@ class pricelist_partnerinfo(osv.osv):
}
_order = 'min_quantity asc'
pricelist_partnerinfo()
class res_currency(osv.osv):
_inherit = 'res.currency'
def _check_main_currency_rounding(self, cr, uid, ids, context=None):
cr.execute('SELECT digits FROM decimal_precision WHERE name like %s',('Account',))
digits = cr.fetchone()
if digits and len(digits):
digits = digits[0]
main_currency = self.pool.get('res.users').browse(cr, uid, uid, context=context).company_id.currency_id
for currency_id in ids:
if currency_id == main_currency.id:
if main_currency.rounding < 10 ** -digits:
return False
return True
_constraints = [
(_check_main_currency_rounding, 'Error! You cannot define a rounding factor for the company\'s main currency that is smaller than the decimal precision of \'Account\'.', ['rounding']),
]
class decimal_precision(osv.osv):
_inherit = 'decimal.precision'
def _check_main_currency_rounding(self, cr, uid, ids, context=None):
cr.execute('SELECT id, digits FROM decimal_precision WHERE name like %s',('Account',))
res = cr.fetchone()
if res and len(res):
account_precision_id, digits = res
main_currency = self.pool.get('res.users').browse(cr, uid, uid, context=context).company_id.currency_id
for decimal_precision in ids:
if decimal_precision == account_precision_id:
if main_currency.rounding < 10 ** -digits:
return False
return True
_constraints = [
(_check_main_currency_rounding, 'Error! You cannot define the decimal precision of \'Account\' as greater than the rounding factor of the company\'s main currency', ['digits']),
]
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+3 -3
View File
@@ -323,7 +323,7 @@ class project(osv.osv):
default.pop('alias_id', None)
proj = self.browse(cr, uid, id, context=context)
if not default.get('name', False):
default['name'] = proj.name + _(' (copy)')
default.update(name=_("%s (copy)") % (proj.name))
res = super(project, self).copy(cr, uid, id, default, context)
self.map_tasks(cr,uid,id,res,context)
return res
@@ -344,7 +344,7 @@ class project(osv.osv):
new_date_end = (datetime(*time.strptime(new_date_start,'%Y-%m-%d')[:3])+(end_date-start_date)).strftime('%Y-%m-%d')
context.update({'copy':True})
new_id = self.copy(cr, uid, proj.id, default = {
'name': proj.name +_(' (copy)'),
'name':_("%s (copy)") % (proj.name),
'state':'open',
'date_start':new_date_start,
'date':new_date_end,
@@ -694,7 +694,7 @@ class task(base_stage, osv.osv):
if not default.get('name', False):
default['name'] = self.browse(cr, uid, id, context=context).name or ''
if not context.get('copy',False):
new_name = _("%s (copy)")%default.get('name','')
new_name = _("%s (copy)") % (default.get('name', ''))
default.update({'name':new_name})
return super(task, self).copy_data(cr, uid, id, default, context)
+3 -3
View File
@@ -355,7 +355,7 @@ class project_issue(base_stage, osv.osv):
if not default:
default = {}
default = default.copy()
default['name'] = issue['name'] + _(' (copy)')
default.update(name=_('%s (copy)') % (issue['name']))
return super(project_issue, self).copy(cr, uid, id, default=default,
context=context)
@@ -534,7 +534,7 @@ class project(osv.osv):
def _get_alias_models(self, cr, uid, context=None):
return [('project.task', "Tasks"), ("project.issue", "Issues")]
def _issue_count(self, cr, uid, ids, field_name, arg, context=None):
res = dict.fromkeys(ids, 0)
issue_ids = self.pool.get('project.issue').search(cr, uid, [('project_id', 'in', ids)])
@@ -557,7 +557,7 @@ class project(osv.osv):
_constraints = [
(_check_escalation, 'Error! You cannot assign escalation to the same project!', ['project_escalation_id'])
]
project()
class account_analytic_account(osv.osv):
@@ -138,7 +138,7 @@ class project_phase(osv.osv):
if default is None:
default = {}
if not default.get('name', False):
default['name'] = self.browse(cr, uid, id, context=context).name + _(' (copy)')
default.update(name=_('%s (copy)') % (self.browse(cr, uid, id, context=context).name))
return super(project_phase, self).copy(cr, uid, id, default, context)
def set_draft(self, cr, uid, ids, *args):
@@ -227,7 +227,7 @@ class project(osv.osv):
'phase_ids': fields.one2many('project.phase', 'project_id', "Project Phases"),
'phase_count': fields.function(_phase_count, type='integer', string="Open Phases"),
}
def schedule_phases(self, cr, uid, ids, context=None):
context = context or {}
if type(ids) in (long, int,):
@@ -250,7 +250,7 @@ class project(osv.osv):
# Maybe it's better to update than unlink/create if it already exists ?
p = getattr(project_gantt, 'Phase_%d' % (phase.id,))
self.pool.get('project.user.allocation').unlink(cr, uid,
self.pool.get('project.user.allocation').unlink(cr, uid,
[x.id for x in phase.user_ids],
context=context
)
+24 -24
View File
@@ -45,24 +45,24 @@ class resource_calendar(osv.osv):
def working_hours_on_day(self, cr, uid, resource_calendar_id, day, context=None):
"""Calculates the Working Total Hours based on Resource Calendar and
given working day (datetime object).
@param resource_calendar_id: resource.calendar browse record
@param day: datetime object
@return: returns the working hours (as float) men should work on the given day if is in the attendance_ids of the resource_calendar_id (i.e if that day is a working day), returns 0.0 otherwise
"""
res = 0.0
for working_day in resource_calendar_id.attendance_ids:
if (int(working_day.dayofweek) + 1) == day.isoweekday():
res += working_day.hour_to - working_day.hour_from
return res
return res
def _get_leaves(self, cr, uid, id, resource):
"""Private Method to Calculate resource Leaves days
"""Private Method to Calculate resource Leaves days
@param id: resource calendar id
@param resource: resource id for which leaves will ew calculated
@param resource: resource id for which leaves will ew calculated
@return : returns the list of dates, where resource on leave in
resource.calendar.leaves object (e.g.['%Y-%m-%d', '%Y-%m-%d'])
"""
@@ -85,9 +85,9 @@ class resource_calendar(osv.osv):
"""
Calculates the working Schedule from supplied from date to till hours
will be satisfied based or resource calendar id. If resource is also
given then it will consider the resource leave also and than will
given then it will consider the resource leave also and than will
calculates resource working schedule
@param dt_from: datetime object, start of working scheduled
@param hours: float, total number working hours needed scheduled from
start date
@@ -187,29 +187,29 @@ class resource_calendar(osv.osv):
def interval_get(self, cr, uid, id, dt_from, hours, resource=False, byday=True):
"""Calculates Resource Working Internal Timing Based on Resource Calendar.
@param dt_from: start resource schedule calculation.
@param hours : total number of working hours to be scheduled.
@param resource: optional resource id, If supplied it will take care of
@param resource: optional resource id, If supplied it will take care of
resource leave while scheduling.
@param byday: boolean flag bit enforce day wise scheduling
@return : list of scheduled working timing based on resource calendar.
"""
res = self.interval_get_multi(cr, uid, [(dt_from.strftime('%Y-%m-%d %H:%M:%S'), hours, id)], resource, byday)[(dt_from.strftime('%Y-%m-%d %H:%M:%S'), hours, id)]
return res
def interval_hours_get(self, cr, uid, id, dt_from, dt_to, resource=False):
""" Calculates the Total Working hours based on given start_date to
end_date, If resource id is supplied that it will consider the source
""" Calculates the Total Working hours based on given start_date to
end_date, If resource id is supplied that it will consider the source
leaves also in calculating the hours.
@param dt_from : date start to calculate hours
@param dt_end : date end to calculate hours
@param resource: optional resource id, If given resource leave will be
considered.
@return : Total number of working hours based dt_from and dt_end and
considered.
@return : Total number of working hours based dt_from and dt_end and
resource if supplied.
"""
if not id:
@@ -257,7 +257,7 @@ resource_calendar()
class resource_calendar_attendance(osv.osv):
_name = "resource.calendar.attendance"
_description = "Work Detail"
_columns = {
'name' : fields.char("Name", size=64, required=True),
'dayofweek': fields.selection([('0','Monday'),('1','Tuesday'),('2','Wednesday'),('3','Thursday'),('4','Friday'),('5','Saturday'),('6','Sunday')], 'Day of Week', required=True, select=True),
@@ -266,9 +266,9 @@ class resource_calendar_attendance(osv.osv):
'hour_to' : fields.float("Work to", required=True),
'calendar_id' : fields.many2one("resource.calendar", "Resource's Calendar", required=True),
}
_order = 'dayofweek, hour_from'
_defaults = {
'dayofweek' : '0'
}
@@ -302,12 +302,12 @@ class resource_resource(osv.osv):
'company_id': lambda self, cr, uid, context: self.pool.get('res.company')._company_default_get(cr, uid, 'resource.resource', context=context)
}
def copy(self, cr, uid, id, default=None, context=None):
if default is None:
default = {}
if not default.get('name', False):
default['name'] = self.browse(cr, uid, id, context=context).name + _(' (copy)')
default.update(name=_('%s (copy)') % (self.browse(cr, uid, id, context=context).name))
return super(resource_resource, self).copy(cr, uid, id, default, context)
def generate_resources(self, cr, uid, user_ids, calendar_id, context=None):
@@ -368,7 +368,7 @@ class resource_resource(osv.osv):
"""
if not calendar_id:
# Calendar is not specified: working days: 24/7
return [('fri', '8:0-12:0','13:0-17:0'), ('thu', '8:0-12:0','13:0-17:0'), ('wed', '8:0-12:0','13:0-17:0'),
return [('fri', '8:0-12:0','13:0-17:0'), ('thu', '8:0-12:0','13:0-17:0'), ('wed', '8:0-12:0','13:0-17:0'),
('mon', '8:0-12:0','13:0-17:0'), ('tue', '8:0-12:0','13:0-17:0')]
resource_attendance_pool = self.pool.get('resource.calendar.attendance')
time_range = "8:00-8:00"
+2397 -1950
View File
File diff suppressed because it is too large Load Diff
+2031 -1813
View File
File diff suppressed because it is too large Load Diff
+1848 -1763
View File
File diff suppressed because it is too large Load Diff
+2413 -1991
View File
File diff suppressed because it is too large Load Diff
+2160 -1828
View File
File diff suppressed because it is too large Load Diff
+1820 -1736
View File
File diff suppressed because it is too large Load Diff
+2788 -2058
View File
File diff suppressed because it is too large Load Diff
+2007 -1765
View File
File diff suppressed because it is too large Load Diff
+2530 -2008
View File
File diff suppressed because it is too large Load Diff
+1860 -1760
View File
File diff suppressed because it is too large Load Diff
+2448 -1999
View File
File diff suppressed because it is too large Load Diff
+2779 -2120
View File
File diff suppressed because it is too large Load Diff
+2181 -1897
View File
File diff suppressed because it is too large Load Diff
+1869 -1762
View File
File diff suppressed because it is too large Load Diff
+2369 -1858
View File
File diff suppressed because it is too large Load Diff
+2734 -2110
View File
File diff suppressed because it is too large Load Diff
+1770 -1789
View File
File diff suppressed because it is too large Load Diff
+2462 -1975
View File
File diff suppressed because it is too large Load Diff
+2414 -1992
View File
File diff suppressed because it is too large Load Diff
+2409 -1978
View File
File diff suppressed because it is too large Load Diff
+1929 -1876
View File
File diff suppressed because it is too large Load Diff
+2420 -1995
View File
File diff suppressed because it is too large Load Diff
+2565 -1903
View File
File diff suppressed because it is too large Load Diff
+1849 -1760
View File
File diff suppressed because it is too large Load Diff
+1699 -1721
View File
File diff suppressed because it is too large Load Diff
+2053 -1896
View File
File diff suppressed because it is too large Load Diff
+1839 -1759
View File
File diff suppressed because it is too large Load Diff
+2755 -2096
View File
File diff suppressed because it is too large Load Diff
+2599 -2014
View File
File diff suppressed because it is too large Load Diff
+2775 -2116
View File
File diff suppressed because it is too large Load Diff
+2763 -2095
View File
File diff suppressed because it is too large Load Diff
+1704 -1723
View File
File diff suppressed because it is too large Load Diff
+2737 -2091
View File
File diff suppressed because it is too large Load Diff
+2762 -2103
View File
File diff suppressed because it is too large Load Diff
+2666 -2006
View File
File diff suppressed because it is too large Load Diff
+2780 -2123
View File
File diff suppressed because it is too large Load Diff
+2537 -2003
View File
File diff suppressed because it is too large Load Diff
+2028 -1795
View File
File diff suppressed because it is too large Load Diff
+2157 -1840
View File
File diff suppressed because it is too large Load Diff
+1699 -1721
View File
File diff suppressed because it is too large Load Diff
+2097 -1850
View File
File diff suppressed because it is too large Load Diff
+2096 -1849
View File
File diff suppressed because it is too large Load Diff
+2750 -2091
View File
File diff suppressed because it is too large Load Diff
+1826 -1723
View File
File diff suppressed because it is too large Load Diff
+1699 -1721
View File
File diff suppressed because it is too large Load Diff
+2783 -2121
View File
File diff suppressed because it is too large Load Diff
+1798 -1751
View File
File diff suppressed because it is too large Load Diff
+1969 -1768
View File
File diff suppressed because it is too large Load Diff
+2502 -1923
View File
File diff suppressed because it is too large Load Diff
+1834 -1759
View File
File diff suppressed because it is too large Load Diff
+574 -2400
View File
File diff suppressed because it is too large Load Diff
+550 -2479
View File
File diff suppressed because it is too large Load Diff
+540 -2370
View File
File diff suppressed because it is too large Load Diff
+581 -2843
View File
File diff suppressed because it is too large Load Diff
+562 -2209
View File
File diff suppressed because it is too large Load Diff
+543 -2032
View File
File diff suppressed because it is too large Load Diff
+594 -2902
View File
File diff suppressed because it is too large Load Diff
+559 -2543
View File
File diff suppressed because it is too large Load Diff
+588 -2857
View File
File diff suppressed because it is too large Load Diff
+544 -2412
View File
File diff suppressed because it is too large Load Diff
+568 -2689
View File
File diff suppressed because it is too large Load Diff
+577 -2944
View File
File diff suppressed because it is too large Load Diff
+526 -2009
View File
File diff suppressed because it is too large Load Diff
+577 -2725
View File
File diff suppressed because it is too large Load Diff
+563 -2776
View File
File diff suppressed because it is too large Load Diff
+583 -2515
View File
File diff suppressed because it is too large Load Diff
+530 -2002
View File
File diff suppressed because it is too large Load Diff
+585 -2784
View File
File diff suppressed because it is too large Load Diff
+571 -2144
View File
File diff suppressed because it is too large Load Diff
+538 -2365
View File
File diff suppressed because it is too large Load Diff
+526 -1982
View File
File diff suppressed because it is too large Load Diff
+541 -2475
View File
File diff suppressed because it is too large Load Diff
+537 -2241
View File
File diff suppressed because it is too large Load Diff
+588 -2635
View File
File diff suppressed because it is too large Load Diff

Some files were not shown because too many files have changed in this diff Show More