From f1e3ea91d6a7ee6bd1c1079500164d5f99ed6fbe Mon Sep 17 00:00:00 2001 From: "Pedro M. Baeza" Date: Sun, 25 Oct 2015 11:24:01 +0100 Subject: [PATCH 01/20] OCA Transbot updated translations from Transifex --- account_check_deposit/i18n/ca.po | 12 ++++++------ account_check_deposit/i18n/es.po | 8 ++++---- account_check_deposit/i18n/hr.po | 4 ++-- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/account_check_deposit/i18n/ca.po b/account_check_deposit/i18n/ca.po index cf28381d2..792d34b7e 100644 --- a/account_check_deposit/i18n/ca.po +++ b/account_check_deposit/i18n/ca.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: account-financial-tools (8.0)\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2015-07-01 13:26+0000\n" +"POT-Creation-Date: 2015-10-20 18:44+0000\n" "PO-Revision-Date: 2015-06-03 15:58+0000\n" "Last-Translator: <>\n" "Language-Team: Catalan (http://www.transifex.com/oca/OCA-account-financial-tools-8-0/language/ca/)\n" @@ -136,12 +136,12 @@ msgstr "" #. module: account_check_deposit #: field:account.check.deposit,create_uid:0 msgid "Created by" -msgstr "" +msgstr "Creat per" #. module: account_check_deposit #: field:account.check.deposit,create_date:0 msgid "Created on" -msgstr "" +msgstr "Creat el" #. module: account_check_deposit #: view:account.check.deposit:account_check_deposit.view_check_deposit_search @@ -208,7 +208,7 @@ msgstr "" #. module: account_check_deposit #: field:account.check.deposit,id:0 msgid "ID" -msgstr "" +msgstr "ID" #. module: account_check_deposit #: view:account.check.deposit:account_check_deposit.view_check_deposit_search @@ -229,12 +229,12 @@ msgstr "" #. module: account_check_deposit #: field:account.check.deposit,write_uid:0 msgid "Last Updated by" -msgstr "" +msgstr "Darrera Actualització per" #. module: account_check_deposit #: field:account.check.deposit,write_date:0 msgid "Last Updated on" -msgstr "" +msgstr "Darrera Actualització el" #. module: account_check_deposit #: field:account.check.deposit,line_ids:0 diff --git a/account_check_deposit/i18n/es.po b/account_check_deposit/i18n/es.po index 0470a9cbb..a680d38aa 100644 --- a/account_check_deposit/i18n/es.po +++ b/account_check_deposit/i18n/es.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: account-financial-tools (8.0)\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2015-07-01 13:26+0000\n" +"POT-Creation-Date: 2015-10-20 18:44+0000\n" "PO-Revision-Date: 2015-06-03 15:58+0000\n" "Last-Translator: <>\n" "Language-Team: Spanish (http://www.transifex.com/oca/OCA-account-financial-tools-8-0/language/es/)\n" @@ -35,7 +35,7 @@ msgstr "" #. module: account_check_deposit #: view:website:account_check_deposit.report_checkdeposit msgid "Amount" -msgstr "" +msgstr "Importe" #. module: account_check_deposit #: view:account.check.deposit:account_check_deposit.account_check_deposit_view_form @@ -179,7 +179,7 @@ msgstr "" #: view:account.check.deposit:account_check_deposit.view_check_deposit_search #: selection:account.check.deposit,state:0 msgid "Done" -msgstr "" +msgstr "Completado" #. module: account_check_deposit #: view:account.check.deposit:account_check_deposit.view_check_deposit_search @@ -219,7 +219,7 @@ msgstr "Diario" #. module: account_check_deposit #: field:account.check.deposit,move_id:0 msgid "Journal Entry" -msgstr "" +msgstr "Asiento contable" #. module: account_check_deposit #: model:ir.model,name:account_check_deposit.model_account_move_line diff --git a/account_check_deposit/i18n/hr.po b/account_check_deposit/i18n/hr.po index 23e8b889c..0daf86f12 100644 --- a/account_check_deposit/i18n/hr.po +++ b/account_check_deposit/i18n/hr.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: account-financial-tools (8.0)\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2015-07-01 13:26+0000\n" +"POT-Creation-Date: 2015-10-20 18:44+0000\n" "PO-Revision-Date: 2015-06-03 15:58+0000\n" "Last-Translator: <>\n" "Language-Team: Croatian (http://www.transifex.com/oca/OCA-account-financial-tools-8-0/language/hr/)\n" @@ -208,7 +208,7 @@ msgstr "" #. module: account_check_deposit #: field:account.check.deposit,id:0 msgid "ID" -msgstr "" +msgstr "ID" #. module: account_check_deposit #: view:account.check.deposit:account_check_deposit.view_check_deposit_search From 9f7b49530ea6f7e4e4d910af28f50a61fc830c55 Mon Sep 17 00:00:00 2001 From: Alexis de Lattre Date: Fri, 30 Oct 2015 14:20:19 +0100 Subject: [PATCH 02/20] account_check_deposit : Port to new API Move description from __openerp__.py to README.rst --- account_check_deposit/README.rst | 69 ++++ account_check_deposit/__init__.py | 19 - account_check_deposit/__openerp__.py | 14 +- account_check_deposit/account_data.xml | 10 - account_check_deposit/account_deposit.py | 333 +++++++----------- .../account_deposit_sequence.xml | 2 +- .../account_deposit_view.xml | 7 +- 7 files changed, 210 insertions(+), 244 deletions(-) create mode 100644 account_check_deposit/README.rst diff --git a/account_check_deposit/README.rst b/account_check_deposit/README.rst new file mode 100644 index 000000000..12fb31dca --- /dev/null +++ b/account_check_deposit/README.rst @@ -0,0 +1,69 @@ +.. image:: https://img.shields.io/badge/licence-AGPL--3-blue.svg + :target: http://www.gnu.org/licenses/agpl-3.0-standalone.html + :alt: License: AGPL-3 + +============= +Check Deposit +============= + +This module allows you to easily manage check deposits : you can select all +the checks you received and create a global deposit for the +selected checks. This module supports multi-currency ; each deposit has a currency +and all the checks of the deposit must have the same currency +(so, if you have checks in EUR and checks in USD, you must create 2 deposits : +one in EUR and one in USD). + +Configuration +============= + +A journal named *Check Received* is automatically created. It will be available as a payment method in Odoo. On this journal, you must configure the *Default Debit Account* and *Defaut Credit Account* ; this is the account via which the amounts of checks will transit between the reception of a check from a customer and the validation of the check deposit in Odoo. + +On the company form view, you should configure the *Account for Check Deposits* ; this is the account via which the amounts of checks will transit between the validation of the check deposit in Odoo and the credit on the bank account. + +Usage +===== + +When you receive a check that pays a customer invoice, you can go to that invoice and click on the button *Register Payment* and select the *Check Received* journal as *Payment Method*. + +When you want to deposit checks to the bank, go to the menu *Accounting > Bank and Cash > Check Deposit*, create a new check deposit and set the journal *Checks Received* and select the bank account on which you want to credit the checks. Then click on *Add an item* to select the checks you want to deposit at the bank. Eventually, validate the deposit and print the report (you probably want to customize this report). + +.. image:: https://odoo-community.org/website/image/ir.attachment/5784_f2813bd/datas + :alt: Try me on Runbot + :target: https://runbot.odoo-community.org/runbot/92/8.0 + +For further information, please visit: + + * https://www.odoo.com/forum/help-1 + +Bug Tracker +=========== + +Bugs are tracked on `GitHub Issues `_. +In case of trouble, please check there if your issue has already been reported. +If you spotted it first, help us smashing it by providing a detailed and welcomed feedback +`here `_. + +Credits +======= + +Contributors +------------ + +* Benoît GUILLOT +* Chafique DELLI +* Alexis de Lattre + +Maintainer +---------- + +.. image:: http://odoo-community.org/logo.png + :alt: Odoo Community Association + :target: http://odoo-community.org + +This module is maintained by the OCA. + +OCA, or the Odoo Community Association, is a nonprofit organization whose +mission is to support the collaborative development of Odoo features and +promote its widespread use. + +To contribute to this module, please visit http://odoo-community.org. diff --git a/account_check_deposit/__init__.py b/account_check_deposit/__init__.py index f1c1297b1..a98c879ff 100644 --- a/account_check_deposit/__init__.py +++ b/account_check_deposit/__init__.py @@ -1,22 +1,3 @@ # -*- coding: utf-8 -*- -############################################################################### -# -# account_check_deposit for Odoo/OpenERP -# Copyright (C) 2012-2015 Akretion (http://www.akretion.com/) -# -# 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 . -# -############################################################################### from . import account_deposit diff --git a/account_check_deposit/__openerp__.py b/account_check_deposit/__openerp__.py index 1536a39ed..f387103ec 100644 --- a/account_check_deposit/__openerp__.py +++ b/account_check_deposit/__openerp__.py @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- ############################################################################### # -# account_check_deposit for Odoo/OpenERP +# account_check_deposit for Odoo # Copyright (C) 2012-2015 Akretion (http://www.akretion.com/) # @author: Benoît GUILLOT # @author: Chafique DELLI @@ -28,18 +28,6 @@ 'category': 'Accounting & Finance', 'license': 'AGPL-3', 'summary': 'Manage deposit of checks to the bank', - 'description': """ -Account Check Deposit -===================== -This module allows you to easily manage check deposits : you can select all -the checks you received as payments and create a global deposit for the -selected checks. - -A journal for received checks is automatically created. -You must configure on this journal the default debit account and the default -credit account. You must also configure on the company the account for -check deposits. -""", 'author': "Akretion,Odoo Community Association (OCA)", 'website': 'http://www.akretion.com/', 'depends': [ diff --git a/account_check_deposit/account_data.xml b/account_check_deposit/account_data.xml index 141123f54..a2c525ec6 100644 --- a/account_check_deposit/account_data.xml +++ b/account_check_deposit/account_data.xml @@ -1,6 +1,5 @@ Check Received CHK bank - diff --git a/account_check_deposit/account_deposit.py b/account_check_deposit/account_deposit.py index cdc0fbd2c..8f40887b0 100644 --- a/account_check_deposit/account_deposit.py +++ b/account_check_deposit/account_deposit.py @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- ############################################################################### # -# account_check_deposit for Odoo/OpenERP +# account_check_deposit for Odoo # Copyright (C) 2012-2015 Akretion (http://www.akretion.com/) # @author: Benoît GUILLOT # @author: Chafique DELLI @@ -22,19 +22,24 @@ # ############################################################################### -from openerp.osv import fields, orm -from openerp.tools.translate import _ +from openerp import models, fields, api, _ import openerp.addons.decimal_precision as dp +from openerp.exceptions import ValidationError +from openerp.exceptions import Warning as UserError -class account_check_deposit(orm.Model): +class AccountCheckDeposit(models.Model): _name = "account.check.deposit" _description = "Account Check Deposit" _order = 'deposit_date desc' - def _compute_check_deposit(self, cr, uid, ids, name, args, context=None): - res = {} - for deposit in self.browse(cr, uid, ids, context=context): + @api.multi + @api.depends( + 'company_id', 'currency_id', 'check_payment_ids.debit', + 'check_payment_ids.amount_currency', + 'move_id.line_id.reconcile_id') + def _compute_check_deposit(self): + for deposit in self: total = 0.0 count = 0 reconcile = False @@ -51,82 +56,70 @@ class account_check_deposit(orm.Model): for line in deposit.move_id.line_id: if line.debit > 0 and line.reconcile_id: reconcile = True - res[deposit.id] = { - 'total_amount': total, - 'is_reconcile': reconcile, - 'currency_none_same_company_id': currency_none_same_company_id, - 'check_count': count, - } - return res + deposit.total_amount = total + deposit.is_reconcile = reconcile + deposit.currency_none_same_company_id =\ + currency_none_same_company_id + deposit.check_count = count - _columns = { - 'name': fields.char( - 'Name', size=64, readonly=True), - 'check_payment_ids': fields.one2many( - 'account.move.line', 'check_deposit_id', 'Check Payments', - states={'done': [('readonly', '=', True)]}), - 'deposit_date': fields.date( - 'Deposit Date', required=True, - states={'done': [('readonly', '=', True)]}), - 'journal_id': fields.many2one( - 'account.journal', 'Journal', domain=[('type', '=', 'bank')], - required=True, states={'done': [('readonly', '=', True)]}), - 'journal_default_account_id': fields.related( - 'journal_id', 'default_debit_account_id', type='many2one', - relation='account.account', - string='Default Debit Account of the Journal'), - 'currency_id': fields.many2one( - 'res.currency', 'Currency', required=True, - states={'done': [('readonly', '=', True)]}), - 'currency_none_same_company_id': fields.function( - _compute_check_deposit, type='many2one', - relation='res.currency', multi='deposit', - string='Currency (False if same as company)'), - 'state': fields.selection([ - ('draft', 'Draft'), - ('done', 'Done'), - ], 'Status', readonly=True), - 'move_id': fields.many2one( - 'account.move', 'Journal Entry', readonly=True), - 'partner_bank_id': fields.many2one( - 'res.partner.bank', 'Bank Account', required=True, - domain="[('company_id', '=', company_id)]", - states={'done': [('readonly', '=', True)]}), - 'line_ids': fields.related( - 'move_id', 'line_id', relation='account.move.line', - type='one2many', string='Lines', readonly=True), - 'company_id': fields.many2one( - 'res.company', 'Company', required=True, - change_default=True, - states={'done': [('readonly', '=', True)]}), - 'total_amount': fields.function( - _compute_check_deposit, multi='deposit', - string="Total Amount", readonly=True, - type="float", digits_compute=dp.get_precision('Account')), - 'check_count': fields.function( - _compute_check_deposit, multi='deposit', readonly=True, - string="Number of Checks", type="integer"), - 'is_reconcile': fields.function( - _compute_check_deposit, multi='deposit', readonly=True, - string="Reconcile", type="boolean"), - } + name = fields.Char(string='Name', size=64, readonly=True, default='/') + check_payment_ids = fields.One2many( + 'account.move.line', 'check_deposit_id', string='Check Payments', + states={'done': [('readonly', '=', True)]}) + deposit_date = fields.Date( + string='Deposit Date', required=True, + states={'done': [('readonly', '=', True)]}, + default=fields.Date.context_today) + journal_id = fields.Many2one( + 'account.journal', string='Journal', domain=[('type', '=', 'bank')], + required=True, states={'done': [('readonly', '=', True)]}) + journal_default_account_id = fields.Many2one( + 'account.account', related='journal_id.default_debit_account_id', + string='Default Debit Account of the Journal') + currency_id = fields.Many2one( + 'res.currency', string='Currency', required=True, + states={'done': [('readonly', '=', True)]}) + currency_none_same_company_id = fields.Many2one( + 'res.currency', compute='_compute_check_deposit', + string='Currency (False if same as company)') + state = fields.Selection([ + ('draft', 'Draft'), + ('done', 'Done'), + ], string='Status', default='draft', readonly=True) + move_id = fields.Many2one( + 'account.move', string='Journal Entry', readonly=True) + partner_bank_id = fields.Many2one( + 'res.partner.bank', string='Bank Account', required=True, + domain="[('company_id', '=', company_id)]", + states={'done': [('readonly', '=', True)]}) + line_ids = fields.One2many( + 'account.move.line', related='move_id.line_id', + string='Lines', readonly=True) + company_id = fields.Many2one( + 'res.company', string='Company', required=True, + states={'done': [('readonly', '=', True)]}, + default=lambda self: self.env['res.company']._company_default_get( + 'account.check.deposit')) + total_amount = fields.Float( + compute='_compute_check_deposit', + string="Total Amount", readonly=True, + digits=dp.get_precision('Account')) + check_count = fields.Integer( + compute='_compute_check_deposit', readonly=True, + string="Number of Checks") + is_reconcile = fields.Boolean( + compute='_compute_check_deposit', readonly=True, + string="Reconcile") - _defaults = { - 'name': '/', - 'deposit_date': fields.date.context_today, - 'state': 'draft', - 'company_id': lambda self, cr, uid, c: self.pool['res.company']. - _company_default_get(cr, uid, 'account.check.deposit', context=c), - } - - def _check_deposit(self, cr, uid, ids): - for deposit in self.browse(cr, uid, ids): + @api.multi + @api.constrains('currency_id', 'check_payment_ids', 'company_id') + def _check_deposit(self): + for deposit in self: deposit_currency = deposit.currency_id if deposit_currency == deposit.company_id.currency_id: for line in deposit.check_payment_ids: if line.currency_id: - raise orm.except_orm( - _('Error:'), + raise ValidationError( _("The check with amount %s and reference '%s' " "is in currency %s but the deposit is in " "currency %s.") % ( @@ -136,35 +129,27 @@ class account_check_deposit(orm.Model): else: for line in deposit.check_payment_ids: if line.currency_id != deposit_currency: - raise orm.except_orm( - _('Error:'), + raise ValidationError( _("The check with amount %s and reference '%s' " "is in currency %s but the deposit is in " "currency %s.") % ( line.debit, line.ref or '', line.currency_id.name, deposit_currency.name)) - return True - _constraints = [( - _check_deposit, - "All the checks of the deposit must be in the currency of the deposit", - ['currency_id', 'check_payment_ids', 'company_id'] - )] - - def unlink(self, cr, uid, ids, context=None): - for deposit in self.browse(cr, uid, ids, context=context): + @api.multi + def unlink(self): + for deposit in self: if deposit.state == 'done': - raise orm.except_orm( - _('Error!'), + raise UserError( _("The deposit '%s' is in valid state, so you must " "cancel it before deleting it.") % deposit.name) - return super(account_check_deposit, self).unlink( - cr, uid, ids, context=context) + return super(AccountCheckDeposit, self).unlink() - def backtodraft(self, cr, uid, ids, context=None): - for deposit in self.browse(cr, uid, ids, context=context): + @api.multi + def backtodraft(self): + for deposit in self: if deposit.move_id: # It will raise here if journal_id.update_posted = False deposit.move_id.button_cancel() @@ -175,29 +160,30 @@ class account_check_deposit(orm.Model): deposit.write({'state': 'draft'}) return True - def create(self, cr, uid, vals, context=None): + @api.model + def create(self, vals): if vals.get('name', '/') == '/': - vals['name'] = self.pool['ir.sequence'].\ - next_by_code(cr, uid, 'account.check.deposit') - return super(account_check_deposit, self).\ - create(cr, uid, vals, context=context) + vals['name'] = self.env['ir.sequence'].\ + next_by_code('account.check.deposit') + return super(AccountCheckDeposit, self).create(vals) - def _prepare_account_move_vals(self, cr, uid, deposit, context=None): + @api.model + def _prepare_account_move_vals(self, deposit): date = deposit.deposit_date - period_obj = self.pool['account.period'] - period_ids = period_obj.find(cr, uid, dt=date, context=context) + period_obj = self.env['account.period'] + period_ids = period_obj.find(dt=date) # period_ids will always have a value, cf the code of find() move_vals = { 'journal_id': deposit.journal_id.id, 'date': date, - 'period_id': period_ids[0], + 'period_id': period_ids[0].id, 'name': _('Check Deposit %s') % deposit.name, 'ref': deposit.name, } return move_vals - def _prepare_move_line_vals( - self, cr, uid, line, context=None): + @api.model + def _prepare_move_line_vals(self, line): assert (line.debit > 0), 'Debit must have a value' return { 'name': _('Check Deposit - Ref. Check %s') % line.ref, @@ -209,9 +195,9 @@ class account_check_deposit(orm.Model): 'amount_currency': line.amount_currency * -1, } + @api.model def _prepare_counterpart_move_lines_vals( - self, cr, uid, deposit, total_debit, total_amount_currency, - context=None): + self, deposit, total_debit, total_amount_currency): return { 'name': _('Check Deposit %s') % deposit.name, 'debit': total_debit, @@ -222,119 +208,74 @@ class account_check_deposit(orm.Model): 'amount_currency': total_amount_currency, } - def validate_deposit(self, cr, uid, ids, context=None): - am_obj = self.pool['account.move'] - aml_obj = self.pool['account.move.line'] - if context is None: - context = {} - for deposit in self.browse(cr, uid, ids, context=context): - move_vals = self._prepare_account_move_vals( - cr, uid, deposit, context=context) - context['journal_id'] = move_vals['journal_id'] - context['period_id'] = move_vals['period_id'] - move_id = am_obj.create(cr, uid, move_vals, context=context) + @api.multi + def validate_deposit(self): + am_obj = self.env['account.move'] + aml_obj = self.env['account.move.line'] + for deposit in self: + move_vals = self._prepare_account_move_vals(deposit) + move = am_obj.create(move_vals) total_debit = 0.0 total_amount_currency = 0.0 - to_reconcile_line_ids = [] + to_reconcile_lines = [] for line in deposit.check_payment_ids: total_debit += line.debit total_amount_currency += line.amount_currency - line_vals = self._prepare_move_line_vals( - cr, uid, line, context=context) - line_vals['move_id'] = move_id - move_line_id = aml_obj.create( - cr, uid, line_vals, context=context) - to_reconcile_line_ids.append([line.id, move_line_id]) + line_vals = self._prepare_move_line_vals(line) + line_vals['move_id'] = move.id + move_line = aml_obj.create(line_vals) + to_reconcile_lines.append(line + move_line) # Create counter-part if not deposit.company_id.check_deposit_account_id: - raise orm.except_orm( - _('Configuration Error:'), + raise UserError( _("Missing Account for Check Deposits on the " "company '%s'.") % deposit.company_id.name) counter_vals = self._prepare_counterpart_move_lines_vals( - cr, uid, deposit, total_debit, total_amount_currency, - context=context) - counter_vals['move_id'] = move_id - aml_obj.create(cr, uid, counter_vals, context=context) + deposit, total_debit, total_amount_currency) + counter_vals['move_id'] = move.id + aml_obj.create(counter_vals) - am_obj.post(cr, uid, [move_id], context=context) - deposit.write({'state': 'done', 'move_id': move_id}) + move.post() + deposit.write({'state': 'done', 'move_id': move.id}) # We have to reconcile after post() - for reconcile_line_ids in to_reconcile_line_ids: - aml_obj.reconcile( - cr, uid, reconcile_line_ids, context=context) + for reconcile_lines in to_reconcile_lines: + reconcile_lines.reconcile() return True - def onchange_company_id( - self, cr, uid, ids, company_id, currency_id, context=None): - vals = {} - if company_id: - company = self.pool['res.company'].browse( - cr, uid, company_id, context=context) - if currency_id: - if company.currency_id.id == currency_id: - vals['currency_none_same_company_id'] = False - else: - vals['currency_none_same_company_id'] = currency_id - partner_bank_ids = self.pool['res.partner.bank'].search( - cr, uid, [('company_id', '=', company_id)], context=context) - if len(partner_bank_ids) == 1: - vals['partner_bank_id'] = partner_bank_ids[0] + @api.onchange('company_id') + def onchange_company_id(self): + if self.company_id: + partner_banks = self.env['res.partner.bank'].search( + [('company_id', '=', self.company_id.id)]) + if len(partner_banks) == 1: + self.partner_bank_id = partner_banks[0] else: - vals['currency_none_same_company_id'] = False - vals['partner_bank_id'] = False - return {'value': vals} + self.partner_bank_id = False - def onchange_journal_id(self, cr, uid, ids, journal_id, context=None): - vals = {} - if journal_id: - journal = self.pool['account.journal'].browse( - cr, uid, journal_id, context=context) - vals['journal_default_account_id'] = \ - journal.default_debit_account_id.id - if journal.currency: - vals['currency_id'] = journal.currency.id + @api.onchange('journal_id') + def onchange_journal_id(self): + if self.journal_id: + if self.journal_id.currency: + self.currency_id = self.journal_id.currency else: - vals['currency_id'] = journal.company_id.currency_id.id - else: - vals['journal_default_account_id'] = False - return {'value': vals} - - def onchange_currency_id( - self, cr, uid, ids, currency_id, company_id, context=None): - vals = {} - if currency_id and company_id: - company = self.pool['res.company'].browse( - cr, uid, company_id, context=context) - if company.currency_id.id == currency_id: - vals['currency_none_same_company_id'] = False - else: - vals['currency_none_same_company_id'] = currency_id - else: - vals['currency_none_same_company_id'] = False - return {'value': vals} + self.currency_id = self.journal_id.company_id.currency_id -class account_move_line(orm.Model): +class AccountMoveLine(models.Model): _inherit = "account.move.line" - _columns = { - 'check_deposit_id': fields.many2one( - 'account.check.deposit', - 'Check Deposit'), - } + check_deposit_id = fields.Many2one( + 'account.check.deposit', string='Check Deposit', copy=False) -class res_company(orm.Model): +class ResCompany(models.Model): _inherit = 'res.company' - _columns = { - 'check_deposit_account_id': fields.many2one( - 'account.account', 'Account for Check Deposits', - domain=[ - ('type', '<>', 'view'), - ('type', '<>', 'closed'), - ('reconcile', '=', True)]), - } + check_deposit_account_id = fields.Many2one( + 'account.account', string='Account for Check Deposits', copy=False, + domain=[ + ('type', '<>', 'view'), + ('type', '<>', 'closed'), + ('reconcile', '=', True)]) diff --git a/account_check_deposit/account_deposit_sequence.xml b/account_check_deposit/account_deposit_sequence.xml index 47a53f88e..07c4c13bd 100644 --- a/account_check_deposit/account_deposit_sequence.xml +++ b/account_check_deposit/account_deposit_sequence.xml @@ -1,6 +1,6 @@ - - Account Check Deposit - account.check.deposit - - Account Check Deposit account.check.deposit diff --git a/account_check_deposit/models/account_deposit.py b/account_check_deposit/models/account_deposit.py index 980a61b0c..076775c4d 100644 --- a/account_check_deposit/models/account_deposit.py +++ b/account_check_deposit/models/account_deposit.py @@ -2,23 +2,13 @@ ############################################################################### # # account_check_deposit for Odoo -# Copyright (C) 2012-2015 Akretion (http://www.akretion.com/) +# Copyright (C) 2012-2016 Akretion (http://www.akretion.com/) # @author: Benoît GUILLOT # @author: Chafique DELLI # @author: Alexis de Lattre +# @author: Mourad EL HADJ MIMOUNE # -# 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 . +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). # ############################################################################### @@ -37,7 +27,7 @@ class AccountCheckDeposit(models.Model): @api.depends( 'company_id', 'currency_id', 'check_payment_ids.debit', 'check_payment_ids.amount_currency', - 'move_id.line_id.reconcile_id') + 'move_id.line_ids.reconciled') def _compute_check_deposit(self): for deposit in self: total = 0.0 @@ -53,8 +43,8 @@ class AccountCheckDeposit(models.Model): else: total += line.debit if deposit.move_id: - for line in deposit.move_id.line_id: - if line.debit > 0 and line.reconcile_id: + for line in deposit.move_id.line_ids: + if line.debit > 0 and line.reconciled: reconcile = True deposit.total_amount = total deposit.is_reconcile = reconcile @@ -82,9 +72,10 @@ class AccountCheckDeposit(models.Model): currency_none_same_company_id = fields.Many2one( 'res.currency', compute='_compute_check_deposit', string='Currency (False if same as company)') - state = fields.Selection([ - ('draft', 'Draft'), - ('done', 'Done'), + state = fields.Selection( + [ + ('draft', 'Draft'), + ('done', 'Done'), ], string='Status', default='draft', readonly=True) move_id = fields.Many2one( 'account.move', string='Journal Entry', readonly=True) @@ -93,7 +84,7 @@ class AccountCheckDeposit(models.Model): domain="[('company_id', '=', company_id)]", states={'done': [('readonly', '=', True)]}) line_ids = fields.One2many( - 'account.move.line', related='move_id.line_id', + 'account.move.line', related='move_id.line_ids', string='Lines', readonly=True) company_id = fields.Many2one( 'res.company', string='Company', required=True, @@ -154,8 +145,8 @@ class AccountCheckDeposit(models.Model): # It will raise here if journal_id.update_posted = False deposit.move_id.button_cancel() for line in deposit.check_payment_ids: - if line.reconcile_id: - line.reconcile_id.unlink() + if line.reconciled: + line.remove_move_reconcile() deposit.move_id.unlink() deposit.write({'state': 'draft'}) return True @@ -170,16 +161,12 @@ class AccountCheckDeposit(models.Model): @api.model def _prepare_account_move_vals(self, deposit): date = deposit.deposit_date - period_obj = self.env['account.period'] - period_ids = period_obj.find(dt=date) - # period_ids will always have a value, cf the code of find() move_vals = { 'journal_id': deposit.journal_id.id, 'date': date, - 'period_id': period_ids[0].id, 'name': _('Check Deposit %s') % deposit.name, 'ref': deposit.name, - } + } return move_vals @api.model @@ -193,7 +180,7 @@ class AccountCheckDeposit(models.Model): 'partner_id': line.partner_id.id, 'currency_id': line.currency_id.id or False, 'amount_currency': line.amount_currency * -1, - } + } @api.model def _prepare_counterpart_move_lines_vals( @@ -206,25 +193,24 @@ class AccountCheckDeposit(models.Model): 'partner_id': False, 'currency_id': deposit.currency_none_same_company_id.id or False, 'amount_currency': total_amount_currency, - } + } @api.multi def validate_deposit(self): am_obj = self.env['account.move'] - aml_obj = self.env['account.move.line'] for deposit in self: move_vals = self._prepare_account_move_vals(deposit) - move = am_obj.create(move_vals) total_debit = 0.0 total_amount_currency = 0.0 to_reconcile_lines = [] + mv_lines_vals = [] for line in deposit.check_payment_ids: total_debit += line.debit total_amount_currency += line.amount_currency line_vals = self._prepare_move_line_vals(line) - line_vals['move_id'] = move.id - move_line = aml_obj.create(line_vals) - to_reconcile_lines.append(line + move_line) + mv_lines_vals.append((0, 0, line_vals)) + + to_reconcile_lines.append(line) # Create counter-part if not deposit.company_id.check_deposit_account_id: @@ -234,8 +220,10 @@ class AccountCheckDeposit(models.Model): counter_vals = self._prepare_counterpart_move_lines_vals( deposit, total_debit, total_amount_currency) - counter_vals['move_id'] = move.id - aml_obj.create(counter_vals) + mv_lines_vals.append((0, 0, counter_vals)) + move_vals['line_ids'] = mv_lines_vals + move = am_obj.create(move_vals) + to_reconcile_lines.extend(move.line_ids) move.post() deposit.write({'state': 'done', 'move_id': move.id}) @@ -257,8 +245,8 @@ class AccountCheckDeposit(models.Model): @api.onchange('journal_id') def onchange_journal_id(self): if self.journal_id: - if self.journal_id.currency: - self.currency_id = self.journal_id.currency + if self.journal_id.currency_id: + self.currency_id = self.journal_id.currency_id else: self.currency_id = self.journal_id.company_id.currency_id @@ -275,7 +263,4 @@ class ResCompany(models.Model): check_deposit_account_id = fields.Many2one( 'account.account', string='Account for Check Deposits', copy=False, - domain=[ - ('type', '<>', 'view'), - ('type', '<>', 'closed'), - ('reconcile', '=', True)]) + domain=[('reconcile', '=', True)]) diff --git a/account_check_deposit/tests/__init__.py b/account_check_deposit/tests/__init__.py new file mode 100644 index 000000000..841522611 --- /dev/null +++ b/account_check_deposit/tests/__init__.py @@ -0,0 +1,2 @@ + +from . import test_check_deposit diff --git a/account_check_deposit/tests/test_check_deposit.py b/account_check_deposit/tests/test_check_deposit.py new file mode 100644 index 000000000..477dd8e3e --- /dev/null +++ b/account_check_deposit/tests/test_check_deposit.py @@ -0,0 +1,189 @@ +# -*- coding: utf-8 -*- +# © 2014-2016 Akretion (http://www.akretion.com) +# @author Mourad EL HADJ MIMOUNE +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). + +from openerp.addons.account.tests.account_test_classes\ + import AccountingTestCase +import time + + +class TestPayment(AccountingTestCase): + + def setUp(self): + super(TestPayment, self).setUp() + self.register_payments_model = self.env['account.register.payments'] + self.payment_model = self.env['account.payment'] + self.journal_model = self.env['account.journal'] + self.account_account_model = self.env['account.account'] + self.invoice_model = self.env['account.invoice'] + self.invoice_line_model = self.env['account.invoice.line'] + self.acc_bank_stmt_model = self.env['account.bank.statement'] + self.acc_bank_stmt_line_model = self.env['account.bank.statement.line'] + self.res_partner_bank_model = self.env['res.partner.bank'] + self.check_deposit_model = self.env['account.check.deposit'] + + self.partner_agrolait = self.env.ref("base.res_partner_2") + self.currency_eur_id = self.env.ref("base.EUR").id + self.main_company = self.env.ref('base.main_company') + self.main_company.write({'currency_id': self.currency_eur_id}) + self.product = self.env.ref("product.product_product_4") + self.payment_method_manual_in = self.env.ref( + "account.account_payment_method_manual_in") + self.payment_method_manual_out = self.env.ref( + "account.account_payment_method_manual_out") + # check if those accounts exist otherwise create them + self.account_receivable = self.account_account_model.search( + [('code', '=', '411100')], limit=1) + + if not self.account_receivable: + self.account_receivable = self.account_account_model.create( + {"code": '411100', + "name": "Debtors - (test)", + "reconcile": True, + "user_type_id": + self.ref('account.data_account_type_receivable') + }) + + self.account_revenue = self.account_account_model.search( + [('code', '=', '707100')], limit=1) + if not self.account_revenue: + self.account_revenue = self.account_account_model.create( + {"code": '707100', + "name": "Product Sales - (test)", + "user_type_id": + self.ref('account.data_account_type_revenue') + }) + + self.recived_check_account_id = self.account_account_model.search( + [('code', '=', '511200')], limit=1) + if not self.recived_check_account_id: + self.recived_check_account_id = self.account_account_model.create( + {"code": '511200', + "name": "Recived check - (test)", + "reconcile": True, + "user_type_id": + self.ref('account.data_account_type_liquidity') + }) + self.main_company.check_deposit_account_id = \ + self.account_account_model.search( + [('code', '=', '511201')], limit=1) + if not self.main_company.check_deposit_account_id: + self.main_company.check_deposit_account_id = \ + self.account_account_model.create( + {"code": '511201', + "name": "Check deposited in bank - (test)", + "reconcile": True, + "user_type_id": + self.ref('account.data_account_type_liquidity') + }) + self.bank_account_id = self.account_account_model.search( + [('code', '=', '512001')], limit=1) + if not self.bank_account_id: + self.bank_account_id = self.account_account_model.create( + {"code": '512001', + "name": "Bank - (test)", + "reconcile": True, + "user_type_id": + self.ref('account.data_account_type_liquidity') + }) + + self.check_journal = self.journal_model.search( + [('code', '=', 'CHK')], limit=1) + if not self.check_journal: + self.check_journal = self.journal_model.create( + {'name': 'Recived check', 'type': 'bank', 'code': 'CHK'}) + self.check_journal.default_debit_account_id = \ + self.recived_check_account_id + self.check_journal.default_credit_account_id = \ + self.recived_check_account_id + self.bank_journal = self.journal_model.search( + [('code', '=', 'BNK1')], limit=1) + if not self.bank_journal: + self.bank_journal = self.journal_model.create( + {'name': 'Bank', 'type': 'bank', 'code': 'BNK1'}) + self.bank_journal.default_debit_account_id = self.bank_account_id + self.bank_journal.default_credit_account_id = self.bank_account_id + self.partner_bank_id = self.res_partner_bank_model.search( + [('partner_id', '=', self.main_company.partner_id.id)], limit=1) + if not self.partner_bank_id: + self.partner_bank_id = self.res_partner_bank_model.create( + {"acc_number": 'SI56 1910 0000 0123 438 584', + "partner_id": self.main_company.partner_id.id, + }) + + def create_invoice(self, amount=100, type='out_invoice', currency_id=None): + """ Returns an open invoice """ + invoice = self.invoice_model.create({ + 'partner_id': self.partner_agrolait.id, + 'reference_type': 'none', + 'currency_id': currency_id, + 'name': type == 'out_invoice' and + 'invoice to client' or 'invoice to supplier', + 'account_id': self.account_receivable.id, + 'type': type, + 'date_invoice': time.strftime('%Y-%m-%d'), + }) + self.invoice_line_model.create({ + 'product_id': self.product.id, + 'quantity': 1, + 'price_unit': amount, + 'invoice_id': invoice.id, + 'name': 'something', + 'account_id': self.account_revenue.id, + }) + invoice.signal_workflow('invoice_open') + return invoice + + def create_check_deposit( + self, move_lines): + """ Returns an validated check deposit """ + check_deposit = self.check_deposit_model.create({ + 'journal_id': self.bank_journal.id, + 'partner_bank_id': self.partner_bank_id.id, + 'deposit_date': time.strftime('%Y-%m-%d'), + 'currency_id': self.currency_eur_id, + }) + for move_line in move_lines: + move_line.check_deposit_id = check_deposit + check_deposit.validate_deposit() + return check_deposit + + def test_full_payment_process(self): + """ Create a payment for on invoice by check, + post it and create check deposit""" + inv_1 = self.create_invoice( + amount=100, currency_id=self.currency_eur_id) + inv_2 = self.create_invoice( + amount=200, currency_id=self.currency_eur_id) + + ctx = { + 'active_model': 'account.invoice', + 'active_ids': [ + inv_1.id, + inv_2.id]} + register_payments = self.register_payments_model.with_context( + ctx).create({ + 'payment_date': time.strftime('%Y-%m-%d'), + 'journal_id': self.check_journal.id, + 'payment_method_id': self.payment_method_manual_in.id, + }) + register_payments.create_payment() + payment = self.payment_model.search([], order="id desc", limit=1) + + self.assertAlmostEquals(payment.amount, 300) + self.assertEqual(payment.state, 'posted') + self.assertEqual(inv_1.state, 'paid') + self.assertEqual(inv_2.state, 'paid') + + check_aml = payment.move_line_ids.filtered( + lambda r: r.account_id == self.recived_check_account_id) + + check_deposit = self.create_check_deposit([check_aml]) + liquidity_aml = check_deposit.move_id.line_ids.filtered( + lambda r: r.account_id != self.recived_check_account_id) + + self.assertEqual(check_deposit.total_amount, 300) + self.assertEqual(liquidity_aml.debit, 300) + self.assertEqual(check_deposit.move_id.state, 'posted') + self.assertEqual(check_deposit.state, 'done') diff --git a/account_check_deposit/views/account_deposit_view.xml b/account_check_deposit/views/account_deposit_view.xml index fd58b77f9..f09700ef8 100644 --- a/account_check_deposit/views/account_deposit_view.xml +++ b/account_check_deposit/views/account_deposit_view.xml @@ -55,7 +55,7 @@ ', 0), ('check_deposit_id', '=', False), ('currency_id', '=', currency_none_same_company_id), @@ -119,7 +119,7 @@ From 8f066beb59d0d8ea8196c38499f6013a54cbeb38 Mon Sep 17 00:00:00 2001 From: Florian da Costa Date: Sun, 6 Nov 2016 15:33:05 +0100 Subject: [PATCH 19/20] Fix payment field + automatic reconciliation on validation --- .../models/account_deposit.py | 16 ++++++++-------- .../views/account_deposit_view.xml | 18 +++++++++++++++++- 2 files changed, 25 insertions(+), 9 deletions(-) diff --git a/account_check_deposit/models/account_deposit.py b/account_check_deposit/models/account_deposit.py index 076775c4d..38f37feda 100644 --- a/account_check_deposit/models/account_deposit.py +++ b/account_check_deposit/models/account_deposit.py @@ -198,19 +198,21 @@ class AccountCheckDeposit(models.Model): @api.multi def validate_deposit(self): am_obj = self.env['account.move'] + move_line_obj = self.env['account.move.line'] for deposit in self: move_vals = self._prepare_account_move_vals(deposit) + move = am_obj.create(move_vals) total_debit = 0.0 total_amount_currency = 0.0 to_reconcile_lines = [] - mv_lines_vals = [] for line in deposit.check_payment_ids: total_debit += line.debit total_amount_currency += line.amount_currency line_vals = self._prepare_move_line_vals(line) - mv_lines_vals.append((0, 0, line_vals)) - - to_reconcile_lines.append(line) + line_vals['move_id'] = move.id + move_line = move_line_obj.with_context( + check_move_validity=False).create(line_vals) + to_reconcile_lines.append(line + move_line) # Create counter-part if not deposit.company_id.check_deposit_account_id: @@ -220,10 +222,8 @@ class AccountCheckDeposit(models.Model): counter_vals = self._prepare_counterpart_move_lines_vals( deposit, total_debit, total_amount_currency) - mv_lines_vals.append((0, 0, counter_vals)) - move_vals['line_ids'] = mv_lines_vals - move = am_obj.create(move_vals) - to_reconcile_lines.extend(move.line_ids) + counter_vals['move_id'] = move.id + move_line_obj.create(counter_vals) move.post() deposit.write({'state': 'done', 'move_id': move.id}) diff --git a/account_check_deposit/views/account_deposit_view.xml b/account_check_deposit/views/account_deposit_view.xml index f09700ef8..7d178d400 100644 --- a/account_check_deposit/views/account_deposit_view.xml +++ b/account_check_deposit/views/account_deposit_view.xml @@ -61,7 +61,23 @@ ('currency_id', '=', currency_none_same_company_id), ('account_id', '=', journal_default_account_id)]" context="{'currency': currency_id, - 'journal_id': journal_id}" /> + 'journal_id': journal_id}"> + + + + + + + + + + + + + + + + From 259946a28d42b4a402e41369f0ec23b34eca9704 Mon Sep 17 00:00:00 2001 From: Florian da Costa Date: Tue, 24 Jan 2017 14:52:13 +0100 Subject: [PATCH 20/20] [Fix] Pdf Report and version number --- account_check_deposit/README.rst | 4 ++-- account_check_deposit/__openerp__.py | 2 +- account_check_deposit/report/report_checkdeposit.xml | 6 +++--- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/account_check_deposit/README.rst b/account_check_deposit/README.rst index fc0afa5b3..201503d39 100644 --- a/account_check_deposit/README.rst +++ b/account_check_deposit/README.rst @@ -29,7 +29,7 @@ When you want to deposit checks to the bank, go to the menu *Accounting > Bank a .. image:: https://odoo-community.org/website/image/ir.attachment/5784_f2813bd/datas :alt: Try me on Runbot - :target: https://runbot.odoo-community.org/runbot/92/8.0 + :target: https://runbot.odoo-community.org/runbot/92/9.0 For further information, please visit: @@ -41,7 +41,7 @@ Bug Tracker Bugs are tracked on `GitHub Issues `_. In case of trouble, please check there if your issue has already been reported. If you spotted it first, help us smashing it by providing a detailed and welcomed feedback -`here `_. +`here `_. Credits ======= diff --git a/account_check_deposit/__openerp__.py b/account_check_deposit/__openerp__.py index 854713d08..f098ba487 100644 --- a/account_check_deposit/__openerp__.py +++ b/account_check_deposit/__openerp__.py @@ -13,7 +13,7 @@ { 'name': 'Account Check Deposit', - 'version': '8.0.0.1.0', + 'version': '9.0.0.1.0', 'category': 'Accounting & Finance', 'license': 'AGPL-3', 'summary': 'Manage deposit of checks to the bank', diff --git a/account_check_deposit/report/report_checkdeposit.xml b/account_check_deposit/report/report_checkdeposit.xml index 0ec70ed2b..c94348586 100644 --- a/account_check_deposit/report/report_checkdeposit.xml +++ b/account_check_deposit/report/report_checkdeposit.xml @@ -20,9 +20,9 @@

Check Deposit n°

Bank:

-


-
-

+


+
+

Beneficiary: