diff --git a/account_spread_cost_revenue/README.rst b/account_spread_cost_revenue/README.rst new file mode 100644 index 00000000..ac538f56 --- /dev/null +++ b/account_spread_cost_revenue/README.rst @@ -0,0 +1,229 @@ +=================== +Cost-Revenue Spread +=================== + +.. + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + !! This file is generated by oca-gen-addon-readme !! + !! changes will be overwritten. !! + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + !! source digest: sha256:560d87ede92fd18ca4a929595b6a9fd9f558f6b577e8c9bad1f8e7236ad4175d + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + +.. |badge1| image:: https://img.shields.io/badge/maturity-Beta-yellow.png + :target: https://odoo-community.org/page/development-status + :alt: Beta +.. |badge2| image:: https://img.shields.io/badge/licence-AGPL--3-blue.png + :target: http://www.gnu.org/licenses/agpl-3.0-standalone.html + :alt: License: AGPL-3 +.. |badge3| image:: https://img.shields.io/badge/github-OCA%2Faccount--financial--tools-lightgray.png?logo=github + :target: https://github.com/OCA/account-financial-tools/tree/16.0/account_spread_cost_revenue + :alt: OCA/account-financial-tools +.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png + :target: https://translation.odoo-community.org/projects/account-financial-tools-16-0/account-financial-tools-16-0-account_spread_cost_revenue + :alt: Translate me on Weblate +.. |badge5| image:: https://img.shields.io/badge/runboat-Try%20me-875A7B.png + :target: https://runboat.odoo-community.org/builds?repo=OCA/account-financial-tools&target_branch=16.0 + :alt: Try me on Runboat + +|badge1| |badge2| |badge3| |badge4| |badge5| + +Allows to spread costs or revenues over a customizable periods, to even out cost or invoice spikes. + +**Table of contents** + +.. contents:: + :local: + +Configuration +============= + +To be able to access the full spreading features, the user must belong to *Show Full Accounting Features* group. + +On the form view of the company, in the *Account Spread* tab, you can configure +the journals in which the spread journal items will be generated by default: + +* the *Default Spread Journal for Revenues*, +* the *Default Spread Journal for Expenses*. + +In the same *Account Spread* tab, you can also configure the Spread Balance Sheet Accounts used by default: + +* the *Default Spread Account for Revenues*, +* the *Default Spread Account for Expenses*. + +This module by default allows the spreading even before the receipt of the invoice or when the invoice is still draft, +so that it is possible to work on the plan of the cost/revenue spreading. To disable this feature, on the form view of +the company disable the *Allow Spread Planning* option. + +In Spread Template, there is also option to *Auto assign template on invoice validate*, based on the preset invoice line criteria. + +On the form view of the company, the *Auto-post spread lines* option forces the account moves created +during the cost/revenue spreading to be automatically posted. When this option is false, the user can +enable/disable the automatic posting by the flag *Auto-post lines* present in the spread board. + +On the form view of the company, enable the *Auto-archive spread* option if you want the +cron job to automatically archive the spreads when all lines are posted. + +Usage +===== + +Define Spread Costs/Revenues Board +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Under Invoicing -> Accounting -> Journals -> Spread Costs/Revenues, create a new spread board. + +Complete the definition of the spreading criteria, by setting the the fields: + +* *Debit Account* +* *Credit Account* +* *Estimated Amount* (The total amount to spread) +* *Number of Repetitions* +* *Period Type* (Duration of each period) +* *Start date* +* *Journal* + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/spread.png + :alt: Create a new spread board + +Click on the "Recalculate unposted lines" button on the top-left to calculate the spread lines. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/create_spread.png + :alt: The spreading board is defined + +A cron job will automatically create the accounting moves for all the lines having date previous that the current day (today). + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/update_spread.png + :alt: The spreading board is updated by the cron job + +By default, the status of the created accounting moves is posted. +To disable the automatic posting of the accounting moves, set the flag *Auto-post lines* to False. +This flag is only available when the *Auto-post spread lines* option, present on the form view of the company, is disabled. + +Click on button *Recalculate entire spread* button in the spread board to force the recalculation of the spread lines: +this will also reset all the journal entries previously created. + +Link Invoice to Spread Costs/Revenues Board +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Create an invoice or vendor bill in draft. On its lines, the spreading right-arrow icon are displayed in dark-grey color. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/invoice_line_1.png + :alt: On the invoice line the spreading icon is displayed + +Click on the spreading right-arrow icon. A wizard prompts to enter a *Spread Action Type*: + +- *Link to existing spread board* +- *Create from spread template* +- *Create new spread board* + +Select *Link to existing spread board* and enter the previously generated Spread Board. Click on Confirm button: +the selected Spread Board will be automatically displayed. + +Go back to the draft invoice/bill. The spreading functionality is now enabled on the invoice line: +the spreading right-arrow icon is now displayed in green color. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/invoice_line_2.png + :alt: On the invoice line the spreading icon is displayed in green color + +Validate the invoice/bill. Click on the spreading (green) right-arrow icon to open the spread board, then click +on the smart button *Posted entries* to see the moves of the spread lines together with the move of the invoice line. + +In case the Subtotal Price of the invoice line is different than the *Estimated Amount* of the spread board, the spread +lines (not yet posted) will be recalculated when validating the invoice/bill. + +Define Spread Costs/Revenues Template +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Under Invoicing -> Configuration -> Accounting -> Spread Templates, create a new spread template. + +* *Spread Type* +* *Spread Balance Sheet Account* +* *Expense/Revenue Account* This option visible if invoice line account is balance sheet account, user need to specify this too. +* *Journal* +* *Auto assign template on invoice validate* + +When creating a new Spread Costs/Revenues Board, select the right template. +This way the above fields will be copied to the Spread Board. + +If *Auto assign template on invoice validate* is checked, this template will be used to auto create spread, if the underlining invoice match the preset product/account/analytic criteria. + +Changelog +========= + +13.0.1.0.0 +~~~~~~~~~~ + +* [MIG] Port account_spread_cost_revenue to V13. + +12.0.2.0.0 +~~~~~~~~~~ + +* [ENH] In spread template, add option to auto create spread on invoice validation + +12.0.1.1.0 +~~~~~~~~~~ + +* [ENH] Add optional Expense/Revenue Account in Chart Template, which can be used + in place of account from invoice line to set Expense/Revenue account in the spread + + +12.0.1.0.0 +~~~~~~~~~~ + +* [MIG] Port account_spread_cost_revenue to V12. + + +11.0.1.0.0 +~~~~~~~~~~ + +* [ADD] Module account_spread_cost_revenue. + (`#715 `_) + +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 to smash it by providing a detailed and welcomed +`feedback `_. + +Do not contact contributors directly about support or help with technical issues. + +Credits +======= + +Authors +~~~~~~~ + +* Onestein + +Contributors +~~~~~~~~~~~~ + +* Andrea Stirpe +* Kitti U. +* Saran Lim. + +Other credits +~~~~~~~~~~~~~ + +Part of the code in this module (in particular the computation of the spread lines) +is highly inspired by the Assets Management module from the standard +Odoo 11.0 Community developed by Odoo SA. + +Maintainers +~~~~~~~~~~~ + +This module is maintained by the OCA. + +.. image:: https://odoo-community.org/logo.png + :alt: Odoo Community Association + :target: https://odoo-community.org + +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. + +This module is part of the `OCA/account-financial-tools `_ project on GitHub. + +You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute. diff --git a/account_spread_cost_revenue/__init__.py b/account_spread_cost_revenue/__init__.py new file mode 100644 index 00000000..adc6207f --- /dev/null +++ b/account_spread_cost_revenue/__init__.py @@ -0,0 +1,4 @@ +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from . import models +from . import wizards diff --git a/account_spread_cost_revenue/__manifest__.py b/account_spread_cost_revenue/__manifest__.py new file mode 100644 index 00000000..a4789d82 --- /dev/null +++ b/account_spread_cost_revenue/__manifest__.py @@ -0,0 +1,25 @@ +# Copyright 2016-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +{ + "name": "Cost-Revenue Spread", + "summary": "Spread costs and revenues over a custom period", + "version": "16.0.1.0.0", + "development_status": "Beta", + "author": "Onestein,Odoo Community Association (OCA)", + "license": "AGPL-3", + "website": "https://github.com/OCA/account-financial-tools", + "category": "Accounting & Finance", + "depends": ["account"], + "data": [ + "security/ir.model.access.csv", + "security/account_spread_security.xml", + "views/account_spread.xml", + "views/account_move.xml", + "views/res_company.xml", + "views/account_spread_template.xml", + "wizards/account_spread_invoice_line_link_wizard.xml", + "data/spread_cron.xml", + ], + "installable": True, +} diff --git a/account_spread_cost_revenue/data/spread_cron.xml b/account_spread_cost_revenue/data/spread_cron.xml new file mode 100644 index 00000000..b77437b8 --- /dev/null +++ b/account_spread_cost_revenue/data/spread_cron.xml @@ -0,0 +1,15 @@ + + + + Cost/revenue Spread: Create Entries + + + 1 + days + -1 + + + code + model._create_entries() + + diff --git a/account_spread_cost_revenue/i18n/account_spread_cost_revenue.pot b/account_spread_cost_revenue/i18n/account_spread_cost_revenue.pot new file mode 100644 index 00000000..10c09d1a --- /dev/null +++ b/account_spread_cost_revenue/i18n/account_spread_cost_revenue.pot @@ -0,0 +1,1087 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * account_spread_cost_revenue +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 14.0\n" +"Report-Msgid-Bugs-To: \n" +"Last-Translator: \n" +"Language-Team: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: \n" +"Plural-Forms: \n" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" This account in deprecated! The reconciliation will be NOT possible.\n" +" " +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" This account in deprecated! The reconciliation will be NOT possible.\n" +" " +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Balance Sheet account used for the spreading.
This account is the counterpart of the account in the invoice line.\n" +"
\n" +" \n" +" The Expense account in the vendor bill line.
Usually the same account of the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Balance Sheet account.
This is the account in the invoice line.\n" +"
\n" +" \n" +" The Expense account used for the spreading.
This account is the counterpart of the account of the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Revenue account in the invoice line.
Usually the same account of the invoice line.\n" +"
\n" +" \n" +" The Balance Sheet account used for the spreading.
This account is the counterpart of the account in the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Revenue account used for the spreading.
This account is the counterpart of the account of the invoice line.\n" +"
\n" +" \n" +" The Balance Sheet account.
This is the account in the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__account_id +msgid "Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Account Spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_invoice_line_link_wizard +msgid "Account Spread Invoice Line Link Wizard" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_line +msgid "Account Spread Lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_template +msgid "Account Spread Template" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "Action Needed" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__active +msgid "Active" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__all_posted +msgid "All Posted" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "Allow Spread Planning" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__amount +msgid "Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__analytic_account_id +msgid "Analytic" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__account_analytic_id +msgid "Analytic Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__analytic_tag_ids +msgid "Analytic Tags" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_search +msgid "Archived" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_attachment_count +msgid "Attachment Count" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__auto_spread_ids +msgid "Auto Spread On" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__auto_spread +msgid "Auto assign template on invoice validate" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_template_auto +msgid "Auto create spread, based on product/account/analytic" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__auto_archive_spread +msgid "Auto-archive spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__move_line_auto_post +msgid "Auto-post lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "Auto-post spread lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "" +"Automatically use this spread template on invoice validation for invoice " +"lines using below product and/or account and/or analytic," +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_account_id +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Balance sheet account / Spread account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Cancel" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Cannot delete spread(s) that are linked to an invoice line." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Cannot delete spread(s): there are posted Journal Entries." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "Cannot reconcile entries that are already reconciled:\n" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Cannot unlink invoice lines if the invoice is validated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_res_company +msgid "Companies" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__company_id +msgid "Company" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Confirm" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.server,name:account_spread_cost_revenue.ir_cron_spread_create_entries_ir_actions_server +#: model:ir.cron,cron_name:account_spread_cost_revenue.ir_cron_spread_create_entries +#: model:ir.cron,name:account_spread_cost_revenue.ir_cron_spread_create_entries +msgid "Cost/revenue Spread: Create Entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create Move" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#, python-format +msgid "Create from spread template" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#, python-format +msgid "Create new spread board" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__create_uid +msgid "Created by" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:0 +#, python-format +msgid "Created move(s) " +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__create_date +msgid "Created on" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__credit_account_id +msgid "Credit Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__currency_id +msgid "Currency" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__spread_type__sale +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__spread_type__sale +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_template__spread_type__sale +msgid "Customer" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__invoice_type__out_refund +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__invoice_type__out_refund +msgid "Customer Credit Note" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__invoice_type__out_invoice +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__invoice_type__out_invoice +msgid "Customer Invoice" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__date +msgid "Date" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__debit_account_id +msgid "Debit Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Accounts" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Journals" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Define the number of spread lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Delete Move" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:0 +#, python-format +msgid "Deleted move %s" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__name +msgid "Description" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "" +"Disable this option if you do not want to allow the spreading before the " +"invoice is validated." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_move_line_auto_post +msgid "Display Button Auto-post lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_create_all_moves +msgid "Display Create All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move_line__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__display_name +msgid "Display Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_recompute_buttons +msgid "Display Recompute Buttons" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__auto_archive_spread +msgid "" +"Enable this option if you want the cron job to automatically archive the " +"spreads when all lines are posted." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "" +"Enable this option if you want to post automatically the accounting moves of" +" all the spreads." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__estimated_amount +msgid "Estimated Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_account_id +msgid "Expense Spread Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_journal_id +msgid "Expense Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Expense account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Expense/Revenue Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +msgid "Expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_follower_ids +msgid "Followers" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_channel_ids +msgid "Followers (Channels)" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_partner_ids +msgid "Followers (Partners)" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_template.py:0 +#, python-format +msgid "" +"Followings are duplicated combinations,\n" +"\n" +"%s\n" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move_line__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__id +msgid "ID" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread +msgid "If checked, new messages require your attention." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__auto_spread +msgid "" +"If checked, provide option to auto create spread during invoice validation, " +"based on product/account/analytic in invoice line." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_sms_error +msgid "If checked, some messages have a delivery error." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Invoice" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_line_id +msgid "Invoice Line" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_ids +msgid "Invoice Lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_type +msgid "Invoice Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "Invoice account as spread account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_id +msgid "Invoice line" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_credit_account_deprecated +msgid "Is Credit Account Deprecated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_debit_account_deprecated +msgid "Is Debit Account Deprecated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_is_follower +msgid "Is Follower" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__journal_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_journal_id +msgid "Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:0 +#: model:ir.model,name:account_spread_cost_revenue.model_account_move +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__move_id +#, python-format +msgid "Journal Entry" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_move_line +msgid "Journal Item" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_moves_all_spread +msgid "Journal Items" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move_line____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company____last_update +msgid "Last Modified on" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__write_uid +msgid "Last Updated by" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__write_date +msgid "Last Updated on" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "Link Invoice Line with Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#, python-format +msgid "Link to existing spread board" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_move_line__spread_check__linked +msgid "Linked" +msgstr "" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:0 +#, python-format +msgid "Linked to spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_main_attachment_id +msgid "Main Attachment" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "Message Delivery error" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_ids +msgid "Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__period_type__month +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_template__period_type__month +msgid "Month" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "Move line: %s (%s), account code: %s\n" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__name +msgid "Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#, python-format +msgid "New Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:0 +#, python-format +msgid "Not linked to spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of Actions" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Number of Repetitions" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of errors" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of messages which requires an action" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of messages with delivery error" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Number of unread messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Optional account to overwrite the existing expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period length for the entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_template.py:0 +#, python-format +msgid "Please select product and/or account on auto spread options" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__posted_amount +msgid "Posted Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__product_id +msgid "Product" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__period_type__quarter +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_template__period_type__quarter +msgid "Quarter" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate entire spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate unposted lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Reconciled entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_account_id +msgid "Revenue Spread Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_journal_id +msgid "Revenue Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_sms_error +msgid "SMS Delivery error" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "Some entries are not from the same account:\n" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__spread_id +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_search +#, python-format +msgid "Spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_action_type +msgid "Spread Action Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_account_id +msgid "Spread Balance Sheet Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move_line__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_id +msgid "Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread Board Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_move_line__spread_check +msgid "Spread Check" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_form +msgid "Spread Costs/Revenues" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:0 +#, python-format +msgid "Spread Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_invoice_type_domain_ids +msgid "Spread Invoice Type Domain" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_journal_id +msgid "Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__line_ids +msgid "Spread Lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__template_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__template_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template_auto__template_id +msgid "Spread Template" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "Spread Template Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_template_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_template_form +msgid "Spread Templates" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_type +msgid "Spread Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Spread table '%s' created." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__start_date +msgid "Start Date" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__spread_type__purchase +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__spread_type__purchase +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_template__spread_type__purchase +msgid "Supplier" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "The Invoice Type does not correspond to the Invoice" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "The Journal is not consistent with the account moves." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "" +"The Spread Template (Purchases) is not compatible with selected invoice type" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "" +"The Spread Template (Sales) is not compatible with selected invoice type" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "" +"The account of the invoice line does not correspond to the Balance Sheet " +"(credit account) of the spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "" +"The account of the invoice line does not correspond to the Balance Sheet " +"(debit account) of the spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__invoice_id +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_id +msgid "The move of this entry line." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:0 +#, python-format +msgid "" +"This spread line is already linked to a journal entry! Please post or delete" +" it." +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "This will delete the move. Are you sure ?" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_move_line.py:0 +#, python-format +msgid "Too many auto spread templates (%s) matched with the invoice line, %s" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Total" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__total_amount +msgid "Total Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_move_line__spread_check__unavailable +msgid "Unavailable" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Undo spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Unlink Invoice Line" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_move_line__spread_check__unlinked +msgid "Unlinked" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Unlinked '%s' (invoice line %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:0 +#, python-format +msgid "Unlinked invoice line '%s' (view %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unposted_amount +msgid "Unposted Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread +msgid "Unread Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Unread Messages Counter" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unspread_amount +msgid "Unspread Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__use_invoice_line_account +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +msgid "Use Invoice Line Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "" +"Use invoice line's account as Balance sheet / spread account.\n" +"In this case, user need to select expense/revenue account too." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__invoice_type__in_invoice +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__invoice_type__in_invoice +msgid "Vendor Bill" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__invoice_type__in_refund +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_invoice_line_link_wizard__invoice_type__in_refund +msgid "Vendor Credit Note" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "View Move" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website communication history" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread__period_type__year +#: model:ir.model.fields.selection,name:account_spread_cost_revenue.selection__account_spread_template__period_type__year +msgid "Year" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "e.g. One year offices cleaning contract" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "e.g. Template cleaning contract" +msgstr "" diff --git a/account_spread_cost_revenue/i18n/fr.po b/account_spread_cost_revenue/i18n/fr.po new file mode 100644 index 00000000..09ec4db8 --- /dev/null +++ b/account_spread_cost_revenue/i18n/fr.po @@ -0,0 +1,1117 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * account_spread_cost_revenue +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 12.0\n" +"Report-Msgid-Bugs-To: \n" +"PO-Revision-Date: 2020-02-17 17:13+0000\n" +"Last-Translator: Martronic SA \n" +"Language-Team: none\n" +"Language: fr\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: \n" +"Plural-Forms: nplurals=2; plural=n > 1;\n" +"X-Generator: Weblate 3.10\n" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "invoice line.\n" +#| "
\n" +#| " \n" +#| " The Expense account in the vendor bill " +#| "line.
Usually the same account of the vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the invoice " +"line.\n" +"
\n" +" \n" +" The Expense account in the vendor bill " +"line.
Usually the same account of the vendor bill line.\n" +"
" +msgstr "" +"\n" +" Le compte de bilan utilisé pour cette " +"régularisation.
Ce compte est la contrepartie du compte utilisé dans la " +"ligne de facture.\n" +"
\n" +" \n" +" Le compte de dépense dans la ligne de " +"facture fournisseur.
Généralement le même compte que la ligne de facture " +"fournisseur.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Revenue account in the invoice line." +#| "
Usually the same account of the invoice line.\n" +#| "
\n" +#| " \n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Balance Sheet account.
This is " +"the account in the invoice line.\n" +"
\n" +" \n" +" The Expense account used for the " +"spreading.
This account is the counterpart of the account of the vendor " +"bill line.\n" +"
" +msgstr "" +"\n" +" Le compte de revenu dans la ligne de " +"facture.
Généralement le même compte que la ligne de facture.\n" +"
\n" +" \n" +" Le compte de bilan utilisé pour cette " +"régularisation.
Ce compte est la contrepartie du compte dans la ligne de " +"facture client.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Revenue account in the invoice line." +#| "
Usually the same account of the invoice line.\n" +#| "
\n" +#| " \n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Revenue account in the invoice " +"line.
Usually the same account of the invoice line.\n" +"
\n" +" \n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the vendor " +"bill line.\n" +"
" +msgstr "" +"\n" +" Le compte de revenu dans la ligne de " +"facture.
Généralement le même compte que la ligne de facture.\n" +"
\n" +" \n" +" Le compte de bilan utilisé pour cette " +"régularisation.
Ce compte est la contrepartie du compte dans la ligne de " +"facture client.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "invoice line.\n" +#| "
\n" +#| " \n" +#| " The Expense account in the vendor bill " +#| "line.
Usually the same account of the vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Revenue account used for the " +"spreading.
This account is the counterpart of the account of the invoice " +"line.\n" +"
\n" +" \n" +" The Balance Sheet account.
This is " +"the account in the vendor bill line.\n" +"
" +msgstr "" +"\n" +" Le compte de bilan utilisé pour cette " +"régularisation.
Ce compte est la contrepartie du compte utilisé dans la " +"ligne de facture.\n" +"
\n" +" \n" +" Le compte de dépense dans la ligne de " +"facture fournisseur.
Généralement le même compte que la ligne de facture " +"fournisseur.\n" +"
" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Account Spread" +msgstr "Régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_invoice_line_link_wizard +msgid "Account Spread Invoice Line Link Wizard" +msgstr "Assistant lien ligne de facture et régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_line +msgid "Account Spread Lines" +msgstr "Lignes de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_template +msgid "Account Spread Template" +msgstr "Modèle de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "Action Needed" +msgstr "Action requise" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__active +msgid "Active" +msgstr "Actif" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__all_posted +msgid "All Posted" +msgstr "Entièrement comptabilisé" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "Allow Spread Planning" +msgstr "Permettre de planifier la régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__amount +msgid "Amount" +msgstr "Montant" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__account_analytic_id +msgid "Analytic Account" +msgstr "Compte analytique" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__analytic_tag_ids +msgid "Analytic Tags" +msgstr "Étiquettes analytiques" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_search +msgid "Archived" +msgstr "Archivé" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_attachment_count +msgid "Attachment Count" +msgstr "Nombre de pièces jointes" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__auto_archive +msgid "Auto-archive spread" +msgstr "Régularisation auto-archivée" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__move_line_auto_post +msgid "Auto-post lines" +msgstr "Lignes auto-comptabilisées" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "Auto-post spread lines" +msgstr "Lignes de régularisation auto-postées" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_account_id +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Balance sheet account / Spread account" +msgstr "Compte de bilan / Compte de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Cancel" +msgstr "Annuler" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:467 +#, python-format +msgid "Cannot delete spread(s) that are linked to an invoice line." +msgstr "" +"Impossible de supprimer des régularisation(s) liées à une ligne de facture." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:472 +#, python-format +msgid "Cannot delete spread(s): there are posted Journal Entries." +msgstr "" +"Ne peut pas supprimer la (les) régularisation(s) : Il y a des écritures " +"comptables comptabilisées." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:439 +#, python-format +msgid "Cannot unlink invoice lines if the invoice is validated" +msgstr "Ne peut pas supprimer les lignes de facture si la facture est validée" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_res_company +msgid "Companies" +msgstr "Sociétés" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__company_id +msgid "Company" +msgstr "Société" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Confirm" +msgstr "Confirmer" + +#. module: account_spread_cost_revenue +#: model:ir.actions.server,name:account_spread_cost_revenue.ir_cron_spread_create_entries_ir_actions_server +#: model:ir.cron,cron_name:account_spread_cost_revenue.ir_cron_spread_create_entries +#: model:ir.cron,name:account_spread_cost_revenue.ir_cron_spread_create_entries +msgid "Cost/revenue Spread: Create Entries" +msgstr "Régularisation des coûts/revenus : Créer les écritures" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create All Moves" +msgstr "Créer toutes les écritures" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create Move" +msgstr "Créer l'écriture" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:13 +#, python-format +msgid "Create from spread template" +msgstr "Créer depuis un Modèle de régularisation" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:14 +#, python-format +msgid "Create new spread board" +msgstr "Créer un nouveau tableau de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_uid +msgid "Created by" +msgstr "Créé par" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:36 +#, python-format +msgid "Created move(s) " +msgstr "Écritures créée(s) " + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_date +msgid "Created on" +msgstr "Créé le" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__credit_account_id +msgid "Credit Account" +msgstr "Compte de crédit" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__currency_id +msgid "Currency" +msgstr "Devise" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Customer" +msgstr "Client" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Credit Note" +msgstr "Avoir client" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Invoice" +msgstr "Facture client" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__date +msgid "Date" +msgstr "Date" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__debit_account_id +msgid "Debit Account" +msgstr "Compte de débit" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Accounts" +msgstr "Compte de régularisation par défaut" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Journals" +msgstr "Journaux de régularisation par défaut" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Define the number of spread lines" +msgstr "Définir le nombre de lignes de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Delete Move" +msgstr "Supprimer la pièce comptable" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:149 +#, python-format +msgid "Deleted move %s" +msgstr "Supprimer la pièce %s" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__name +msgid "Description" +msgstr "Description" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Details" +msgstr "Détails" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "" +"Disable this option if you do not want to allow the spreading before the " +"invoice is validated." +msgstr "" +"Désactivez cette option si vous ne voulez pas permettre la régularisation " +"avant que la facture ne soit validée." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_create_all_moves +msgid "Display Button All Moves" +msgstr "Afficher le bouton Toutes les pièces" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_move_line_auto_post +msgid "Display Button Auto-post lines" +msgstr "Afficher le bouton Auto-comptabiliser les écritures" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_recompute_buttons +msgid "Display Buttons Recompute" +msgstr "Afficher le bouton Recalculer" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__display_name +msgid "Display Name" +msgstr "Nom affiché" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__auto_archive +msgid "" +"Enable this option if you want the cron job to automatically archive the " +"spreads when all lines are posted." +msgstr "" +"Activer cette option si vous voulez que la tâche cron archive " +"automatiquement les régularisations lorsque toutes les écritures sont " +"comptabilisées." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "" +"Enable this option if you want to post automatically the accounting moves of " +"all the spreads." +msgstr "" +"Activez cette options si vous voulez comptabiliser automatiquement les " +"écritures comptables de toutes les régularisations." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__estimated_amount +msgid "Estimated Amount" +msgstr "Montant estimé" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_account_id +msgid "Expense Spread Account" +msgstr "Compte de dépense de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_journal_id +msgid "Expense Spread Journal" +msgstr "Journal de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Expense account" +msgstr "Compte de dépense" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +#, fuzzy +#| msgid "Revenue account" +msgid "Expense/Revenue Account" +msgstr "Compte de revenus" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#, fuzzy +#| msgid "Expense account" +msgid "Expense/revenue account" +msgstr "Compte de dépense" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_follower_ids +msgid "Followers" +msgstr "Abonnés" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_channel_ids +msgid "Followers (Channels)" +msgstr "Abonnés (Canaux)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_partner_ids +msgid "Followers (Partners)" +msgstr "Abonnés (Partenaires)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__id +msgid "ID" +msgstr "ID" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread +msgid "If checked new messages require your attention." +msgstr "Si coché, de nouveaux messages demandent votre attention." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "If checked, new messages require your attention." +msgstr "Si coché, de nouveaux messages demandent votre attention." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "If checked, some messages have a delivery error." +msgstr "Si actif, certains messages ont une erreur de livraison." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:453 +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_id +#, python-format +msgid "Invoice" +msgstr "Facture" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice_line +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_line_id +msgid "Invoice Line" +msgstr "Ligne de facture" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_ids +msgid "Invoice Lines" +msgstr "Lignes de facture" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_id +msgid "Invoice Reference" +msgstr "Référence de facture" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_type +msgid "Invoice Type" +msgstr "Type de facture" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +#, fuzzy +#| msgid "Balance sheet account / Spread account" +msgid "Invoice account as spread account" +msgstr "Compte de bilan / Compte de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_id +msgid "Invoice line" +msgstr "Ligne de facture" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_credit_account_deprecated +#, fuzzy +msgid "Is Credit Account Deprecated" +msgstr "Est compte de crédit obsolète" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_debit_account_deprecated +msgid "Is Debit Account Deprecated" +msgstr "Est compte de débit obsolète" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_is_follower +msgid "Is Follower" +msgstr "Est un abonné" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__journal_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_journal_id +msgid "Journal" +msgstr "Journal" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:130 +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__move_id +#, python-format +msgid "Journal Entry" +msgstr "Écriture comptable" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template____last_update +msgid "Last Modified on" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_uid +msgid "Last Updated by" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_date +msgid "Last Updated on" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:60 +#, python-format +msgid "Link Invoice Line with Spread Board" +msgstr "Lier la ligne de facture à une régularisation" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:20 +#, python-format +msgid "Link to existing spread board" +msgstr "Lier à un tableau de régularisation existant" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Linked" +msgstr "Lié" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:33 +#, python-format +msgid "Linked to spread" +msgstr "Lié à la régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_main_attachment_id +msgid "Main Attachment" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "Message Delivery error" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_ids +msgid "Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Month" +msgstr "Mois" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__name +msgid "Name" +msgstr "Nom" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:157 +#, python-format +msgid "New Spread Board" +msgstr "Nouvelle régularisation" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:35 +#, python-format +msgid "Not linked to spread" +msgstr "Non-lié à une régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of Actions" +msgstr "Nombre d'actions" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Number of Repetitions" +msgstr "Nombre de Répétitions" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of error" +msgstr "Nombre d'erreurs" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of messages which requires an action" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of messages with delivery error" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Number of unread messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Optional account to overwrite the existing expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period Type" +msgstr "Type de période" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period length for the entries" +msgstr "Durée de la période pour les écritures" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__posted_amount +msgid "Posted Amount" +msgstr "Montant comptabilisé" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Quarter" +msgstr "Trimestre" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate entire spread" +msgstr "Recalculer toute la régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate unposted lines" +msgstr "Recalculer les écritures non comptabilisées" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Reconciled entries" +msgstr "Écritures lettrées" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_account_id +msgid "Revenue Spread Account" +msgstr "Compte de revenus de la régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_journal_id +msgid "Revenue Spread Journal" +msgstr "Journal de revenus de la régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Revenue account" +msgstr "Compte de revenus" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:458 +#, python-format +msgid "Spread" +msgstr "Régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_action_type +msgid "Spread Action Type" +msgstr "Type d'action de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_account_id +msgid "Spread Balance Sheet Account" +msgstr "Compte de bilan de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__spread_id +msgid "Spread Board" +msgstr "Tableau de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread Board Name" +msgstr "Nom du tableau de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_check +msgid "Spread Check" +msgstr "Contrôle de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_form +msgid "Spread Costs/Revenues" +msgstr "Régularisation Coûts/Revenus" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:40 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:134 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:213 +#, python-format +msgid "Spread Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_journal_id +msgid "Spread Journal" +msgstr "Journal de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__line_ids +msgid "Spread Lines" +msgstr "Lignes de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__template_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__template_id +msgid "Spread Template" +msgstr "Modèle de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "Spread Template Name" +msgstr "Nom du modèle de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_template_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_template_form +msgid "Spread Templates" +msgstr "Modèles de régularisation" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_type +msgid "Spread Type" +msgstr "Type de régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread lines" +msgstr "Lignes de régularisation" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:378 +#, python-format +msgid "Spread table '%s' created." +msgstr "Tableau de régularisation '%s' créé." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__start_date +msgid "Start Date" +msgstr "Date de début" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Supplier" +msgstr "Fournisseur" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:264 +#, python-format +msgid "The Invoice Type does not correspond to the Invoice" +msgstr "Le Type de facture ne correspond pas à la facture" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:272 +#, python-format +msgid "The Journal is not consistent with the account moves." +msgstr "Le journal n'est pas cohérent avec les écritures comptables." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:285 +#, python-format +msgid "" +"The Spread Template (Purchases) is not compatible with selected invoice type" +msgstr "" +"Le modèle de régularisation (Achats) n'est pas compatible avec le type de " +"facture sélectionné" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:280 +#, python-format +msgid "" +"The Spread Template (Sales) is not compatible with selected invoice type" +msgstr "" +"Le modèle de régularisation (Ventes) n'est pas compatible avec le type de " +"facture sélectionné" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:65 +#, python-format +msgid "" +"This spread line is already linked to a journal entry! Please post or delete " +"it." +msgstr "" +"Cette ligne de régularisation est déjà liée à une écriture comptable! " +"Veuillez la comptabiliser ou la supprimer." + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "This will delete the move. Are you sure ?" +msgstr "Cela supprimera la pièce comptable. Êtes-vous sûr?" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Total" +msgstr "Total" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__total_amount +msgid "Total Amount" +msgstr "Montant total" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unavailable" +msgstr "Non-disponible" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Undo spread" +msgstr "Annuler la régularisation" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Unlink Invoice Line" +msgstr "Délier la ligne de facture" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unlinked" +msgstr "Non-lié" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:459 +#, python-format +msgid "Unlinked '%s' (invoice line %s)." +msgstr "Non-lié '%s' (ligne de facture %s)." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:454 +#, python-format +msgid "Unlinked invoice line '%s' (view %s)." +msgstr "Ligne de facture non-liée '%s' (voir %s)." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unposted_amount +msgid "Unposted Amount" +msgstr "Montant non-comptabilisé" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread +msgid "Unread Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Unread Messages Counter" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unspread_amount +msgid "Unspread Amount" +msgstr "Montant non régularisé" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__use_invoice_line_account +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#, fuzzy +#| msgid "Revenue account" +msgid "Use invoice line's account" +msgstr "Compte de revenus" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "" +"Use invoice line's account as Balance sheet / spread account.\n" +"In this case, user need to select expense/revenue account too." +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Bill" +msgstr "Facture fournisseur" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Credit Note" +msgstr "Avoir fournisseur" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "View Move" +msgstr "Voir la pièce comptable" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website Messages" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website communication history" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Year" +msgstr "Année" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "e.g. One year offices cleaning contract" +msgstr "p. ex. Contrat annuel nettoyage bureau" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "e.g. Template cleaning contract" +msgstr "p. ex. Modèle contrat nettoyage" diff --git a/account_spread_cost_revenue/i18n/nl.po b/account_spread_cost_revenue/i18n/nl.po new file mode 100644 index 00000000..75037bc8 --- /dev/null +++ b/account_spread_cost_revenue/i18n/nl.po @@ -0,0 +1,1000 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * account_spread_cost_revenue +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 12.0\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2019-04-25 13:10+0000\n" +"PO-Revision-Date: 2019-04-25 13:10+0000\n" +"Last-Translator: <>\n" +"Language-Team: \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: \n" +"Plural-Forms: \n" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the invoice " +"line.\n" +"
\n" +" \n" +" The Expense account in the vendor bill " +"line.
Usually the same account of the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Balance Sheet account.
This is " +"the account in the invoice line.\n" +"
\n" +" \n" +" The Expense account used for the " +"spreading.
This account is the counterpart of the account of the vendor " +"bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Revenue account in the invoice " +"line.
Usually the same account of the invoice line.\n" +"
\n" +" \n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the vendor " +"bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +" The Revenue account used for the " +"spreading.
This account is the counterpart of the account of the invoice " +"line.\n" +"
\n" +" \n" +" The Balance Sheet account.
This is " +"the account in the vendor bill line.\n" +"
" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Account Spread" +msgstr "Grootboekrekening Spreiding" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_invoice_line_link_wizard +msgid "Account Spread Invoice Line Link Wizard" +msgstr "Transitorisch Factuur Regel Koppel Wizard" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_line +msgid "Account Spread Lines" +msgstr "Grootboekrekening Spreiding Regels" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_template +msgid "Account Spread Template" +msgstr "Transitorische Spreidingsjabloon" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "Action Needed" +msgstr "Vereist actie" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__active +msgid "Active" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__all_posted +msgid "All Posted" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "Allow Spread Planning" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__amount +msgid "Amount" +msgstr "Bedrag" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__account_analytic_id +msgid "Analytic Account" +msgstr "Kostenplaats" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__analytic_tag_ids +msgid "Analytic Tags" +msgstr "Labels kostenplaats" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_search +msgid "Archived" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_attachment_count +msgid "Attachment Count" +msgstr "Aantal bijlagen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__auto_archive +msgid "Auto-archive spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__move_line_auto_post +msgid "Auto-post lines" +msgstr "Automatisch boeken regels" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__force_move_auto_post +#, fuzzy +msgid "Auto-post spread lines" +msgstr "Automatisch boeken regels" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_account_id +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Balance sheet account / Spread account" +msgstr "Balance grootboekrekening / Grootboekrekening Spreiding" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Cancel" +msgstr "Annuleren" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:467 +#, python-format +msgid "Cannot delete spread(s) that are linked to an invoice line." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:472 +#, python-format +msgid "Cannot delete spread(s): there are posted Journal Entries." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:439 +#, python-format +msgid "Cannot unlink invoice lines if the invoice is validated" +msgstr "" +"Ontkoppelen van factuurregels is niet mogelijk als de factuur bevestigd is" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_res_company +msgid "Companies" +msgstr "Bedrijven" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__company_id +msgid "Company" +msgstr "Bedrijf" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Confirm" +msgstr "Bevestigen" + +#. module: account_spread_cost_revenue +#: model:ir.actions.server,name:account_spread_cost_revenue.ir_cron_spread_create_entries_ir_actions_server +#: model:ir.cron,cron_name:account_spread_cost_revenue.ir_cron_spread_create_entries +#: model:ir.cron,name:account_spread_cost_revenue.ir_cron_spread_create_entries +msgid "Cost/revenue Spread: Create Entries" +msgstr "Kosten/omzet spreiding: Aanmaken regels" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create Move" +msgstr "Maak mutatie" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:13 +#, fuzzy, python-format +#| msgid "Spread Template" +msgid "Create from spread template" +msgstr "Spreidingsjabloon" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:14 +#, fuzzy, python-format +#| msgid "New Spread Board" +msgid "Create new spread board" +msgstr "Nieuw Spreiding Tabel" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_uid +msgid "Created by" +msgstr "Aangemaakt door" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:36 +#, python-format +msgid "Created move(s) " +msgstr "Aangemaakte regel(s) " + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_date +msgid "Created on" +msgstr "Aangemaakt op" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__credit_account_id +msgid "Credit Account" +msgstr "Credit Grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__currency_id +msgid "Currency" +msgstr "Valuta" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Customer" +msgstr "Klant" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Credit Note" +msgstr "Klant Credit Nota" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Invoice" +msgstr "Klant Factuur" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__date +msgid "Date" +msgstr "Datum" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__debit_account_id +msgid "Debit Account" +msgstr "Debet Grootboekrekening" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Accounts" +msgstr "Standaard Spreiding Grootboekrekeningen" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Journals" +msgstr "Standaard Spreiding Dagboeken" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Define the number of spread lines" +msgstr "Definieer het aantal spreiding regels" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Delete Move" +msgstr "Verwijder Boeking" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:149 +#, python-format +msgid "Deleted move %s" +msgstr "Verwijder boeking %s" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__name +msgid "Description" +msgstr "Omschrijving" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "" +"Disable this option if you do not want to allow the spreading before the " +"invoice is validated." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_create_all_moves +msgid "Display Button All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_move_line_auto_post +#, fuzzy +msgid "Display Button Auto-post lines" +msgstr "Automatisch boeken regels" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_recompute_buttons +msgid "Display Buttons Recompute" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__display_name +msgid "Display Name" +msgstr "Schermnaam" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__auto_archive +msgid "" +"Enable this option if you want the cron job to automatically archive the " +"spreads when all lines are posted." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "" +"Enable this option if you want to post automatically the accounting moves of " +"all the spreads." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__estimated_amount +msgid "Estimated Amount" +msgstr "Geschat Bedrag" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_account_id +msgid "Expense Spread Account" +msgstr "Kosten spreiding Grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_journal_id +msgid "Expense Spread Journal" +msgstr "Kosten spreiding Dagboek" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Expense account" +msgstr "Kosten grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +#, fuzzy +#| msgid "Revenue account" +msgid "Expense/Revenue Account" +msgstr "Omzet grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#, fuzzy +#| msgid "Expense account" +msgid "Expense/revenue account" +msgstr "Kosten grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_follower_ids +msgid "Followers" +msgstr "Volgers" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_channel_ids +msgid "Followers (Channels)" +msgstr "Volgers (Kanalen)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_partner_ids +msgid "Followers (Partners)" +msgstr "Volgers (Relaties)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__id +msgid "ID" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread +msgid "If checked new messages require your attention." +msgstr "Indien aangevinkt zullen nieuwe berichten uw aandacht vragen." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "If checked, new messages require your attention." +msgstr "Indien aangevinkt vragen nieuwe berichten uw aandacht." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "If checked, some messages have a delivery error." +msgstr "indien aangevinkt hebben sommige leveringen een fout." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:453 +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_id +#, python-format +msgid "Invoice" +msgstr "Factuur" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice_line +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_line_id +msgid "Invoice Line" +msgstr "Factuurregel" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_ids +msgid "Invoice Lines" +msgstr "Factuurregels" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_id +msgid "Invoice Reference" +msgstr "Factuurreferentie" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_type +msgid "Invoice Type" +msgstr "Factuur Type" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +#, fuzzy +#| msgid "Balance sheet account / Spread account" +msgid "Invoice account as spread account" +msgstr "Balance grootboekrekening / Grootboekrekening Spreiding" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_id +msgid "Invoice line" +msgstr "Factuur regel" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_credit_account_deprecated +msgid "Is Credit Account Deprecated" +msgstr "Is Credit Grootboekrekening Verouderd" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_debit_account_deprecated +msgid "Is Debit Account Deprecated" +msgstr "Is Debet Grootboekrekening Verouderd" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_is_follower +msgid "Is Follower" +msgstr "Is een volger" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__journal_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_journal_id +msgid "Journal" +msgstr "Dagboek" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:130 +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__move_id +#, python-format +msgid "Journal Entry" +msgstr "Boeking" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template____last_update +msgid "Last Modified on" +msgstr "Laatst gewijzigd op" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_uid +msgid "Last Updated by" +msgstr "Laatst bijgewerkt door" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_date +msgid "Last Updated on" +msgstr "Laatst bijgewerkt op" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:60 +#, python-format +msgid "Link Invoice Line with Spread Board" +msgstr "Koppel Factuur Regel met Spreiding Tabel" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:20 +#, fuzzy, python-format +#| msgid "Link Invoice Line with Spread Board" +msgid "Link to existing spread board" +msgstr "Koppel Factuur Regel met Spreiding Tabel" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Linked" +msgstr "Gekoppeld" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:33 +#, python-format +msgid "Linked to spread" +msgstr "Gekoppeld met spreiding" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_main_attachment_id +msgid "Main Attachment" +msgstr "Hoofd bijlage" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "Message Delivery error" +msgstr "Bericht afleverfout" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_ids +msgid "Messages" +msgstr "Berichten" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Month" +msgstr "Maand" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__name +msgid "Name" +msgstr "Naam" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:157 +#, python-format +msgid "New Spread Board" +msgstr "Nieuw Spreiding Tabel" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:35 +#, python-format +msgid "Not linked to spread" +msgstr "Niet gekoppeld met spreiding" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of Actions" +msgstr "Aantal acties" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Number of Repetitions" +msgstr "Aantal Herhalingen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of error" +msgstr "Aantal foutmeldingen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of messages which requires an action" +msgstr "Aantal berichten die actie vereisen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of messages with delivery error" +msgstr "Aantal berichten met leveringsfout" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Number of unread messages" +msgstr "Aantal ongelezen berichten" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Optional account to overwrite the existing expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period Type" +msgstr "Periode Type" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period length for the entries" +msgstr "Periode lengte voor boekingen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__posted_amount +msgid "Posted Amount" +msgstr "Geboekte Bedrag" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Quarter" +msgstr "Kwartaal" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate entire spread" +msgstr "Herbereken volledige spreiding" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate unposted lines" +msgstr "Herbereken ongeboekte regels" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Reconciled entries" +msgstr "Afgeletterde boekingen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_account_id +msgid "Revenue Spread Account" +msgstr "Omzet Spreiding Grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_journal_id +msgid "Revenue Spread Journal" +msgstr "Omzet Spreiding Dagboek" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Revenue account" +msgstr "Omzet grootboekrekening" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:458 +#, fuzzy, python-format +msgid "Spread" +msgstr "Spreiding Type" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_action_type +msgid "Spread Action Type" +msgstr "Spreiding Actie Type" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_account_id +msgid "Spread Balance Sheet Account" +msgstr "Spreiding Balans Grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__spread_id +msgid "Spread Board" +msgstr "Spreiding Tabel" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread Board Name" +msgstr "Spreiding Tabel Naam" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_check +msgid "Spread Check" +msgstr "Spreiding Controle" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_form +msgid "Spread Costs/Revenues" +msgstr "Spreiding Kosten/Omzet" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:40 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:134 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:213 +#, python-format +msgid "Spread Details" +msgstr "Spreiding Details" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_journal_id +msgid "Spread Journal" +msgstr "Spreiding Dagboek" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__line_ids +msgid "Spread Lines" +msgstr "Boekingsregels Spreiding" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__template_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__template_id +msgid "Spread Template" +msgstr "Spreidingsjabloon" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "Spread Template Name" +msgstr "Spreidingsjabloon Naam" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_template_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_template_form +msgid "Spread Templates" +msgstr "Spreidingsjablonen" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_type +msgid "Spread Type" +msgstr "Spreiding Type" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread lines" +msgstr "Spreiding Regels" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:378 +#, python-format +msgid "Spread table '%s' created." +msgstr "Spreiding tabel '%s' aangemaakt." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__start_date +msgid "Start Date" +msgstr "Startdatum" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Supplier" +msgstr "Leverancier" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:264 +#, python-format +msgid "The Invoice Type does not correspond to the Invoice" +msgstr "De Factuur Type komt niet overeen met de Factuur" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:272 +#, python-format +msgid "The Journal is not consistent with the account moves." +msgstr "De dagboek komt niet overeen met de boekingsregels." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:285 +#, python-format +msgid "" +"The Spread Template (Purchases) is not compatible with selected invoice type" +msgstr "" +"De Spreidingsjabloon (Inkoop) is not compatibel met geselecteerde factuur " +"type" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:280 +#, python-format +msgid "" +"The Spread Template (Sales) is not compatible with selected invoice type" +msgstr "" +"De Spreidingsjabloon (Verkoop) is not compatibel met geselecteerde factuur " +"type" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:65 +#, python-format +msgid "" +"This spread line is already linked to a journal entry! Please post or delete " +"it." +msgstr "" +"Deze spreidingsregel is al gekoppeld aan een boekingsregel! Graag boeken of " +"verwijderen." + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "This will delete the move. Are you sure ?" +msgstr "Hiermee wordt de boekingsregel verwijderd. Weet u het zeker?" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Total" +msgstr "Totaal" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__total_amount +msgid "Total Amount" +msgstr "Totaal Bedrag" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unavailable" +msgstr "Niet beschikbaar" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Undo spread" +msgstr "Spreiding ongedaan maken" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Unlink Invoice Line" +msgstr "Ontkoppel Facuur Regel" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unlinked" +msgstr "Ontkoppeld" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:459 +#, python-format +msgid "Unlinked '%s' (invoice line %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:454 +#, python-format +msgid "Unlinked invoice line '%s' (view %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unposted_amount +msgid "Unposted Amount" +msgstr "Ongeboekte Bedrag" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread +msgid "Unread Messages" +msgstr "Ongelezen berichten" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Unread Messages Counter" +msgstr "Aantal ongelezen berichten" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unspread_amount +msgid "Unspread Amount" +msgstr "Niet gespeid Bedrag" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__use_invoice_line_account +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#, fuzzy +#| msgid "Revenue account" +msgid "Use invoice line's account" +msgstr "Omzet grootboekrekening" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "" +"Use invoice line's account as Balance sheet / spread account.\n" +"In this case, user need to select expense/revenue account too." +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Bill" +msgstr "Leverancier Facuur" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Credit Note" +msgstr "Leverancier Creditnota" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "View Move" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website Messages" +msgstr "Website berichten" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website communication history" +msgstr "Website communicatie geschiedenis" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Year" +msgstr "Jaar" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "e.g. One year offices cleaning contract" +msgstr "bijv Één jaar kantoor schoonmaak contract" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "e.g. Template cleaning contract" +msgstr "e.g. Template schoonmaak contract" diff --git a/account_spread_cost_revenue/i18n/pt.po b/account_spread_cost_revenue/i18n/pt.po new file mode 100644 index 00000000..d0a9fc12 --- /dev/null +++ b/account_spread_cost_revenue/i18n/pt.po @@ -0,0 +1,1086 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * account_spread_cost_revenue +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 12.0\n" +"Report-Msgid-Bugs-To: \n" +"PO-Revision-Date: 2020-02-28 00:14+0000\n" +"Last-Translator: alvarorib \n" +"Language-Team: none\n" +"Language: pt\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: \n" +"Plural-Forms: nplurals=2; plural=n > 1;\n" +"X-Generator: Weblate 3.10\n" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "" +"\n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "invoice line.\n" +#| "
\n" +#| " \n" +#| " The Expense account in the vendor bill " +#| "line.
Usually the same account of the vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the invoice " +"line.\n" +"
\n" +" \n" +" The Expense account in the vendor bill " +"line.
Usually the same account of the vendor bill line.\n" +"
" +msgstr "" +"\n" +" A conta de Balanço usada para margem.
Esta conta é a contrapartida da conta na linha da fatura.\n" +"
\n" +" \n" +" A conta de Gastos na linha da fatura de " +"compra.
Habitualmente a mesma conta que a da linha da fatura de compra.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Revenue account in the invoice line." +#| "
Usually the same account of the invoice line.\n" +#| "
\n" +#| " \n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Balance Sheet account.
This is " +"the account in the invoice line.\n" +"
\n" +" \n" +" The Expense account used for the " +"spreading.
This account is the counterpart of the account of the vendor " +"bill line.\n" +"
" +msgstr "" +"\n" +" A conta de Rendimentos usada para a margem." +"
Habitualmente a mesma conta que a da linha da fatura.\n" +"
\n" +" \n" +" A conta de Balanço usada para a margem.
Esta conta é a contrapartida da conta da linha da fatura de compra.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Revenue account in the invoice line." +#| "
Usually the same account of the invoice line.\n" +#| "
\n" +#| " \n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Revenue account in the invoice " +"line.
Usually the same account of the invoice line.\n" +"
\n" +" \n" +" The Balance Sheet account used for the " +"spreading.
This account is the counterpart of the account in the vendor " +"bill line.\n" +"
" +msgstr "" +"\n" +" A conta de Rendimentos usada para a margem." +"
Habitualmente a mesma conta que a da linha da fatura.\n" +"
\n" +" \n" +" A conta de Balanço usada para a margem.
Esta conta é a contrapartida da conta da linha da fatura de compra.\n" +"
" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +#, fuzzy +#| msgid "" +#| "\n" +#| " The Balance Sheet account used for the " +#| "spreading.
This account is the counterpart of the account in the " +#| "invoice line.\n" +#| "
\n" +#| " \n" +#| " The Expense account in the vendor bill " +#| "line.
Usually the same account of the vendor bill line.\n" +#| "
" +msgid "" +"\n" +" The Revenue account used for the " +"spreading.
This account is the counterpart of the account of the invoice " +"line.\n" +"
\n" +" \n" +" The Balance Sheet account.
This is " +"the account in the vendor bill line.\n" +"
" +msgstr "" +"\n" +" A conta de Balanço usada para margem.
Esta conta é a contrapartida da conta na linha da fatura.\n" +"
\n" +" \n" +" A conta de Gastos na linha da fatura de " +"compra.
Habitualmente a mesma conta que a da linha da fatura de compra.\n" +"
" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Account Spread" +msgstr "Conta da Margem" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_invoice_line_link_wizard +msgid "Account Spread Invoice Line Link Wizard" +msgstr "Assistente de ligação da linha de fatura de conta margem" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_line +msgid "Account Spread Lines" +msgstr "Linhas da Conta Margem" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_spread_template +msgid "Account Spread Template" +msgstr "Modelo da Conta Margem" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "Action Needed" +msgstr "Ação Necessária" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__active +msgid "Active" +msgstr "Ativo" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__all_posted +msgid "All Posted" +msgstr "Tudo Publicado" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "Allow Spread Planning" +msgstr "Permitir Planear a Margem" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__amount +msgid "Amount" +msgstr "Montante" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__account_analytic_id +msgid "Analytic Account" +msgstr "Conta Analítica" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__analytic_tag_ids +msgid "Analytic Tags" +msgstr "Etiquetas Analíticas" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_search +msgid "Archived" +msgstr "Arquivado" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_attachment_count +msgid "Attachment Count" +msgstr "Contagem de Anexos" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__auto_archive +msgid "Auto-archive spread" +msgstr "Margem auto arquivada" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__move_line_auto_post +msgid "Auto-post lines" +msgstr "Linhas auto publicadas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "Auto-post spread lines" +msgstr "Linhas de margem auto publicadas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_account_id +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Balance sheet account / Spread account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Cancel" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:467 +#, python-format +msgid "Cannot delete spread(s) that are linked to an invoice line." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:472 +#, python-format +msgid "Cannot delete spread(s): there are posted Journal Entries." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:439 +#, python-format +msgid "Cannot unlink invoice lines if the invoice is validated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_res_company +msgid "Companies" +msgstr "Empresas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__company_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__company_id +msgid "Company" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_invoice_line_link_wizard +msgid "Confirm" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.server,name:account_spread_cost_revenue.ir_cron_spread_create_entries_ir_actions_server +#: model:ir.cron,cron_name:account_spread_cost_revenue.ir_cron_spread_create_entries +#: model:ir.cron,name:account_spread_cost_revenue.ir_cron_spread_create_entries +msgid "Cost/revenue Spread: Create Entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Create Move" +msgstr "Criar movimento" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:13 +#, python-format +msgid "Create from spread template" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:14 +#, python-format +msgid "Create new spread board" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_uid +msgid "Created by" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:36 +#, python-format +msgid "Created move(s) " +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__create_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__create_date +msgid "Created on" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__credit_account_id +msgid "Credit Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__currency_id +msgid "Currency" +msgstr "Moeda" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Customer" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Credit Note" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Customer Invoice" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__date +msgid "Date" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__debit_account_id +msgid "Debit Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Accounts" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_company_form +msgid "Default Spread Journals" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Define the number of spread lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Delete Move" +msgstr "Apagar Movimento" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:149 +#, python-format +msgid "Deleted move %s" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__name +msgid "Description" +msgstr "Descrição" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__allow_spread_planning +msgid "" +"Disable this option if you do not want to allow the spreading before the " +"invoice is validated." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_create_all_moves +msgid "Display Button All Moves" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_move_line_auto_post +msgid "Display Button Auto-post lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_recompute_buttons +msgid "Display Buttons Recompute" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__display_name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__display_name +msgid "Display Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__auto_archive +msgid "" +"Enable this option if you want the cron job to automatically archive the " +"spreads when all lines are posted." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_res_company__force_move_auto_post +msgid "" +"Enable this option if you want to post automatically the accounting moves of " +"all the spreads." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__estimated_amount +msgid "Estimated Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_account_id +msgid "Expense Spread Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_expense_journal_id +msgid "Expense Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Expense account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Expense/Revenue Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +msgid "Expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_follower_ids +msgid "Followers" +msgstr "Seguidores" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_channel_ids +msgid "Followers (Channels)" +msgstr "Seguidores (Canais)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_partner_ids +msgid "Followers (Partners)" +msgstr "Seguidores (Parceiros)" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__id +msgid "ID" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread +msgid "If checked new messages require your attention." +msgstr "Se selecionado novas mensagens necessitam da sua atenção." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction +msgid "If checked, new messages require your attention." +msgstr "Se selecionado, novas mensagens necessitam da sua atenção." + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "If checked, some messages have a delivery error." +msgstr "Se selecionado, algumas mensagens têm mensagem de erro." + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:453 +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_id +#, python-format +msgid "Invoice" +msgstr "Fatura" + +#. module: account_spread_cost_revenue +#: model:ir.model,name:account_spread_cost_revenue.model_account_invoice_line +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_line_id +msgid "Invoice Line" +msgstr "Linha de fatura" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_ids +msgid "Invoice Lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_id +msgid "Invoice Reference" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__invoice_type +msgid "Invoice Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "Invoice account as spread account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__invoice_line_id +msgid "Invoice line" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_credit_account_deprecated +msgid "Is Credit Account Deprecated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__is_debit_account_deprecated +msgid "Is Debit Account Deprecated" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_is_follower +msgid "Is Follower" +msgstr "É um Seguidor" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__journal_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_journal_id +msgid "Journal" +msgstr "Diário" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:130 +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__move_id +#, python-format +msgid "Journal Entry" +msgstr "Movimento de Diário" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line____last_update +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template____last_update +msgid "Last Modified on" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_uid +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_uid +msgid "Last Updated by" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__write_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__write_date +msgid "Last Updated on" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:60 +#, python-format +msgid "Link Invoice Line with Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:20 +#, python-format +msgid "Link to existing spread board" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Linked" +msgstr "" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:33 +#, python-format +msgid "Linked to spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_main_attachment_id +msgid "Main Attachment" +msgstr "Anexo Principal" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error +msgid "Message Delivery error" +msgstr "Erro de Mensagem de Envio" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_ids +msgid "Messages" +msgstr "Mensagens" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Month" +msgstr "Mês" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__name +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__name +msgid "Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:157 +#, python-format +msgid "New Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#. openerp-web +#: code:addons/account_spread_cost_revenue/static/src/js/account_spread.js:35 +#, python-format +msgid "Not linked to spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of Actions" +msgstr "Número de Ações" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_number +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_number +msgid "Number of Repetitions" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of error" +msgstr "Número de erros" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_needaction_counter +msgid "Number of messages which requires an action" +msgstr "Número de mensagens que requerem atenção" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_has_error_counter +msgid "Number of messages with delivery error" +msgstr "Número de mensagens com erro de envio" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Number of unread messages" +msgstr "Número de mensagens não lidas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__exp_rev_account_id +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__exp_rev_account_id +msgid "Optional account to overwrite the existing expense/revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__period_type +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__period_type +msgid "Period length for the entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__posted_amount +msgid "Posted Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Quarter" +msgstr "Trimestre" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate entire spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Recalculate unposted lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Reconciled entries" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_account_id +msgid "Revenue Spread Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_res_company__default_spread_revenue_journal_id +msgid "Revenue Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Revenue account" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:458 +#, python-format +msgid "Spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_action_type +msgid "Spread Action Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_account_id +msgid "Spread Balance Sheet Account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_line__spread_id +msgid "Spread Board" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread Board Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_invoice_line__spread_check +msgid "Spread Check" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_form +msgid "Spread Costs/Revenues" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_invoice_line.py:40 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:134 +#: code:addons/account_spread_cost_revenue/wizards/account_spread_invoice_line_link_wizard.py:213 +#, python-format +msgid "Spread Details" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_journal_id +msgid "Spread Journal" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__line_ids +msgid "Spread Lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__template_id +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__template_id +msgid "Spread Template" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "Spread Template Name" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.actions.act_window,name:account_spread_cost_revenue.action_account_spread_template_form +#: model:ir.ui.menu,name:account_spread_cost_revenue.menu_action_account_spread_template_form +msgid "Spread Templates" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__spread_type +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__spread_type +msgid "Spread Type" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Spread lines" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:378 +#, python-format +msgid "Spread table '%s' created." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__spread_date +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_template__start_date +msgid "Start Date" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,spread_type:0 +#: selection:account.spread.invoice.line.link.wizard,spread_type:0 +#: selection:account.spread.template,spread_type:0 +msgid "Supplier" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:264 +#, python-format +msgid "The Invoice Type does not correspond to the Invoice" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:272 +#, python-format +msgid "The Journal is not consistent with the account moves." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:285 +#, python-format +msgid "" +"The Spread Template (Purchases) is not compatible with selected invoice type" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:280 +#, python-format +msgid "" +"The Spread Template (Sales) is not compatible with selected invoice type" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread_line.py:65 +#, python-format +msgid "" +"This spread line is already linked to a journal entry! Please post or delete " +"it." +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "This will delete the move. Are you sure ?" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Total" +msgstr "Total" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__total_amount +msgid "Total Amount" +msgstr "Valor Total" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unavailable" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Undo spread" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "Unlink Invoice Line" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.invoice.line,spread_check:0 +msgid "Unlinked" +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:459 +#, python-format +msgid "Unlinked '%s' (invoice line %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: code:addons/account_spread_cost_revenue/models/account_spread.py:454 +#, python-format +msgid "Unlinked invoice line '%s' (view %s)." +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unposted_amount +msgid "Unposted Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread +msgid "Unread Messages" +msgstr "Mensagens Não lidas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__message_unread_counter +msgid "Unread Messages Counter" +msgstr "Contador de Mensagens Não Lidas" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__unspread_amount +msgid "Unspread Amount" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__use_invoice_line_account +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +msgid "Use invoice line's account" +msgstr "" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_invoice_line_link_wizard__use_invoice_line_account +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread_template__use_invoice_line_account +msgid "" +"Use invoice line's account as Balance sheet / spread account.\n" +"In this case, user need to select expense/revenue account too." +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Bill" +msgstr "" + +#. module: account_spread_cost_revenue +#: selection:account.spread,invoice_type:0 +#: selection:account.spread.invoice.line.link.wizard,invoice_type:0 +msgid "Vendor Credit Note" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "View Move" +msgstr "Vista Movimento" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,field_description:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website Messages" +msgstr "Mensagens de Website" + +#. module: account_spread_cost_revenue +#: model:ir.model.fields,help:account_spread_cost_revenue.field_account_spread__website_message_ids +msgid "Website communication history" +msgstr "História de Comunicações do Website" + +#. module: account_spread_cost_revenue +#: selection:account.spread,period_type:0 +#: selection:account.spread.template,period_type:0 +msgid "Year" +msgstr "Ano" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread +msgid "e.g. One year offices cleaning contract" +msgstr "" + +#. module: account_spread_cost_revenue +#: model_terms:ir.ui.view,arch_db:account_spread_cost_revenue.view_account_spread_template +msgid "e.g. Template cleaning contract" +msgstr "" diff --git a/account_spread_cost_revenue/models/__init__.py b/account_spread_cost_revenue/models/__init__.py new file mode 100644 index 00000000..c37541a4 --- /dev/null +++ b/account_spread_cost_revenue/models/__init__.py @@ -0,0 +1,8 @@ +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from . import account_move +from . import account_move_line +from . import account_spread_line +from . import account_spread +from . import account_spread_template +from . import res_company diff --git a/account_spread_cost_revenue/models/account_move.py b/account_spread_cost_revenue/models/account_move.py new file mode 100644 index 00000000..511c0a80 --- /dev/null +++ b/account_spread_cost_revenue/models/account_move.py @@ -0,0 +1,39 @@ +# Copyright 2016-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import api, models + + +class AccountMove(models.Model): + _inherit = "account.move" + + def action_post(self): + """Invoked when validating the invoices.""" + self.mapped("invoice_line_ids").create_auto_spread() + res = super().action_post() + spreads = self.mapped("invoice_line_ids.spread_id") + spreads.compute_spread_board() + # On posting of spread moves. Find their related spreads to reconcile + move_spreads = self.env["account.spread"].search( + [("line_ids.move_id", "in", self.ids)] + ) + spreads += move_spreads + spreads.reconcile_spread_moves() + return res + + def button_cancel(self): + """Cancel the spread lines and their related moves when + the invoice is canceled.""" + spread_lines = self.mapped("invoice_line_ids.spread_id.line_ids") + moves = spread_lines.mapped("move_id") + moves.line_ids.remove_move_reconcile() + moves.filtered(lambda move: move.state == "posted").button_draft() + moves.with_context(force_delete=True).unlink() + spread_lines.unlink() + res = super().button_cancel() + return res + + @api.constrains("name", "journal_id", "state") + def _check_unique_sequence_number(self): + if not self.env.context.get("skip_unique_sequence_number"): + return super()._check_unique_sequence_number() diff --git a/account_spread_cost_revenue/models/account_move_line.py b/account_spread_cost_revenue/models/account_move_line.py new file mode 100644 index 00000000..2091927a --- /dev/null +++ b/account_spread_cost_revenue/models/account_move_line.py @@ -0,0 +1,177 @@ +# Copyright 2016-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import _, api, fields, models +from odoo.exceptions import UserError, ValidationError + + +class AccountMoveLine(models.Model): + _inherit = "account.move.line" + + spread_id = fields.Many2one("account.spread", string="Spread Board", copy=False) + spread_check = fields.Selection( + [ + ("linked", "Linked"), + ("unlinked", "Unlinked"), + ("unavailable", "Unavailable"), + ], + compute="_compute_spread_check", + ) + + @api.depends("spread_id", "move_id.state") + def _compute_spread_check(self): + for line in self: + if line.spread_id: + line.spread_check = "linked" + elif line.move_id.state == "draft": + line.spread_check = "unlinked" + else: + line.spread_check = "unavailable" + + def spread_details(self): + """Button on the invoice lines tree view of the invoice + form to show the spread form view.""" + if not self: + # In case the widget clicked before the creation of the line + return + + if self.spread_id: + return { + "name": _("Spread Details"), + "view_mode": "form", + "res_model": "account.spread", + "type": "ir.actions.act_window", + "target": "current", + "readonly": False, + "res_id": self.spread_id.id, + } + + # In case no spread board is linked to the invoice line + # open the wizard to link them + ctx = dict( + self.env.context, + default_invoice_line_id=self.id, + default_company_id=self.move_id.company_id.id, + allow_spread_planning=self.move_id.company_id.allow_spread_planning, + ) + return { + "name": _("Link Invoice Line with Spread Board"), + "view_mode": "form", + "res_model": "account.spread.invoice.line.link.wizard", + "type": "ir.actions.act_window", + "target": "new", + "context": ctx, + } + + @api.constrains("spread_id", "account_id") + def _check_spread_account_balance_sheet(self): + for line in self: + if not line.spread_id: + pass + elif line.move_id.move_type in ("out_invoice", "in_refund"): + if line.account_id != line.spread_id.debit_account_id: + raise ValidationError( + _( + "The account of the invoice line does not correspond " + "to the Balance Sheet (debit account) of the spread" + ) + ) + elif line.move_id.move_type in ("in_invoice", "out_refund"): + if line.account_id != line.spread_id.credit_account_id: + raise ValidationError( + _( + "The account of the invoice line does not correspond " + "to the Balance Sheet (credit account) of the spread" + ) + ) + + def write(self, vals): + if vals.get("spread_id"): + spread = self.env["account.spread"].browse(vals.get("spread_id")) + if spread.invoice_type in ["out_invoice", "in_refund"]: + vals["account_id"] = spread.debit_account_id.id + else: + vals["account_id"] = spread.credit_account_id.id + return super().write(vals) + + def _check_spread_reconcile_validity(self): + # Improve error messages of standard Odoo + reconciled_lines = self.filtered(lambda l: l.reconciled) + msg_line = _( + "Move line: %(line_id)s (%(line_name)s), account code: %(account_code)s\n" + ) + if reconciled_lines: + msg = _("Cannot reconcile entries that are already reconciled:\n") + for line in reconciled_lines: + msg += msg_line % { + "line_id": line.id, + "line_name": line.name, + "account_code": line.account_id.code, + } + raise ValidationError(msg) + if len(self.mapped("account_id").ids) > 1: + msg = _("Some entries are not from the same account:\n") + for line in self: + msg += msg_line % { + "line_id": line.id, + "line_name": line.name, + "account_code": line.account_id.code, + } + raise ValidationError(msg) + + def create_auto_spread(self): + """Create auto spread table for each invoice line, when needed""" + + def _filter_line(aline, iline): + """Find matching template auto line with invoice line""" + if aline.product_id and iline.product_id != aline.product_id: + return False + if aline.account_id and iline.account_id != aline.account_id: + return False + if ( + aline.analytic_distribution + and iline.analytic_distribution != aline.analytic_distribution + ): + return False + return True + + # Skip create new template when create move on spread lines + if self.env.context.get("skip_create_template"): + return + + for line in self: + if line.spread_check == "linked": + continue + spread_type = ( + "sale" + if line.move_id.move_type in ["out_invoice", "out_refund"] + else "purchase" + ) + spread_auto = self.env["account.spread.template.auto"].search( + [ + ("template_id.auto_spread", "=", True), + ("template_id.spread_type", "=", spread_type), + ] + ) + matched = spread_auto.filtered(lambda a, i=line: _filter_line(a, i)) + template = matched.mapped("template_id") + if not template: + continue + elif len(template) > 1: + raise UserError( + _( + "Too many auto spread templates (%(len_template)s) matched with the " + "invoice line, %(line_name)s" + ) + % {"len_template": len(template), "line_name": line.display_name} + ) + # Found auto spread template for this invoice line, create it + wizard = self.env["account.spread.invoice.line.link.wizard"].new( + { + "invoice_line_id": line.id, + "company_id": line.company_id.id, + "spread_action_type": "template", + "template_id": template.id, + } + ) + wizard.confirm() diff --git a/account_spread_cost_revenue/models/account_spread.py b/account_spread_cost_revenue/models/account_spread.py new file mode 100644 index 00000000..5ed039c1 --- /dev/null +++ b/account_spread_cost_revenue/models/account_spread.py @@ -0,0 +1,614 @@ +# Copyright 2018-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +import calendar +import time + +from dateutil.relativedelta import relativedelta + +from odoo import _, api, fields, models +from odoo.exceptions import UserError, ValidationError +from odoo.tools import float_is_zero + + +class AccountSpread(models.Model): + _name = "account.spread" + _description = "Account Spread" + _inherit = ["mail.thread", "analytic.mixin"] + _check_company_auto = True + + name = fields.Char(required=True) + template_id = fields.Many2one("account.spread.template", string="Spread Template") + invoice_type = fields.Selection( + [ + ("out_invoice", "Customer Invoice"), + ("in_invoice", "Vendor Bill"), + ("out_refund", "Customer Credit Note"), + ("in_refund", "Vendor Credit Note"), + ], + required=True, + ) + spread_type = fields.Selection( + [("sale", "Customer"), ("purchase", "Supplier")], + compute="_compute_spread_type", + required=True, + ) + period_number = fields.Integer( + string="Number of Repetitions", + default=12, + help="Define the number of spread lines", + required=True, + ) + period_type = fields.Selection( + [("month", "Month"), ("quarter", "Quarter"), ("year", "Year")], + default="month", + help="Period length for the entries", + required=True, + ) + days_calc = fields.Boolean( + string="Calculate by days", + default=False, + help="Use number of days to calculate amount", + ) + use_invoice_line_account = fields.Boolean() + credit_account_id = fields.Many2one( + "account.account", + compute="_compute_credit_account_id", + readonly=False, + store=True, + required=True, + ) + debit_account_id = fields.Many2one( + "account.account", + compute="_compute_debit_account_id", + readonly=False, + store=True, + required=True, + ) + is_credit_account_deprecated = fields.Boolean( + compute="_compute_deprecated_accounts" + ) + is_debit_account_deprecated = fields.Boolean(compute="_compute_deprecated_accounts") + unspread_amount = fields.Float( + digits="Account", + compute="_compute_amounts", + ) + unposted_amount = fields.Float( + digits="Account", + compute="_compute_amounts", + ) + posted_amount = fields.Float( + digits="Account", + compute="_compute_amounts", + ) + total_amount = fields.Float( + digits="Account", + compute="_compute_amounts", + ) + all_posted = fields.Boolean(compute="_compute_all_posted", store=True) + line_ids = fields.One2many( + "account.spread.line", "spread_id", string="Spread Lines" + ) + spread_date = fields.Date( + string="Start Date", default=time.strftime("%Y-01-01"), required=True + ) + journal_id = fields.Many2one( + "account.journal", + compute="_compute_journal_id", + readonly=False, + precompute=True, + store=True, + required=True, + check_company=True, + domain="[('id', 'in', suitable_journal_ids)]", + ) + suitable_journal_ids = fields.Many2many( + "account.journal", + compute="_compute_suitable_journal_ids", + ) + invoice_line_ids = fields.One2many( + "account.move.line", "spread_id", copy=False, string="Invoice Lines" + ) + invoice_line_id = fields.Many2one( + "account.move.line", + string="Invoice line", + compute="_compute_invoice_line", + inverse="_inverse_invoice_line", + store=True, + ) + invoice_id = fields.Many2one( + related="invoice_line_id.move_id", + readonly=True, + store=True, + ) + estimated_amount = fields.Float(digits="Account") + company_id = fields.Many2one( + "res.company", default=lambda self: self.env.company, required=True + ) + currency_id = fields.Many2one( + "res.currency", + required=True, + default=lambda self: self.env.company.currency_id.id, + ) + move_line_auto_post = fields.Boolean("Auto-post lines", default=True) + display_create_all_moves = fields.Boolean( + compute="_compute_display_create_all_moves", + ) + display_recompute_buttons = fields.Boolean( + compute="_compute_display_recompute_buttons", + ) + display_move_line_auto_post = fields.Boolean( + compute="_compute_display_move_line_auto_post", + string="Display Button Auto-post lines", + ) + active = fields.Boolean(default=True) + + @api.model + def default_journal(self, company_id): + domain = [("type", "=", "general"), ("company_id", "=", company_id)] + return self.env["account.journal"].search(domain, limit=1) + + @api.model + def default_get(self, fields): + res = super().default_get(fields) + if "journal_id" not in res: + company_id = res.get("company_id", self.env.company.id) + default_journal = self.default_journal(company_id) + if default_journal: + res["journal_id"] = default_journal.id + return res + + @api.depends("company_id") + def _compute_suitable_journal_ids(self): + for spread in self: + domain = [("company_id", "=", spread.company_id.id)] + spread.suitable_journal_ids = self.env["account.journal"].search(domain) + + @api.depends("invoice_type") + def _compute_spread_type(self): + for spread in self: + if spread.invoice_type in ["out_invoice", "out_refund"]: + spread.spread_type = "sale" + else: + spread.spread_type = "purchase" + + @api.depends("invoice_line_ids", "invoice_line_ids.move_id") + def _compute_invoice_line(self): + for spread in self: + invoice_lines = spread.invoice_line_ids + spread.invoice_line_id = invoice_lines and invoice_lines[0] or False + + def _inverse_invoice_line(self): + for spread in self: + invoice_line = spread.invoice_line_id + spread.write({"invoice_line_ids": [(6, 0, [invoice_line.id])]}) + + @api.depends( + "estimated_amount", + "currency_id", + "company_id", + "invoice_line_id.price_subtotal", + "invoice_line_id.currency_id", + "line_ids.amount", + "line_ids.move_id.state", + ) + def _compute_amounts(self): + for spread in self: + lines_move = spread.line_ids.filtered(lambda l: l.move_id) + moves_amount = sum(spread_line.amount for spread_line in lines_move) + lines_posted = lines_move.filtered(lambda l: l.move_id.state == "posted") + posted_amount = sum(spread_line.amount for spread_line in lines_posted) + total_amount = spread.estimated_amount + if spread.invoice_line_id: + total_amount = spread.invoice_line_id.currency_id._convert( + spread.invoice_line_id.balance, + spread.currency_id, + spread.company_id, + spread.invoice_id.date, + ) + + spread.unspread_amount = total_amount - moves_amount + spread.unposted_amount = total_amount - posted_amount + spread.posted_amount = posted_amount + spread.total_amount = total_amount + + @api.depends("unposted_amount") + def _compute_all_posted(self): + for spread in self: + rounding = self.currency_id.rounding + unposted = spread.unposted_amount + spread.all_posted = float_is_zero(unposted, precision_rounding=rounding) + + def _compute_display_create_all_moves(self): + for spread in self: + any_not_move = any(not line.move_id for line in spread.line_ids) + spread.display_create_all_moves = any_not_move + + def _compute_display_recompute_buttons(self): + for spread in self: + spread.display_recompute_buttons = True + if not spread.company_id.allow_spread_planning: + if spread.invoice_id.state == "draft": + spread.display_recompute_buttons = False + + @api.depends("company_id.force_move_auto_post") + def _compute_display_move_line_auto_post(self): + for spread in self: + auto_post = spread.company_id.force_move_auto_post + spread.display_move_line_auto_post = not auto_post + + def _get_spread_entry_name(self, seq): + """Use this method to customise the name of the accounting entry.""" + self.ensure_one() + return (self.name or "") + "/" + str(seq) + + @api.onchange("template_id") + def onchange_template(self): + if self.template_id: + if self.template_id.spread_type == "sale": + if self.invoice_type in ["in_invoice", "in_refund"]: + self.invoice_type = "out_invoice" + else: + if self.invoice_type in ["out_invoice", "out_refund"]: + self.invoice_type = "in_invoice" + if self.template_id.period_number: + self.period_number = self.template_id.period_number + if self.template_id.period_type: + self.period_type = self.template_id.period_type + if self.template_id.start_date: + self.spread_date = self.template_id.start_date + if self.template_id.analytic_distribution: + self.analytic_distribution = self.template_id.analytic_distribution + self.days_calc = self.template_id.days_calc + + @api.depends("invoice_type", "company_id") + def _compute_journal_id(self): + if not self.env.context.get("default_journal_id"): + for spread in self: + journal = spread.company_id.default_spread_expense_journal_id + if spread.invoice_type in ("out_invoice", "in_refund"): + journal = spread.company_id.default_spread_revenue_journal_id + if not journal: + journal = self.default_journal(spread.company_id.id) + spread.journal_id = journal + + @api.depends("invoice_type", "company_id") + def _compute_debit_account_id(self): + if not self.env.context.get("default_debit_account_id"): + invoice_types = ("out_invoice", "in_refund") + for spread in self.filtered(lambda s: s.invoice_type in invoice_types): + debit_account = spread.company_id.default_spread_revenue_account_id + spread.debit_account_id = debit_account + + @api.depends("invoice_type", "company_id") + def _compute_credit_account_id(self): + if not self.env.context.get("default_credit_account_id"): + invoice_types = ("in_invoice", "out_refund") + for spread in self.filtered(lambda s: s.invoice_type in invoice_types): + credit_account = spread.company_id.default_spread_expense_account_id + spread.credit_account_id = credit_account + + @api.constrains("invoice_id", "invoice_type") + def _check_invoice_type(self): + if self.filtered( + lambda s: s.invoice_id and s.invoice_type != s.invoice_id.move_type + ): + raise ValidationError( + _("The Invoice Type does not correspond to the Invoice") + ) + + @api.constrains("journal_id") + def _check_journal(self): + for spread in self: + moves = spread.mapped("line_ids.move_id").filtered("journal_id") + if any(move.journal_id != spread.journal_id for move in moves): + err_msg = _("The Journal is not consistent with the account moves.") + raise ValidationError(err_msg) + + @api.constrains("template_id", "invoice_type") + def _check_template_invoice_type(self): + for spread in self.filtered(lambda s: s.template_id.spread_type == "sale"): + if spread.invoice_type in ["in_invoice", "in_refund"]: + err_msg = _( + "The Spread Template (Sales) is not compatible " + "with selected invoice type" + ) + raise ValidationError(err_msg) + for spread in self.filtered(lambda s: s.template_id.spread_type == "purchase"): + if spread.invoice_type in ["out_invoice", "out_refund"]: + err_msg = _( + "The Spread Template (Purchases) is not compatible " + "with selected invoice type" + ) + raise ValidationError(err_msg) + + def _get_spread_period_duration(self): + """Converts the selected period_type to number of months.""" + self.ensure_one() + if self.period_type == "year": + return 12 + elif self.period_type == "quarter": + return 3 + return 1 + + def _init_line_date(self, posted_line_ids): + """Calculates the initial spread date. This method + is used by "def _compute_spread_board()" method. + """ + self.ensure_one() + if posted_line_ids: + # if we already have some previous validated entries, + # starting date is last entry + method period + last_date = posted_line_ids[-1].date + months = self._get_spread_period_duration() + spread_date = last_date + relativedelta(months=months) + else: + spread_date = self.spread_date + return spread_date + + def _next_line_date(self, month_day, date): + """Calculates the next spread date. This method + is used by "def _compute_spread_board()" method. + """ + self.ensure_one() + months = self._get_spread_period_duration() + date = date + relativedelta(months=months) + # get the last day of the month + if month_day > 28: + max_day_in_month = calendar.monthrange(date.year, date.month)[1] + date = date.replace(day=min(max_day_in_month, month_day)) + return date + + def _compute_spread_board(self): + """Creates the spread lines. This method is highly inspired + from method compute_depreciation_board() present in standard + Odoo 11.0 "account_asset" module, developed by Odoo SA. + """ + self.ensure_one() + + posted_line_ids = self.line_ids.filtered( + lambda x: x.move_id.state == "posted" + ).sorted(key=lambda l: l.date) + unposted_line_ids = self.line_ids.filtered( + lambda x: not x.move_id.state == "posted" + ) + + # Remove old unposted spread lines. + commands = [(2, line_id.id, False) for line_id in unposted_line_ids] + + if self.unposted_amount != 0.0: + unposted_amount = self.unposted_amount + + spread_date = self._init_line_date(posted_line_ids) + + month_day = spread_date.day + number_of_periods = self._get_number_of_periods(month_day) + + for x in range(len(posted_line_ids), number_of_periods): + sequence = x + 1 + date = self._get_last_day_of_month(spread_date) + amount = self._compute_board_amount( + sequence, unposted_amount, number_of_periods, date + ) + amount = self.currency_id.round(amount) + rounding = self.currency_id.rounding + if float_is_zero(amount, precision_rounding=rounding): + continue + unposted_amount -= amount + vals = { + "amount": amount, + "spread_id": self.id, + "name": self._get_spread_entry_name(sequence), + "date": date, + } + commands.append((0, False, vals)) + + spread_date = self._next_line_date(month_day, spread_date) + + self.write({"line_ids": commands}) + invoice_type_selection = dict( + self.fields_get(allfields=["invoice_type"])["invoice_type"]["selection"] + )[self.invoice_type] + msg_body = _("Spread table '%s' created.") % invoice_type_selection + self.message_post(body=msg_body) + + def _get_number_of_periods(self, month_day): + """Calculates the number of spread lines.""" + self.ensure_one() + return self.period_number + 1 if month_day != 1 else self.period_number + + @staticmethod + def _get_first_day_of_month(spread_date): + return spread_date + relativedelta(day=1) + + @staticmethod + def _get_last_day_of_month(spread_date): + return spread_date + relativedelta(day=31) + + def _get_spread_start_date(self, period_type, spread_end_date): + self.ensure_one() + spread_start_date = spread_end_date + relativedelta(days=1) + if period_type == "month": + spread_start_date = spread_end_date + relativedelta(day=1) + elif period_type == "quarter": + spread_start_date = spread_start_date - relativedelta(months=3) + elif period_type == "year": + spread_start_date = spread_start_date - relativedelta(years=1) + spread_start_date = self._get_first_day_of_month(spread_start_date) + spread_start_date = max(spread_start_date, self.spread_date) + return spread_start_date + + def _get_spread_end_date(self, period_type, period_number, spread_start_date): + self.ensure_one() + spread_end_date = spread_start_date + number_of_periods = ( + period_number if spread_start_date.day != 1 else period_number - 1 + ) + if period_type == "month": + spread_end_date = spread_start_date + relativedelta( + months=number_of_periods + ) + elif period_type == "quarter": + months = number_of_periods * 3 + spread_end_date = spread_start_date + relativedelta(months=months) + elif period_type == "year": + spread_end_date = spread_start_date + relativedelta(years=number_of_periods) + # calculate by days and not first day of month should compute residual day only + if self.days_calc and spread_end_date.day != 1: + spread_end_date = spread_end_date - relativedelta(days=1) + else: + spread_end_date = self._get_last_day_of_month(spread_end_date) + return spread_end_date + + def _get_amount_per_day(self, amount): + self.ensure_one() + spread_start_date = self.spread_date + spread_end_date = self._get_spread_end_date( + self.period_type, self.period_number, spread_start_date + ) + number_of_days = (spread_end_date - spread_start_date).days + 1 + return amount / number_of_days + + def _compute_board_amount( + self, sequence, amount, number_of_periods, spread_end_date + ): + """Calculates the amount for the spread lines.""" + self.ensure_one() + amount_to_spread = self.total_amount + period = self.period_number + if sequence != number_of_periods: + amount = amount_to_spread / period + if sequence == 1: + date = self.spread_date + month_days = calendar.monthrange(date.year, date.month)[1] + days = month_days - date.day + 1 + amount = (amount_to_spread / period) / month_days * days + if self.days_calc: + spread_start_date = self._get_spread_start_date( + self.period_type, spread_end_date + ) + days = (spread_end_date - spread_start_date).days + 1 + amount = self._get_amount_per_day(amount_to_spread) * days + return amount + + def compute_spread_board(self): + """Checks whether the spread lines should be calculated. + In case checks pass, invoke "def _compute_spread_board()" method. + """ + for spread in self.filtered(lambda s: s.total_amount): + spread._compute_spread_board() + + def action_recalculate_spread(self): + """Recalculate spread""" + self.ensure_one() + spread_lines = self.mapped("line_ids").filtered("move_id") + spread_lines.unlink_move() + self.compute_spread_board() + self.env["account.spread.line"]._create_entries() + + def action_undo_spread(self): + """Undo spreading: Remove all created moves""" + self.ensure_one() + self.mapped("line_ids").filtered("move_id").unlink_move() + self.mapped("line_ids").unlink() + + def action_unlink_invoice_line(self): + """Unlink the invoice line from the spread board""" + self.ensure_one() + if self.invoice_id.state != "draft": + msg = _("Cannot unlink invoice lines if the invoice is validated") + raise UserError(msg) + self._action_unlink_invoice_line() + + def _action_unlink_invoice_line(self): + self.mapped("line_ids.move_id.line_ids").remove_move_reconcile() + self._message_post_unlink_invoice_line() + self.write({"invoice_line_ids": [(5, 0, 0)]}) + + def _message_post_unlink_invoice_line(self): + for spread in self: + inv_link = ( + "%s" % (spread.invoice_id.id, _("Invoice")) + ) + msg_body = _( + "Unlinked invoice line '%(spread_line_name)s' (view %(inv_link)s)." + ) % { + "spread_line_name": spread.invoice_line_id.name, + "inv_link": inv_link, + } + spread.message_post(body=msg_body) + spread_link = ( + "%s" % (spread.id, _("Spread")) + ) + msg_body = _("Unlinked '%(spread_link)s' (invoice line %(inv_line)s).") % { + "spread_link": spread_link, + "inv_line": spread.invoice_line_id.name, + } + spread.invoice_id.message_post(body=msg_body) + + def unlink(self): + if self.filtered(lambda s: s.invoice_line_id): + err_msg = _("Cannot delete spread(s) that are linked to an invoice line.") + raise UserError(err_msg) + if self.mapped("line_ids.move_id").filtered(lambda m: m.state == "posted"): + err_msg = _("Cannot delete spread(s): there are posted Journal Entries.") + raise ValidationError(err_msg) + return super().unlink() + + def reconcile_spread_moves(self): + for spread in self: + spread._reconcile_spread_moves() + + def _reconcile_spread_moves(self, created_moves=False): + """Reconcile spread moves if possible""" + self.ensure_one() + + spread_mls = self.line_ids.mapped("move_id.line_ids") + if created_moves: + spread_mls |= created_moves.mapped("line_ids") + + account = self.invoice_line_id.account_id + mls_to_reconcile = spread_mls.filtered(lambda l: l.account_id == account) + + if mls_to_reconcile: + do_reconcile = mls_to_reconcile + self.invoice_line_id + do_reconcile.remove_move_reconcile() + for line in do_reconcile: + line.reconciled = False + # ensure to reconcile only posted items + do_reconcile = do_reconcile.filtered(lambda l: l.move_id.state == "posted") + do_reconcile._check_spread_reconcile_validity() + do_reconcile.reconcile() + + def create_all_moves(self): + for line in self.mapped("line_ids").filtered(lambda l: not l.move_id): + line.create_move() + + def _post_spread_moves(self, moves): + self.ensure_one() + moves = moves.filtered(lambda l: l.state != "posted") + if not moves: + return + ctx = dict(self.env.context, skip_unique_sequence_number=True) + if self.company_id.force_move_auto_post or self.move_line_auto_post: + moves.with_context(**ctx).action_post() + + @api.depends("debit_account_id.deprecated", "credit_account_id.deprecated") + def _compute_deprecated_accounts(self): + for spread in self: + spread.is_debit_account_deprecated = spread.debit_account_id.deprecated + spread.is_credit_account_deprecated = spread.credit_account_id.deprecated + + def open_posted_view(self): + action_name = "account_spread_cost_revenue.action_account_moves_all_spread" + action = self.env["ir.actions.act_window"]._for_xml_id(action_name) + action["domain"] = [("id", "in", [])] + spread_mls = self.line_ids.mapped("move_id.line_ids") + if self.env.context.get("show_reconciled_only"): + spread_mls = spread_mls.filtered(lambda m: m.reconciled) + if spread_mls: + domain = [("id", "in", spread_mls.ids + [self.invoice_line_id.id])] + action["domain"] = domain + return action diff --git a/account_spread_cost_revenue/models/account_spread_line.py b/account_spread_cost_revenue/models/account_spread_line.py new file mode 100644 index 00000000..e8d9bca1 --- /dev/null +++ b/account_spread_cost_revenue/models/account_spread_line.py @@ -0,0 +1,173 @@ +# Copyright 2016-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import _, api, fields, models +from odoo.exceptions import UserError + + +class AccountInvoiceSpreadLine(models.Model): + _name = "account.spread.line" + _description = "Account Spread Lines" + _order = "date" + + name = fields.Char("Description", readonly=True) + amount = fields.Float(digits="Account", required=True) + date = fields.Date(required=True) + spread_id = fields.Many2one("account.spread", ondelete="cascade") + move_id = fields.Many2one("account.move", string="Journal Entry", readonly=True) + + def create_and_reconcile_moves(self): + grouped_lines = {} + for spread_line in self: + spread = spread_line.spread_id + spread_line_list = grouped_lines.get( + spread, self.env["account.spread.line"] + ) + grouped_lines.update({spread: spread_line_list + spread_line}) + for spread in grouped_lines: + created_moves = grouped_lines[spread]._create_moves() + + if created_moves: + post_msg = _("Created move(s) ") + post_msg += ", ".join( + "%s" % (move.id, move.name) + for move in created_moves + ) + spread.message_post(body=post_msg) + spread._post_spread_moves(created_moves) + + def create_move(self): + """Button to manually create a move from a spread line entry.""" + self.ensure_one() + self.with_context( + skip_create_template=True, + ).create_and_reconcile_moves() + + def _create_moves(self): + if self.filtered(lambda l: l.move_id): + raise UserError( + _( + "This spread line is already linked to a " + "journal entry! Please post or delete it." + ) + ) + + created_moves = self.env["account.move"] + for line in self: + move_vals = line._prepare_move() + move = self.env["account.move"].create(move_vals) + line.move_id = move + created_moves += move + return created_moves + + def _prepare_move(self): + self.ensure_one() + + spread_date = self.env.context.get("spread_date") or self.date + spread = self.spread_id + analytic_distribution = spread.analytic_distribution + + company_currency = spread.company_id.currency_id + current_currency = spread.currency_id + amount = current_currency._convert( + self.amount, company_currency, spread.company_id, spread_date + ) + + debit_credit = spread.invoice_type in ["in_invoice", "out_refund"] + + line_ids = [ + ( + 0, + 0, + { + "name": spread.name, + "account_id": spread.debit_account_id.id + if debit_credit + else spread.credit_account_id.id, + "debit": amount if amount > 0.0 else 0.0, + "credit": -amount if amount < 0.0 else 0.0, + "partner_id": self.spread_id.invoice_id.partner_id.id, + "journal_id": self.spread_id.journal_id.id, + "analytic_distribution": analytic_distribution, + "date": self.date, + }, + ), + ( + 0, + 0, + { + "name": spread.name, + "account_id": spread.credit_account_id.id + if debit_credit + else spread.debit_account_id.id, + "credit": amount if amount > 0.0 else 0.0, + "debit": -amount if amount < 0.0 else 0.0, + "partner_id": self.spread_id.invoice_id.partner_id.id, + "journal_id": self.spread_id.journal_id.id, + "analytic_distribution": analytic_distribution, + "date": self.date, + }, + ), + ] + + return { + "name": False, + "ref": self.name, + "date": spread_date, + "invoice_date": spread_date, + "journal_id": spread.journal_id.id, + "line_ids": line_ids, + "company_id": spread.company_id.id, + "partner_id": spread.invoice_id.partner_id.id, + } + + def open_move(self): + """Used by a button to manually view a move from a spread line entry.""" + self.ensure_one() + return { + "name": _("Journal Entry"), + "view_mode": "form", + "res_model": "account.move", + "view_id": False, + "type": "ir.actions.act_window", + "res_id": self.move_id.id, + } + + def unlink_move(self): + """Used by a button to manually unlink a move from a spread line entry.""" + for line in self: + move = line.move_id + if move.state == "posted": + move.button_cancel() + move.line_ids.remove_move_reconcile() + post_msg = _("Deleted move %s") % line.move_id.id + move.with_context(force_delete=True).unlink() + line.move_id = False + line.spread_id.message_post(body=post_msg) + + @api.model + def _create_entries(self): + """Find spread line entries where date is in the past and + create moves for them. Method also called by the cron job. + """ + lines = self.search( + [("date", "<=", fields.Date.today()), ("move_id", "=", False)] + ) + lines.create_and_reconcile_moves() + + unposted_moves = ( + self.search([("move_id", "!=", False)]) + .mapped("move_id") + .filtered(lambda m: m.state != "posted") + ) + unposted_moves.filtered( + lambda m: m.company_id.force_move_auto_post + ).action_post() + + spreads_to_archive = ( + self.env["account.spread"] + .search([("all_posted", "=", True)]) + .filtered(lambda s: s.company_id.auto_archive_spread) + ) + spreads_to_archive.write({"active": False}) diff --git a/account_spread_cost_revenue/models/account_spread_template.py b/account_spread_cost_revenue/models/account_spread_template.py new file mode 100644 index 00000000..afdb18e5 --- /dev/null +++ b/account_spread_cost_revenue/models/account_spread_template.py @@ -0,0 +1,179 @@ +# Copyright 2018-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import _, api, fields, models +from odoo.exceptions import UserError + + +class AccountSpreadTemplate(models.Model): + _name = "account.spread.template" + _inherit = "analytic.mixin" + _description = "Account Spread Template" + + name = fields.Char(required=True) + spread_type = fields.Selection( + [("sale", "Customer"), ("purchase", "Supplier")], default="sale", required=True + ) + company_id = fields.Many2one( + "res.company", default=lambda self: self.env.company, required=True + ) + spread_journal_id = fields.Many2one( + "account.journal", + string="Journal", + compute="_compute_spread_journal", + readonly=False, + store=True, + required=True, + ) + use_invoice_line_account = fields.Boolean( + string="Invoice account as spread account", + help="Use invoice line's account as Balance sheet / spread account.\n" + "In this case, user need to select expense/revenue account too.", + ) + spread_account_id = fields.Many2one( + "account.account", + string="Spread Balance Sheet Account", + compute="_compute_spread_account", + readonly=False, + store=True, + required=False, + ) + exp_rev_account_id = fields.Many2one( + "account.account", + string="Expense/Revenue Account", + help="Optional account to overwrite the existing expense/revenue account", + ) + period_number = fields.Integer( + string="Number of Repetitions", help="Define the number of spread lines" + ) + period_type = fields.Selection( + [("month", "Month"), ("quarter", "Quarter"), ("year", "Year")], + help="Period length for the entries", + ) + start_date = fields.Date() + days_calc = fields.Boolean( + string="Calculate by days", + default=False, + help="Use number of days to calculate amount", + ) + auto_spread = fields.Boolean( + string="Auto assign template on invoice validate", + help="If checked, provide option to auto create spread during " + "invoice validation, based on product/account/analytic in invoice line.", + ) + auto_spread_ids = fields.One2many( + comodel_name="account.spread.template.auto", + string="Auto Spread On", + inverse_name="template_id", + ) + + @api.model + def default_get(self, fields): + res = super().default_get(fields) + if not res.get("company_id"): + res["company_id"] = self.env.company.id + if "spread_journal_id" not in res: + default_journal = self.env["account.spread"].default_journal( + res["company_id"] + ) + if default_journal: + res["spread_journal_id"] = default_journal.id + return res + + @api.constrains("auto_spread", "auto_spread_ids") + def _check_product_account(self): + for rec in self.filtered("auto_spread"): + for line in rec.auto_spread_ids: + if not line.product_id and not line.account_id: + raise UserError( + _( + "Please select product and/or account " + "on auto spread options" + ) + ) + + @api.depends("spread_type", "company_id") + def _compute_spread_journal(self): + for spread in self: + company = spread.company_id + if spread.spread_type == "sale": + journal = company.default_spread_revenue_journal_id + else: + journal = company.default_spread_expense_journal_id + if journal: + spread.spread_journal_id = journal + + @api.depends("spread_type", "company_id") + def _compute_spread_account(self): + for spread in self: + company = spread.company_id + if spread.spread_type == "sale": + account = company.default_spread_revenue_account_id + else: + account = company.default_spread_expense_account_id + if account: + spread.spread_account_id = account + + @api.onchange("use_invoice_line_account") + def _onchange_user_invoice_line_account(self): + self.exp_rev_account_id = False + + def _prepare_spread_from_template(self, spread_account_id=False): + self.ensure_one() + company = self.company_id + spread_vals = { + "name": self.name, + "template_id": self.id, + "journal_id": self.spread_journal_id.id, + "use_invoice_line_account": self.use_invoice_line_account, + "days_calc": self.days_calc, + "company_id": company.id, + } + + account_id = spread_account_id or self.spread_account_id.id + if self.spread_type == "sale": + invoice_type = "out_invoice" + spread_vals["debit_account_id"] = account_id + else: + invoice_type = "in_invoice" + spread_vals["credit_account_id"] = account_id + + if self.period_number: + spread_vals["period_number"] = self.period_number + if self.period_type: + spread_vals["period_type"] = self.period_type + if self.start_date: + spread_vals["spread_date"] = self.start_date + + spread_vals["invoice_type"] = invoice_type + return spread_vals + + +class AccountSpreadTemplateAuto(models.Model): + _name = "account.spread.template.auto" + _inherit = "analytic.mixin" + _description = "Auto create spread, based on product/account/analytic" + + template_id = fields.Many2one( + comodel_name="account.spread.template", + string="Spread Template", + required=True, + ondelete="cascade", + index=True, + ) + company_id = fields.Many2one( + related="template_id.company_id", + store=True, + ) + name = fields.Char( + required=True, + default="/", + ) + product_id = fields.Many2one( + comodel_name="product.product", + string="Product", + ) + account_id = fields.Many2one( + comodel_name="account.account", + string="Account", + ) diff --git a/account_spread_cost_revenue/models/res_company.py b/account_spread_cost_revenue/models/res_company.py new file mode 100644 index 00000000..a9f46092 --- /dev/null +++ b/account_spread_cost_revenue/models/res_company.py @@ -0,0 +1,40 @@ +# Copyright 2018-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import fields, models + + +class ResCompany(models.Model): + _inherit = "res.company" + + default_spread_revenue_account_id = fields.Many2one( + "account.account", string="Revenue Spread Account" + ) + + default_spread_expense_account_id = fields.Many2one( + "account.account", string="Expense Spread Account" + ) + + default_spread_revenue_journal_id = fields.Many2one( + "account.journal", string="Revenue Spread Journal" + ) + + default_spread_expense_journal_id = fields.Many2one( + "account.journal", string="Expense Spread Journal" + ) + + allow_spread_planning = fields.Boolean( + default=True, + help="Disable this option if you do not want to allow the " + "spreading before the invoice is validated.", + ) + force_move_auto_post = fields.Boolean( + "Auto-post spread lines", + help="Enable this option if you want to post automatically the " + "accounting moves of all the spreads.", + ) + auto_archive_spread = fields.Boolean( + "Auto-archive spread", + help="Enable this option if you want the cron job to automatically " + "archive the spreads when all lines are posted.", + ) diff --git a/account_spread_cost_revenue/readme/CONFIGURE.rst b/account_spread_cost_revenue/readme/CONFIGURE.rst new file mode 100644 index 00000000..6a5cca1d --- /dev/null +++ b/account_spread_cost_revenue/readme/CONFIGURE.rst @@ -0,0 +1,25 @@ +To be able to access the full spreading features, the user must belong to *Show Full Accounting Features* group. + +On the form view of the company, in the *Account Spread* tab, you can configure +the journals in which the spread journal items will be generated by default: + +* the *Default Spread Journal for Revenues*, +* the *Default Spread Journal for Expenses*. + +In the same *Account Spread* tab, you can also configure the Spread Balance Sheet Accounts used by default: + +* the *Default Spread Account for Revenues*, +* the *Default Spread Account for Expenses*. + +This module by default allows the spreading even before the receipt of the invoice or when the invoice is still draft, +so that it is possible to work on the plan of the cost/revenue spreading. To disable this feature, on the form view of +the company disable the *Allow Spread Planning* option. + +In Spread Template, there is also option to *Auto assign template on invoice validate*, based on the preset invoice line criteria. + +On the form view of the company, the *Auto-post spread lines* option forces the account moves created +during the cost/revenue spreading to be automatically posted. When this option is false, the user can +enable/disable the automatic posting by the flag *Auto-post lines* present in the spread board. + +On the form view of the company, enable the *Auto-archive spread* option if you want the +cron job to automatically archive the spreads when all lines are posted. diff --git a/account_spread_cost_revenue/readme/CONTRIBUTORS.rst b/account_spread_cost_revenue/readme/CONTRIBUTORS.rst new file mode 100644 index 00000000..92646386 --- /dev/null +++ b/account_spread_cost_revenue/readme/CONTRIBUTORS.rst @@ -0,0 +1,3 @@ +* Andrea Stirpe +* Kitti U. +* Saran Lim. diff --git a/account_spread_cost_revenue/readme/CREDITS.rst b/account_spread_cost_revenue/readme/CREDITS.rst new file mode 100644 index 00000000..9a3666a4 --- /dev/null +++ b/account_spread_cost_revenue/readme/CREDITS.rst @@ -0,0 +1,3 @@ +Part of the code in this module (in particular the computation of the spread lines) +is highly inspired by the Assets Management module from the standard +Odoo 11.0 Community developed by Odoo SA. diff --git a/account_spread_cost_revenue/readme/DESCRIPTION.rst b/account_spread_cost_revenue/readme/DESCRIPTION.rst new file mode 100644 index 00000000..d37dce99 --- /dev/null +++ b/account_spread_cost_revenue/readme/DESCRIPTION.rst @@ -0,0 +1 @@ +Allows to spread costs or revenues over a customizable periods, to even out cost or invoice spikes. diff --git a/account_spread_cost_revenue/readme/HISTORY.rst b/account_spread_cost_revenue/readme/HISTORY.rst new file mode 100644 index 00000000..0f78ecec --- /dev/null +++ b/account_spread_cost_revenue/readme/HISTORY.rst @@ -0,0 +1,28 @@ +13.0.1.0.0 +~~~~~~~~~~ + +* [MIG] Port account_spread_cost_revenue to V13. + +12.0.2.0.0 +~~~~~~~~~~ + +* [ENH] In spread template, add option to auto create spread on invoice validation + +12.0.1.1.0 +~~~~~~~~~~ + +* [ENH] Add optional Expense/Revenue Account in Chart Template, which can be used + in place of account from invoice line to set Expense/Revenue account in the spread + + +12.0.1.0.0 +~~~~~~~~~~ + +* [MIG] Port account_spread_cost_revenue to V12. + + +11.0.1.0.0 +~~~~~~~~~~ + +* [ADD] Module account_spread_cost_revenue. + (`#715 `_) diff --git a/account_spread_cost_revenue/readme/USAGE.rst b/account_spread_cost_revenue/readme/USAGE.rst new file mode 100644 index 00000000..3737e4b7 --- /dev/null +++ b/account_spread_cost_revenue/readme/USAGE.rst @@ -0,0 +1,79 @@ +Define Spread Costs/Revenues Board +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Under Invoicing -> Accounting -> Journals -> Spread Costs/Revenues, create a new spread board. + +Complete the definition of the spreading criteria, by setting the the fields: + +* *Debit Account* +* *Credit Account* +* *Estimated Amount* (The total amount to spread) +* *Number of Repetitions* +* *Period Type* (Duration of each period) +* *Start date* +* *Journal* + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/spread.png + :alt: Create a new spread board + +Click on the "Recalculate unposted lines" button on the top-left to calculate the spread lines. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/create_spread.png + :alt: The spreading board is defined + +A cron job will automatically create the accounting moves for all the lines having date previous that the current day (today). + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/update_spread.png + :alt: The spreading board is updated by the cron job + +By default, the status of the created accounting moves is posted. +To disable the automatic posting of the accounting moves, set the flag *Auto-post lines* to False. +This flag is only available when the *Auto-post spread lines* option, present on the form view of the company, is disabled. + +Click on button *Recalculate entire spread* button in the spread board to force the recalculation of the spread lines: +this will also reset all the journal entries previously created. + +Link Invoice to Spread Costs/Revenues Board +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Create an invoice or vendor bill in draft. On its lines, the spreading right-arrow icon are displayed in dark-grey color. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/invoice_line_1.png + :alt: On the invoice line the spreading icon is displayed + +Click on the spreading right-arrow icon. A wizard prompts to enter a *Spread Action Type*: + +- *Link to existing spread board* +- *Create from spread template* +- *Create new spread board* + +Select *Link to existing spread board* and enter the previously generated Spread Board. Click on Confirm button: +the selected Spread Board will be automatically displayed. + +Go back to the draft invoice/bill. The spreading functionality is now enabled on the invoice line: +the spreading right-arrow icon is now displayed in green color. + +.. figure:: https://raw.githubusercontent.com/OCA/account-financial-tools/16.0/account_spread_cost_revenue/static/description/invoice_line_2.png + :alt: On the invoice line the spreading icon is displayed in green color + +Validate the invoice/bill. Click on the spreading (green) right-arrow icon to open the spread board, then click +on the smart button *Posted entries* to see the moves of the spread lines together with the move of the invoice line. + +In case the Subtotal Price of the invoice line is different than the *Estimated Amount* of the spread board, the spread +lines (not yet posted) will be recalculated when validating the invoice/bill. + +Define Spread Costs/Revenues Template +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Under Invoicing -> Configuration -> Accounting -> Spread Templates, create a new spread template. + +* *Spread Type* +* *Spread Balance Sheet Account* +* *Expense/Revenue Account* This option visible if invoice line account is balance sheet account, user need to specify this too. +* *Journal* +* *Auto assign template on invoice validate* + +When creating a new Spread Costs/Revenues Board, select the right template. +This way the above fields will be copied to the Spread Board. + +If *Auto assign template on invoice validate* is checked, this template will be used to auto create spread, if the underlining invoice match the preset product/account/analytic criteria. diff --git a/account_spread_cost_revenue/security/account_spread_security.xml b/account_spread_cost_revenue/security/account_spread_security.xml new file mode 100644 index 00000000..5e453c0b --- /dev/null +++ b/account_spread_cost_revenue/security/account_spread_security.xml @@ -0,0 +1,27 @@ + + + + Account Spread multi-company + + + ['|',('company_id','=',False),('company_id', 'in', company_ids)] + + + Account Spread Template multi-company + + + ['|',('company_id','=',False),('company_id', 'in', company_ids)] + + + Account Spread Tempalte Auto multi-company + + + ['|',('company_id','=',False),('company_id', 'in', company_ids)] + + diff --git a/account_spread_cost_revenue/security/ir.model.access.csv b/account_spread_cost_revenue/security/ir.model.access.csv new file mode 100644 index 00000000..a5e13ba1 --- /dev/null +++ b/account_spread_cost_revenue/security/ir.model.access.csv @@ -0,0 +1,10 @@ +id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink +access_account_spread_cost_revenue_full,Full access on account.spread,model_account_spread,account.group_account_manager,1,1,1,1 +access_account_spread_cost_revenue_read,Read access on account.spread,model_account_spread,account.group_account_invoice,1,0,0,0 +access_account_spread_cost_revenue_line_full,Full access on account.spread.line,model_account_spread_line,account.group_account_manager,1,1,1,1 +access_account_spread_cost_revenue_line_read,Read access on account.spread.line,model_account_spread_line,account.group_account_invoice,1,0,0,0 +access_account_spread_cost_revenue_template_full,Full access on account.spread.template,model_account_spread_template,account.group_account_manager,1,1,1,1 +access_account_spread_cost_revenue_template_read,Read access on account.spread.template,model_account_spread_template,account.group_account_invoice,1,0,0,0 +access_account_spread_cost_revenue_template_auto_full,Full access on account.spread.template.auto,model_account_spread_template_auto,account.group_account_manager,1,1,1,1 +access_account_spread_cost_revenue_template_auto_read,Read access on account.spread.template.auto,model_account_spread_template_auto,account.group_account_invoice,1,0,0,0 +access_account_spread_invoice_line_link_wizard,access_account_spread_invoice_line_link_wizard,model_account_spread_invoice_line_link_wizard,base.group_user,1,1,1,1 diff --git a/account_spread_cost_revenue/static/description/create_spread.png b/account_spread_cost_revenue/static/description/create_spread.png new file mode 100644 index 00000000..27bb3c3e Binary files /dev/null and b/account_spread_cost_revenue/static/description/create_spread.png differ diff --git a/account_spread_cost_revenue/static/description/icon.png b/account_spread_cost_revenue/static/description/icon.png new file mode 100644 index 00000000..e23c3eb5 Binary files /dev/null and b/account_spread_cost_revenue/static/description/icon.png differ diff --git a/account_spread_cost_revenue/static/description/index.html b/account_spread_cost_revenue/static/description/index.html new file mode 100644 index 00000000..6e3077e1 --- /dev/null +++ b/account_spread_cost_revenue/static/description/index.html @@ -0,0 +1,575 @@ + + + + + + +Cost-Revenue Spread + + + +
+

Cost-Revenue Spread

+ + +

Beta License: AGPL-3 OCA/account-financial-tools Translate me on Weblate Try me on Runboat

+

Allows to spread costs or revenues over a customizable periods, to even out cost or invoice spikes.

+

Table of contents

+ +
+

Configuration

+

To be able to access the full spreading features, the user must belong to Show Full Accounting Features group.

+

On the form view of the company, in the Account Spread tab, you can configure +the journals in which the spread journal items will be generated by default:

+
    +
  • the Default Spread Journal for Revenues,
  • +
  • the Default Spread Journal for Expenses.
  • +
+

In the same Account Spread tab, you can also configure the Spread Balance Sheet Accounts used by default:

+
    +
  • the Default Spread Account for Revenues,
  • +
  • the Default Spread Account for Expenses.
  • +
+

This module by default allows the spreading even before the receipt of the invoice or when the invoice is still draft, +so that it is possible to work on the plan of the cost/revenue spreading. To disable this feature, on the form view of +the company disable the Allow Spread Planning option.

+

In Spread Template, there is also option to Auto assign template on invoice validate, based on the preset invoice line criteria.

+

On the form view of the company, the Auto-post spread lines option forces the account moves created +during the cost/revenue spreading to be automatically posted. When this option is false, the user can +enable/disable the automatic posting by the flag Auto-post lines present in the spread board.

+

On the form view of the company, enable the Auto-archive spread option if you want the +cron job to automatically archive the spreads when all lines are posted.

+
+
+

Usage

+
+

Define Spread Costs/Revenues Board

+

Under Invoicing -> Accounting -> Journals -> Spread Costs/Revenues, create a new spread board.

+

Complete the definition of the spreading criteria, by setting the the fields:

+
    +
  • Debit Account
  • +
  • Credit Account
  • +
  • Estimated Amount (The total amount to spread)
  • +
  • Number of Repetitions
  • +
  • Period Type (Duration of each period)
  • +
  • Start date
  • +
  • Journal
  • +
+
+Create a new spread board +
+

Click on the “Recalculate unposted lines” button on the top-left to calculate the spread lines.

+
+The spreading board is defined +
+

A cron job will automatically create the accounting moves for all the lines having date previous that the current day (today).

+
+The spreading board is updated by the cron job +
+

By default, the status of the created accounting moves is posted. +To disable the automatic posting of the accounting moves, set the flag Auto-post lines to False. +This flag is only available when the Auto-post spread lines option, present on the form view of the company, is disabled.

+

Click on button Recalculate entire spread button in the spread board to force the recalculation of the spread lines: +this will also reset all the journal entries previously created.

+
+ +
+

Define Spread Costs/Revenues Template

+

Under Invoicing -> Configuration -> Accounting -> Spread Templates, create a new spread template.

+
    +
  • Spread Type
  • +
  • Spread Balance Sheet Account
  • +
  • Expense/Revenue Account This option visible if invoice line account is balance sheet account, user need to specify this too.
  • +
  • Journal
  • +
  • Auto assign template on invoice validate
  • +
+

When creating a new Spread Costs/Revenues Board, select the right template. +This way the above fields will be copied to the Spread Board.

+

If Auto assign template on invoice validate is checked, this template will be used to auto create spread, if the underlining invoice match the preset product/account/analytic criteria.

+
+
+
+

Changelog

+
+

13.0.1.0.0

+
    +
  • [MIG] Port account_spread_cost_revenue to V13.
  • +
+
+
+

12.0.2.0.0

+
    +
  • [ENH] In spread template, add option to auto create spread on invoice validation
  • +
+
+
+

12.0.1.1.0

+
    +
  • [ENH] Add optional Expense/Revenue Account in Chart Template, which can be used +in place of account from invoice line to set Expense/Revenue account in the spread
  • +
+
+
+

12.0.1.0.0

+
    +
  • [MIG] Port account_spread_cost_revenue to V12.
  • +
+
+
+

11.0.1.0.0

+
    +
  • [ADD] Module account_spread_cost_revenue. +(#715)
  • +
+
+
+
+

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 to smash it by providing a detailed and welcomed +feedback.

+

Do not contact contributors directly about support or help with technical issues.

+
+
+

Credits

+
+

Authors

+
    +
  • Onestein
  • +
+
+
+

Contributors

+ +
+
+

Other credits

+

Part of the code in this module (in particular the computation of the spread lines) +is highly inspired by the Assets Management module from the standard +Odoo 11.0 Community developed by Odoo SA.

+
+
+

Maintainers

+

This module is maintained by the OCA.

+Odoo Community Association +

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.

+

This module is part of the OCA/account-financial-tools project on GitHub.

+

You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute.

+
+
+
+ + diff --git a/account_spread_cost_revenue/static/description/invoice_line_1.png b/account_spread_cost_revenue/static/description/invoice_line_1.png new file mode 100644 index 00000000..7d899114 Binary files /dev/null and b/account_spread_cost_revenue/static/description/invoice_line_1.png differ diff --git a/account_spread_cost_revenue/static/description/invoice_line_2.png b/account_spread_cost_revenue/static/description/invoice_line_2.png new file mode 100644 index 00000000..b5278cac Binary files /dev/null and b/account_spread_cost_revenue/static/description/invoice_line_2.png differ diff --git a/account_spread_cost_revenue/static/description/spread.png b/account_spread_cost_revenue/static/description/spread.png new file mode 100644 index 00000000..cd2140b8 Binary files /dev/null and b/account_spread_cost_revenue/static/description/spread.png differ diff --git a/account_spread_cost_revenue/static/description/update_spread.png b/account_spread_cost_revenue/static/description/update_spread.png new file mode 100644 index 00000000..44b6dd32 Binary files /dev/null and b/account_spread_cost_revenue/static/description/update_spread.png differ diff --git a/account_spread_cost_revenue/tests/__init__.py b/account_spread_cost_revenue/tests/__init__.py new file mode 100644 index 00000000..055f442a --- /dev/null +++ b/account_spread_cost_revenue/tests/__init__.py @@ -0,0 +1,6 @@ +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from . import test_account_spread_cost_revenue +from . import test_compute_spread_board +from . import test_account_invoice_spread +from . import test_account_invoice_auto_spread diff --git a/account_spread_cost_revenue/tests/test_account_invoice_auto_spread.py b/account_spread_cost_revenue/tests/test_account_invoice_auto_spread.py new file mode 100644 index 00000000..fd770372 --- /dev/null +++ b/account_spread_cost_revenue/tests/test_account_invoice_auto_spread.py @@ -0,0 +1,103 @@ +# Copyright 2018-2019 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo.exceptions import UserError + +from .test_account_invoice_spread import TestAccountInvoiceSpread + + +class TestAccountInvoiceAutoSpread(TestAccountInvoiceSpread): + def test_01_no_auto_spread_sheet(self): + + self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "purchase", + "period_number": 5, + "period_type": "month", + "spread_account_id": self.account_payable.id, + "spread_journal_id": self.expenses_journal.id, + "auto_spread": False, # Auto Spread = False + "auto_spread_ids": [ + (0, 0, {"account_id": self.vendor_bill_line.account_id.id}) + ], + } + ) + + self.assertFalse(self.vendor_bill_line.spread_id) + self.vendor_bill.action_post() + self.assertFalse(self.vendor_bill_line.spread_id) + + def test_02_new_auto_spread_sheet_purchase(self): + + self.env["account.spread.template"].create( + { + "name": "test 1", + "spread_type": "purchase", + "period_number": 5, + "period_type": "month", + "spread_account_id": self.account_payable.id, + "spread_journal_id": self.expenses_journal.id, + "auto_spread": True, # Auto Spread + "auto_spread_ids": [ + (0, 0, {"account_id": self.vendor_bill_line.account_id.id}) + ], + } + ) + template2 = self.env["account.spread.template"].create( + { + "name": "test 2", + "spread_type": "purchase", + "period_number": 5, + "period_type": "month", + "spread_account_id": self.account_payable.id, + "spread_journal_id": self.expenses_journal.id, + "auto_spread": True, # Auto Spread + "auto_spread_ids": [ + (0, 0, {"account_id": self.vendor_bill_line.account_id.id}) + ], + } + ) + + self.assertFalse(self.vendor_bill_line.spread_id) + with self.assertRaises(UserError): # too many auto_spread_ids matched + self.vendor_bill.action_post() + + template2.auto_spread = False # Do not use this template + self.vendor_bill.action_post() + self.assertTrue(self.vendor_bill_line.spread_id) + + spread_lines = self.vendor_bill_line.spread_id.line_ids + self.assertTrue(spread_lines) + + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + def test_03_new_auto_spread_sheet_sale(self): + + self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "sale", + "period_number": 5, + "period_type": "month", + "spread_account_id": self.account_receivable.id, + "spread_journal_id": self.sales_journal.id, + "auto_spread": True, # Auto Spread + "auto_spread_ids": [ + (0, 0, {"account_id": self.invoice_line.account_id.id}) + ], + } + ) + + self.assertFalse(self.invoice_line.spread_id) + self.sale_invoice.action_post() + self.assertTrue(self.invoice_line.spread_id) + + spread_lines = self.invoice_line.spread_id.line_ids + self.assertTrue(spread_lines) + + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) diff --git a/account_spread_cost_revenue/tests/test_account_invoice_spread.py b/account_spread_cost_revenue/tests/test_account_invoice_spread.py new file mode 100644 index 00000000..4ab88ce4 --- /dev/null +++ b/account_spread_cost_revenue/tests/test_account_invoice_spread.py @@ -0,0 +1,809 @@ +# Copyright 2018-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +import datetime + +from odoo import fields +from odoo.exceptions import UserError, ValidationError +from odoo.tests import Form, common + + +class TestAccountInvoiceSpread(common.TransactionCase): + def create_account_invoice(self, invoice_type, quantity=1.0, price_unit=1000.0): + """Create an invoice as in a view by triggering its onchange methods""" + + invoice_form = Form( + self.env["account.move"].with_context(default_move_type=invoice_type) + ) + invoice_form.partner_id = self.env["res.partner"].create( + {"name": "Partner Name"} + ) + with invoice_form.invoice_line_ids.new() as line: + line.name = "product that costs " + str(price_unit) + line.quantity = quantity + line.price_unit = price_unit + + return invoice_form.save() + + def setUp(self): + super().setUp() + + # Define minimal accounting data to run + a_expense = self.env["account.account"].create( + { + "code": "X2120", + "name": "Expenses - (test)", + "account_type": "expense", + } + ) + a_sale = self.env["account.account"].create( + { + "code": "X2020", + "name": "Product Sales - (test)", + "account_type": "expense_direct_cost", + } + ) + + self.expenses_journal = self.env["account.journal"].create( + { + "name": "Vendor Bills - Test", + "code": "TEXJ", + "type": "purchase", + "default_account_id": a_expense.id, + "refund_sequence": True, + } + ) + self.sales_journal = self.env["account.journal"].create( + { + "name": "Customer Invoices - Test", + "code": "TINV", + "type": "sale", + "default_account_id": a_sale.id, + "refund_sequence": True, + } + ) + + self.account_payable = self.env["account.account"].create( + { + "name": "Test account payable", + "code": "321spread", + "account_type": "income_other", + "reconcile": True, + } + ) + + self.account_receivable = self.env["account.account"].create( + { + "name": "Test account receivable", + "code": "322spread", + "account_type": "income_other", + "reconcile": True, + } + ) + + spread_account_payable = self.env["account.account"].create( + { + "name": "test spread account_payable", + "code": "765spread", + "account_type": "income_other", + "reconcile": True, + } + ) + + spread_account_receivable = self.env["account.account"].create( + { + "name": "test spread account_receivable", + "code": "766spread", + "account_type": "income_other", + "reconcile": True, + } + ) + + # Invoices + + self.vendor_bill = self.create_account_invoice("in_invoice") + self.vendor_bill.invoice_date = fields.Date.today() + self.sale_invoice = self.create_account_invoice("out_invoice") + self.sale_invoice.invoice_date = fields.Date.today() + self.vendor_bill_line = self.vendor_bill.invoice_line_ids[0] + self.invoice_line = self.sale_invoice.invoice_line_ids[0] + + # Set accounts to reconcilable + self.vendor_bill_line.account_id.reconcile = True + self.invoice_line.account_id.reconcile = True + + analytic_plan = self.env["account.analytic.plan"].create( + {"name": "Plan Test", "company_id": False} + ) + self.analytic_account = self.env["account.analytic.account"].create( + {"name": "test account", "plan_id": analytic_plan.id} + ) + self.distribution = self.env["account.analytic.distribution.model"].create( + { + "partner_id": self.vendor_bill.partner_id.id, + "analytic_distribution": {self.analytic_account.id: 100}, + } + ) + self.spread = ( + self.env["account.spread"] + .with_context(mail_create_nosubscribe=True) + .create( + [ + { + "name": "test", + "debit_account_id": spread_account_payable.id, + "credit_account_id": self.account_payable.id, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 2, 1), + "estimated_amount": 1000.0, + "journal_id": self.vendor_bill.journal_id.id, + "invoice_type": "in_invoice", + "analytic_distribution": self.distribution._get_distribution( + { + "partner_id": self.vendor_bill.partner_id.id, + } + ), + } + ] + ) + ) + + self.spread2 = self.env["account.spread"].create( + [ + { + "name": "test2", + "debit_account_id": spread_account_receivable.id, + "credit_account_id": self.account_receivable.id, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 2, 1), + "estimated_amount": 1000.0, + "journal_id": self.sale_invoice.journal_id.id, + "invoice_type": "out_invoice", + } + ] + ) + + def test_01_wizard_defaults(self): + Wizard = self.env["account.spread.invoice.line.link.wizard"] + + wizard1 = Wizard.with_context( + default_invoice_line_id=self.vendor_bill_line.id, + default_company_id=self.env.company.id, + allow_spread_planning=True, + ).create({}) + + self.assertEqual(wizard1.invoice_line_id, self.vendor_bill_line) + self.assertEqual(wizard1.invoice_line_id.move_id, self.vendor_bill) + self.assertEqual(wizard1.invoice_type, "in_invoice") + self.assertFalse(wizard1.spread_id) + self.assertEqual(wizard1.company_id, self.env.company) + self.assertEqual(wizard1.spread_action_type, "link") + self.assertFalse(wizard1.spread_account_id) + self.assertFalse(wizard1.spread_journal_id) + + wizard2 = Wizard.with_context( + default_invoice_line_id=self.invoice_line.id, + default_company_id=self.env.company.id, + ).create({}) + + self.assertEqual(wizard2.invoice_line_id, self.invoice_line) + self.assertEqual(wizard2.invoice_line_id.move_id, self.sale_invoice) + self.assertEqual(wizard2.invoice_type, "out_invoice") + self.assertFalse(wizard2.spread_id) + self.assertEqual(wizard2.company_id, self.env.company) + self.assertEqual(wizard2.spread_action_type, "template") + self.assertFalse(wizard2.spread_account_id) + self.assertFalse(wizard2.spread_journal_id) + + def test_02_wizard_defaults(self): + Wizard = self.env["account.spread.invoice.line.link.wizard"] + + self.env.company.default_spread_revenue_account_id = self.account_receivable + self.env.company.default_spread_expense_account_id = self.account_payable + self.env.company.default_spread_revenue_journal_id = self.sales_journal + self.env.company.default_spread_expense_journal_id = self.expenses_journal + + self.assertTrue(self.env.company.default_spread_revenue_account_id) + self.assertTrue(self.env.company.default_spread_expense_account_id) + self.assertTrue(self.env.company.default_spread_revenue_journal_id) + self.assertTrue(self.env.company.default_spread_expense_journal_id) + + wizard1 = Wizard.with_context( + default_invoice_line_id=self.vendor_bill_line.id, + default_company_id=self.env.company.id, + allow_spread_planning=True, + ).create({}) + + self.assertEqual(wizard1.invoice_line_id, self.vendor_bill_line) + self.assertEqual(wizard1.invoice_line_id.move_id, self.vendor_bill) + self.assertEqual(wizard1.invoice_type, "in_invoice") + self.assertFalse(wizard1.spread_id) + self.assertEqual(wizard1.company_id, self.env.company) + self.assertEqual(wizard1.spread_action_type, "link") + self.assertTrue(wizard1.spread_account_id) + self.assertTrue(wizard1.spread_journal_id) + self.assertEqual(wizard1.spread_account_id, self.account_payable) + self.assertEqual(wizard1.spread_journal_id.id, self.expenses_journal.id) + self.assertTrue(wizard1.spread_invoice_type_domain_ids) + + wizard2 = Wizard.with_context( + default_invoice_line_id=self.invoice_line.id, + default_company_id=self.env.company.id, + ).create({}) + + self.assertEqual(wizard2.invoice_line_id, self.invoice_line) + self.assertEqual(wizard2.invoice_line_id.move_id, self.sale_invoice) + self.assertEqual(wizard2.invoice_type, "out_invoice") + self.assertFalse(wizard2.spread_id) + self.assertEqual(wizard2.company_id, self.env.company) + self.assertEqual(wizard2.spread_action_type, "template") + self.assertTrue(wizard2.spread_account_id) + self.assertTrue(wizard2.spread_journal_id) + self.assertEqual(wizard2.spread_account_id, self.account_receivable) + self.assertEqual(wizard2.spread_journal_id.id, self.sales_journal.id) + self.assertTrue(wizard2.spread_invoice_type_domain_ids) + + def test_03_link_invoice_line_with_spread_sheet(self): + + self.env.user.write( + { + "groups_id": [ + (4, self.env.ref("analytic.group_analytic_accounting").id), + ], + } + ) + + Wizard = self.env["account.spread.invoice.line.link.wizard"] + wizard1 = Wizard.with_context( + default_invoice_line_id=self.vendor_bill_line.id, + default_company_id=self.env.company.id, + allow_spread_planning=True, + ).create({}) + self.assertEqual(wizard1.spread_action_type, "link") + + wizard1.spread_account_id = self.account_receivable + wizard1.spread_journal_id = self.expenses_journal + wizard1.spread_id = self.spread + res_action = wizard1.confirm() + self.assertTrue(isinstance(res_action, dict)) + self.assertTrue(res_action.get("res_id")) + self.assertEqual(res_action.get("res_id"), self.spread.id) + self.assertTrue(self.spread.invoice_line_id) + self.assertEqual(self.spread.invoice_line_id, self.vendor_bill_line) + + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + for ml in line.move_id.line_ids: + self.assertEqual( + ml.analytic_distribution, self.spread.analytic_distribution + ) + + self.spread.invoice_id.button_cancel() + + self.assertTrue(self.spread.invoice_line_id) + with self.assertRaises(UserError): + self.spread.unlink() + with self.assertRaises(UserError): + self.spread.action_unlink_invoice_line() + self.assertTrue(self.spread.invoice_line_id) + + def test_04_new_spread_sheet(self): + + Wizard = self.env["account.spread.invoice.line.link.wizard"] + + spread_journal_id = self.expenses_journal + + wizard1 = Wizard.with_context( + default_invoice_line_id=self.vendor_bill_line.id, + default_company_id=self.env.company.id, + ).create({"spread_action_type": "new"}) + self.assertEqual(wizard1.spread_action_type, "new") + + wizard1.write( + { + "spread_account_id": self.account_receivable.id, + "spread_journal_id": spread_journal_id, + } + ) + + res_action = wizard1.confirm() + self.assertTrue(isinstance(res_action, dict)) + self.assertFalse(res_action.get("res_id")) + self.assertTrue(res_action.get("context")) + res_context = res_action.get("context") + self.assertTrue(res_context.get("default_name")) + self.assertTrue(res_context.get("default_invoice_type")) + self.assertTrue(res_context.get("default_invoice_line_id")) + self.assertTrue(res_context.get("default_debit_account_id")) + self.assertTrue(res_context.get("default_credit_account_id")) + + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + wizard2 = Wizard.with_context( + default_invoice_line_id=self.invoice_line.id, + default_company_id=self.env.company.id, + ).create({"spread_action_type": "new"}) + self.assertEqual(wizard2.spread_action_type, "new") + + wizard2.write( + { + "spread_account_id": self.account_receivable.id, + "spread_journal_id": spread_journal_id, + } + ) + + res_action = wizard2.confirm() + self.assertTrue(isinstance(res_action, dict)) + self.assertFalse(res_action.get("res_id")) + self.assertTrue(res_action.get("context")) + res_context = res_action.get("context") + self.assertTrue(res_context.get("default_name")) + self.assertTrue(res_context.get("default_invoice_type")) + self.assertTrue(res_context.get("default_invoice_line_id")) + self.assertTrue(res_context.get("default_debit_account_id")) + self.assertTrue(res_context.get("default_credit_account_id")) + + self.assertFalse(any(line.move_id for line in self.spread2.line_ids)) + + self.spread2.compute_spread_board() + for line in self.spread2.line_ids: + line.create_move() + self.assertTrue(line.move_id) + + def test_05_new_spread_sheet_from_template(self): + + Wizard = self.env["account.spread.invoice.line.link.wizard"] + + spread_account = self.account_payable + self.assertTrue(spread_account) + spread_journal_id = self.expenses_journal.id + + template = self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "purchase", + "period_number": 5, + "period_type": "month", + "spread_account_id": spread_account.id, + "spread_journal_id": spread_journal_id, + } + ) + + wizard1 = Wizard.with_context( + default_invoice_line_id=self.vendor_bill_line.id, + default_company_id=self.env.company.id, + ).create({"spread_action_type": "template", "template_id": template.id}) + self.assertEqual(wizard1.spread_action_type, "template") + + res_action = wizard1.confirm() + self.assertTrue(isinstance(res_action, dict)) + self.assertTrue(res_action.get("res_id")) + + new_spread = self.env["account.spread"].browse(res_action["res_id"]) + new_spread.compute_spread_board() + + self.assertFalse(any(line.move_id for line in new_spread.line_ids)) + + for line in new_spread.line_ids: + line.create_move() + self.assertTrue(line.move_id) + + wizard2 = Wizard.with_context( + default_invoice_line_id=self.invoice_line.id, + default_company_id=self.env.company.id, + ).create({"spread_action_type": "new"}) + self.assertEqual(wizard2.spread_action_type, "new") + + wizard2.write( + { + "spread_account_id": spread_account.id, + "spread_journal_id": spread_journal_id, + } + ) + + res_action = wizard2.confirm() + self.assertTrue(isinstance(res_action, dict)) + self.assertFalse(res_action.get("res_id")) + self.assertTrue(res_action.get("context")) + res_context = res_action.get("context") + self.assertTrue(res_context.get("default_name")) + self.assertTrue(res_context.get("default_invoice_type")) + self.assertTrue(res_context.get("default_invoice_line_id")) + self.assertTrue(res_context.get("default_debit_account_id")) + self.assertTrue(res_context.get("default_credit_account_id")) + + self.assertFalse(any(line.move_id for line in self.spread2.line_ids)) + + self.spread2.compute_spread_board() + for line in self.spread2.line_ids: + line.create_move() + self.assertTrue(line.move_id) + + def test_06_open_wizard(self): + + res_action = self.vendor_bill_line.spread_details() + self.assertTrue(isinstance(res_action, dict)) + self.assertFalse(res_action.get("res_id")) + self.assertTrue(res_action.get("context")) + + def test_07_unlink_invoice_line_and_spread_sheet(self): + + self.assertFalse(self.spread.invoice_line_id) + + self.vendor_bill_line.spread_id = self.spread + self.assertTrue(self.spread.invoice_line_id) + self.spread.action_unlink_invoice_line() + self.assertFalse(self.spread.invoice_line_id) + + self.assertFalse(self.spread2.invoice_line_id) + self.invoice_line.spread_id = self.spread2 + self.assertTrue(self.spread2.invoice_line_id) + self.spread2.action_unlink_invoice_line() + self.assertFalse(self.spread2.invoice_line_id) + + def test_08_invoice_multi_line(self): + invoice_form = Form(self.vendor_bill) + with invoice_form.invoice_line_ids.new() as line: + line.name = "new test line" + line.quantity = 1.0 + line.price_unit = 1000.0 + self.invoice = invoice_form.save() + self.assertEqual(len(self.vendor_bill.invoice_line_ids), 2) + + self.vendor_bill_line.spread_id = self.spread + self.assertTrue(self.spread.invoice_id.invoice_line_ids[0]) + self.assertEqual( + self.spread.invoice_id.invoice_line_ids[0], self.vendor_bill_line + ) + self.assertTrue(self.vendor_bill_line.spread_id) + self.assertEqual(self.vendor_bill_line.spread_check, "linked") + self.assertFalse(self.vendor_bill.invoice_line_ids[1].spread_id) + self.assertEqual(self.vendor_bill.invoice_line_ids[1].spread_check, "unlinked") + + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + # Validate invoice + self.vendor_bill.action_post() + + self.assertTrue(self.vendor_bill_line.spread_id) + self.assertEqual(self.vendor_bill_line.spread_check, "linked") + self.assertFalse(self.vendor_bill.invoice_line_ids[1].spread_id) + self.assertEqual( + self.vendor_bill.invoice_line_ids[1].spread_check, "unavailable" + ) + + def test_09_no_link_invoice(self): + + balance_sheet = self.spread.credit_account_id + + # Validate invoice + self.vendor_bill.action_post() + + invoice_mls = self.vendor_bill.invoice_line_ids + self.assertTrue(invoice_mls) + for invoice_ml in invoice_mls: + self.assertNotEqual(invoice_ml.account_id, balance_sheet) + + def test_10_link_vendor_bill_line_with_spread_sheet(self): + invoice_form = Form(self.vendor_bill) + with invoice_form.invoice_line_ids.new() as line: + line.name = "new test line" + line.quantity = 1.0 + line.price_unit = 1000.0 + self.invoice = invoice_form.save() + + self.spread.write( + { + "estimated_amount": 1000.0, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + "invoice_line_id": self.vendor_bill_line.id, + "move_line_auto_post": False, + } + ) + + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + expense_account = self.spread.debit_account_id + balance_sheet = self.spread.credit_account_id + self.assertTrue(balance_sheet.reconcile) + + spread_mls = self.spread.line_ids.mapped("move_id.line_ids") + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertEqual(spread_ml.account_id, expense_account) + if spread_ml.credit: + self.assertEqual(spread_ml.account_id, balance_sheet) + + # Validate invoice + self.vendor_bill.action_post() + + count_balance_sheet = len( + self.vendor_bill.line_ids.filtered(lambda x: x.account_id == balance_sheet) + ) + self.assertEqual(count_balance_sheet, 1) + + self.spread.line_ids.create_and_reconcile_moves() + + spread_mls = self.spread.line_ids.mapped("move_id.line_ids") + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertFalse(spread_ml.full_reconcile_id) + if spread_ml.credit: + self.assertFalse(spread_ml.full_reconcile_id) + + action_posted_view = self.spread2.open_posted_view() + self.assertTrue(isinstance(action_posted_view, dict)) + self.assertFalse(action_posted_view.get("domain")[0][2]) + self.assertTrue(action_posted_view.get("context")) + + def test_11_link_vendor_bill_line_with_spread_sheet(self): + invoice_form = Form(self.vendor_bill) + with invoice_form.invoice_line_ids.new() as line: + line.name = "new test line" + line.quantity = 1.0 + line.price_unit = 1000.0 + self.invoice = invoice_form.save() + self.spread.write( + { + "estimated_amount": 1000.0, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + "invoice_line_id": self.vendor_bill_line.id, + "move_line_auto_post": False, + } + ) + + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + expense_account = self.spread.debit_account_id + balance_sheet = self.spread.credit_account_id + self.assertTrue(balance_sheet.reconcile) + + spread_mls = self.spread.line_ids.mapped("move_id.line_ids") + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertEqual(spread_ml.account_id, expense_account) + if spread_ml.credit: + self.assertEqual(spread_ml.account_id, balance_sheet) + + # Validate invoice + self.vendor_bill.action_post() + + invoice_mls = self.vendor_bill.line_ids + self.assertTrue(invoice_mls) + + count_balance_sheet = len( + invoice_mls.filtered(lambda x: x.account_id == balance_sheet) + ) + self.assertEqual(count_balance_sheet, 1) + + self.spread.company_id.force_move_auto_post = True + self.spread.line_ids.create_and_reconcile_moves() + + spread_mls = self.spread.line_ids.mapped("move_id.line_ids") + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.credit: + self.assertEqual(spread_ml.account_id, balance_sheet) + self.assertTrue(spread_ml.full_reconcile_id) + if spread_ml.debit: + self.assertEqual(spread_ml.account_id, expense_account) + self.assertFalse(spread_ml.full_reconcile_id) + + action_posted_view = self.spread.open_posted_view() + self.assertTrue(isinstance(action_posted_view, dict)) + self.assertTrue(action_posted_view.get("domain")[0][2]) + self.assertTrue(action_posted_view.get("context")) + + action_spread_details = self.vendor_bill_line.spread_details() + self.assertTrue(isinstance(action_spread_details, dict)) + self.assertTrue(action_spread_details.get("res_id")) + + def test_12_link_invoice_line_with_spread_sheet_full_reconcile(self): + + # Validate invoice + self.sale_invoice.action_post() + + self.spread2.write( + { + "estimated_amount": 1000.0, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + "invoice_line_id": self.invoice_line.id, + "move_line_auto_post": False, + } + ) + + self.assertFalse(any(line.move_id for line in self.spread2.line_ids)) + + self.spread2.compute_spread_board() + spread_lines = self.spread2.line_ids + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + payable_account = self.spread2.credit_account_id + balance_sheet = self.spread2.debit_account_id + self.assertTrue(balance_sheet.reconcile) + + spread_mls = self.spread2.line_ids.mapped("move_id.line_ids") + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertEqual(spread_ml.account_id, balance_sheet) + self.assertFalse(spread_ml.reconciled) + self.assertFalse(spread_ml.full_reconcile_id) + if spread_ml.credit: + self.assertEqual(spread_ml.account_id, payable_account) + self.assertFalse(spread_ml.reconciled) + self.assertFalse(spread_ml.full_reconcile_id) + + invoice_mls = self.sale_invoice.invoice_line_ids + self.assertTrue(invoice_mls) + for invoice_ml in invoice_mls: + self.assertEqual(invoice_ml.account_id, balance_sheet) + + action_posted_view = self.spread2.open_posted_view() + self.assertTrue(isinstance(action_posted_view, dict)) + self.assertTrue(action_posted_view.get("domain")[0][2]) + self.assertFalse(action_posted_view.get("res_id")) + self.assertTrue(action_posted_view.get("context")) + + action_spread_details = self.invoice_line.spread_details() + self.assertTrue(isinstance(action_spread_details, dict)) + self.assertTrue(action_spread_details.get("res_id")) + + def test_13_link_invoice_line_with_spread_sheet_partial_reconcile(self): + + self.spread2.write( + { + "estimated_amount": 1000.0, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + } + ) + + self.spread2.compute_spread_board() + spread_lines = self.spread2.line_ids + self.assertEqual(len(spread_lines), 13) + self.assertFalse(any(line.move_id for line in spread_lines)) + + spread_lines[0].create_and_reconcile_moves() + spread_lines[1].create_and_reconcile_moves() + spread_lines[2].create_and_reconcile_moves() + spread_lines[3].create_and_reconcile_moves() + + self.assertEqual(spread_lines[0].move_id.state, "posted") + self.assertEqual(spread_lines[1].move_id.state, "posted") + self.assertEqual(spread_lines[2].move_id.state, "posted") + self.assertEqual(spread_lines[3].move_id.state, "posted") + self.assertNotEqual(spread_lines[4].move_id.state, "posted") + + spread_mls = spread_lines[0].move_id.line_ids + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertFalse(spread_ml.matched_debit_ids) + self.assertFalse(spread_ml.matched_credit_ids) + self.assertFalse(spread_ml.full_reconcile_id) + if spread_ml.credit: + self.assertFalse(spread_ml.matched_debit_ids) + self.assertFalse(spread_ml.matched_credit_ids) + self.assertFalse(spread_ml.full_reconcile_id) + + balance_sheet = self.spread2.debit_account_id + self.assertTrue(balance_sheet.reconcile) + + # Assing invoice line to spread + self.spread2.invoice_line_id = self.invoice_line + self.assertEqual(self.invoice_line.spread_id, self.spread2) + + # Validate invoice + self.sale_invoice.action_post() + invoice_mls = self.sale_invoice.invoice_line_ids + self.assertTrue(invoice_mls) + for invoice_ml in invoice_mls: + self.assertEqual(invoice_ml.account_id, balance_sheet) + + spread_lines = self.spread2.line_ids + spread_lines[4].create_and_reconcile_moves() + + self.assertEqual(spread_lines[4].move_id.state, "posted") + + spread_mls = spread_lines[4].move_id.line_ids + self.assertTrue(spread_mls) + for spread_ml in spread_mls: + if spread_ml.debit: + self.assertFalse(spread_ml.matched_debit_ids) + self.assertTrue(spread_ml.matched_credit_ids) + self.assertFalse(spread_ml.full_reconcile_id) + if spread_ml.credit: + self.assertFalse(spread_ml.matched_debit_ids) + self.assertFalse(spread_ml.matched_credit_ids) + self.assertFalse(spread_ml.full_reconcile_id) + + other_journal = self.env["account.journal"].create( + {"name": "Other Journal", "type": "general", "code": "test2"} + ) + with self.assertRaises(ValidationError): + self.spread2.journal_id = other_journal + + with self.assertRaises(UserError): + self.spread2.unlink() + + def test_14_create_all_moves(self): + self.spread.compute_spread_board() + + self.assertEqual(len(self.spread.line_ids), 12) + self.assertFalse(any(line.move_id for line in self.spread.line_ids)) + + # create moves for all the spread lines + self.spread.create_all_moves() + self.assertTrue(all(line.move_id for line in self.spread.line_ids)) + + with self.assertRaises(ValidationError): + self.spread.unlink() + + def test_15_invoice_refund(self): + + self.vendor_bill_line.spread_id = self.spread + + # Validate invoice + self.vendor_bill.action_post() + self.assertTrue(self.vendor_bill.invoice_line_ids.mapped("spread_id")) + + # Create a refund for invoice. + move_reversal = ( + self.env["account.move.reversal"] + .with_context(active_model="account.move", active_ids=self.vendor_bill.ids) + .create( + { + "date": fields.Date.today(), + "reason": "no reason", + "refund_method": "refund", + "journal_id": self.vendor_bill.journal_id.id, + } + ) + ) + reversal = move_reversal.reverse_moves() + refund = self.env["account.move"].browse(reversal["res_id"]) + self.assertFalse(refund.invoice_line_ids.mapped("spread_id")) diff --git a/account_spread_cost_revenue/tests/test_account_spread_cost_revenue.py b/account_spread_cost_revenue/tests/test_account_spread_cost_revenue.py new file mode 100644 index 00000000..936df0c3 --- /dev/null +++ b/account_spread_cost_revenue/tests/test_account_spread_cost_revenue.py @@ -0,0 +1,351 @@ +# Copyright 2018-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +import datetime + +from psycopg2.errors import NotNullViolation + +from odoo.exceptions import ValidationError +from odoo.tests import Form, common +from odoo.tools import mute_logger + + +class TestAccountSpreadCostRevenue(common.TransactionCase): + def setUp(self): + super().setUp() + + self.sales_journal = self.env["account.journal"].create( + {"name": "Customer Invoices - Test", "code": "TEST1", "type": "sale"} + ) + + self.expenses_journal = self.env["account.journal"].create( + {"name": "Vendor Bills - Test", "code": "TEST2", "type": "purchase"} + ) + + self.credit_account = self.env["account.account"].create( + { + "name": "test_account_receivable", + "code": "123", + "account_type": "asset_receivable", + "reconcile": True, + } + ) + + self.debit_account = self.env["account.account"].create( + { + "name": "test account_expenses", + "code": "765", + "account_type": "expense", + "reconcile": True, + } + ) + + self.account_payable = self.env["account.account"].create( + { + "name": "test_account_payable", + "code": "321", + "account_type": "liability_payable", + "reconcile": True, + } + ) + + self.account_revenue = self.env["account.account"].create( + { + "name": "test_account_revenue", + "code": "864", + "account_type": "asset_receivable", + "reconcile": True, + } + ) + + def test_01_account_spread_defaults(self): + this_year = datetime.date.today().year + spread_template = self.env["account.spread.template"].create( + {"name": "test", "spread_account_id": self.debit_account.id} + ) + self.assertEqual(spread_template.spread_type, "sale") + self.assertTrue(spread_template.spread_journal_id) + + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + + self.assertTrue(spread) + self.assertFalse(spread.line_ids) + self.assertFalse(spread.invoice_line_ids) + self.assertFalse(spread.invoice_line_id) + self.assertFalse(spread.invoice_id) + self.assertFalse(spread.analytic_distribution) + self.assertTrue(spread.move_line_auto_post) + self.assertEqual(spread.name, "test") + self.assertEqual(spread.invoice_type, "out_invoice") + self.assertEqual(spread.company_id, self.env.company) + self.assertEqual(spread.currency_id, self.env.company.currency_id) + self.assertEqual(spread.period_number, 12) + self.assertEqual(spread.period_type, "month") + self.assertEqual(spread.debit_account_id, self.debit_account) + self.assertEqual(spread.credit_account_id, self.credit_account) + self.assertEqual(spread.unspread_amount, 0.0) + self.assertEqual(spread.unposted_amount, 0.0) + self.assertEqual(spread.total_amount, 0.0) + self.assertEqual(spread.estimated_amount, 0.0) + self.assertEqual(spread.spread_date, datetime.date(this_year, 1, 1)) + self.assertTrue(spread.journal_id) + self.assertEqual(spread.journal_id.type, "general") + + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) + + def test_02_config_defaults(self): + self.assertFalse(self.env.company.default_spread_revenue_account_id) + self.assertFalse(self.env.company.default_spread_expense_account_id) + self.assertFalse(self.env.company.default_spread_revenue_journal_id) + self.assertFalse(self.env.company.default_spread_expense_journal_id) + + @mute_logger("odoo.sql_db") + def test_03_no_defaults(self): + with self.assertRaises(NotNullViolation): + self.env["account.spread"].create({"name": "test"}) + with self.assertRaises(NotNullViolation): + self.env["account.spread"].create( + {"name": "test", "invoice_type": "out_invoice"} + ) + + @mute_logger("odoo.sql_db") + def test_04_no_defaults(self): + with self.assertRaises(NotNullViolation): + self.env["account.spread"].create( + { + "name": "test", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + with self.assertRaises(NotNullViolation): + self.env["account.spread"].create( + { + "name": "test", + "credit_account_id": self.credit_account.id, + } + ) + + def test_05_config_settings(self): + self.env.company.default_spread_revenue_account_id = self.account_revenue + self.env.company.default_spread_expense_account_id = self.account_payable + self.env.company.default_spread_revenue_journal_id = self.sales_journal + self.env.company.default_spread_expense_journal_id = self.expenses_journal + + self.assertTrue(self.env.company.default_spread_revenue_account_id) + self.assertTrue(self.env.company.default_spread_expense_account_id) + self.assertTrue(self.env.company.default_spread_revenue_journal_id) + self.assertTrue(self.env.company.default_spread_expense_journal_id) + + self.env.user.groups_id += self.env.ref("base.group_multi_company") + + spread_form = Form(self.env["account.spread"]) + spread_form.name = "test" + spread_form.invoice_type = "in_invoice" + spread_form.debit_account_id = self.debit_account + spread_form.credit_account_id = self.credit_account + spread = spread_form.save() + + self.assertTrue(spread) + self.assertFalse(spread.line_ids) + self.assertFalse(spread.invoice_line_ids) + self.assertFalse(spread.invoice_line_id) + self.assertFalse(spread.invoice_id) + self.assertFalse(spread.analytic_distribution) + self.assertTrue(spread.move_line_auto_post) + + defaults = self.env["account.spread"].default_get(["company_id", "currency_id"]) + + self.assertEqual(defaults["company_id"], self.env.company.id) + self.assertEqual(defaults["currency_id"], self.env.company.currency_id.id) + + spread_form = Form(spread) + spread_form.invoice_type = "out_invoice" + spread_form.company_id = self.env.company + spread = spread_form.save() + self.assertEqual(spread.debit_account_id, self.account_revenue) + self.assertFalse(spread.is_debit_account_deprecated) + self.assertEqual(spread.journal_id, self.sales_journal) + self.assertEqual(spread.spread_type, "sale") + + spread_form = Form(spread) + spread_form.invoice_type = "in_invoice" + spread = spread_form.save() + self.assertEqual(spread.credit_account_id, self.account_payable) + self.assertFalse(spread.is_credit_account_deprecated) + self.assertEqual(spread.journal_id, self.expenses_journal) + self.assertEqual(spread.spread_type, "purchase") + + def test_07_create_spread_template(self): + spread_template = self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "sale", + "spread_account_id": self.account_revenue.id, + } + ) + + self.assertEqual(spread_template.company_id, self.env.company) + self.assertTrue(spread_template.spread_journal_id) + + self.env.company.default_spread_revenue_account_id = self.account_revenue + self.env.company.default_spread_expense_account_id = self.account_payable + self.env.company.default_spread_revenue_journal_id = self.sales_journal + self.env.company.default_spread_expense_journal_id = self.expenses_journal + + spread_template.spread_type = "purchase" + self.assertTrue(spread_template.spread_journal_id) + self.assertTrue(spread_template.spread_account_id) + self.assertEqual(spread_template.spread_account_id, self.account_payable) + self.assertEqual(spread_template.spread_journal_id, self.expenses_journal) + + spread_vals = spread_template._prepare_spread_from_template() + self.assertTrue(spread_vals["name"]) + self.assertTrue(spread_vals["template_id"]) + self.assertTrue(spread_vals["journal_id"]) + self.assertTrue(spread_vals["company_id"]) + self.assertTrue(spread_vals["invoice_type"]) + self.assertTrue(spread_vals["credit_account_id"]) + + spread_template.spread_type = "sale" + self.assertTrue(spread_template.spread_journal_id) + self.assertTrue(spread_template.spread_account_id) + self.assertEqual(spread_template.spread_account_id, self.account_revenue) + self.assertEqual(spread_template.spread_journal_id, self.sales_journal) + + spread_vals = spread_template._prepare_spread_from_template() + self.assertTrue(spread_vals["name"]) + self.assertTrue(spread_vals["template_id"]) + self.assertTrue(spread_vals["journal_id"]) + self.assertTrue(spread_vals["company_id"]) + self.assertTrue(spread_vals["invoice_type"]) + self.assertTrue(spread_vals["debit_account_id"]) + + def test_08_check_template_invoice_type(self): + template_sale = self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "sale", + "spread_account_id": self.account_revenue.id, + } + ) + template_purchase = self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "purchase", + "spread_account_id": self.account_payable.id, + } + ) + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + + with self.assertRaises(ValidationError): + spread.template_id = template_purchase + + spread.template_id = template_sale + self.assertEqual(spread.template_id, template_sale) + + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) + + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "in_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + + with self.assertRaises(ValidationError): + spread.template_id = template_sale + + spread.template_id = template_purchase + self.assertEqual(spread.template_id, template_purchase) + + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) + + def test_10_account_spread_unlink(self): + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + spread.unlink() + + def test_11_compute_display_fields(self): + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + spread.company_id.allow_spread_planning = True + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) + + def test_12_compute_display_fields(self): + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + spread.company_id.allow_spread_planning = False + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) + + def test_13_compute_display_fields(self): + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + spread.company_id.force_move_auto_post = True + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertFalse(spread.display_move_line_auto_post) + + def test_14_compute_display_fields(self): + spread = self.env["account.spread"].create( + { + "name": "test", + "invoice_type": "out_invoice", + "debit_account_id": self.debit_account.id, + "credit_account_id": self.credit_account.id, + } + ) + spread.company_id.force_move_auto_post = False + self.assertFalse(spread.display_create_all_moves) + self.assertTrue(spread.display_recompute_buttons) + self.assertTrue(spread.display_move_line_auto_post) diff --git a/account_spread_cost_revenue/tests/test_compute_spread_board.py b/account_spread_cost_revenue/tests/test_compute_spread_board.py new file mode 100644 index 00000000..984e93a6 --- /dev/null +++ b/account_spread_cost_revenue/tests/test_compute_spread_board.py @@ -0,0 +1,725 @@ +# Copyright 2017-2020 Onestein () +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +import datetime + +from odoo.exceptions import UserError +from odoo.tests import Form, common + + +class TestComputeSpreadBoard(common.TransactionCase): + def setUp(self): + super().setUp() + + journal = self.env["account.journal"].create( + {"name": "Test", "type": "general", "code": "test"} + ) + + self.receivable_account = self.env["account.account"].create( + { + "name": "test_account_receivable", + "code": "123", + "account_type": "asset_receivable", + "reconcile": True, + } + ) + + self.expense_account = self.env["account.account"].create( + { + "name": "test account_expenses", + "code": "765", + "account_type": "expense", + "reconcile": True, + } + ) + + self.spread_account = self.env["account.account"].create( + { + "name": "test spread account_expenses", + "code": "321", + "account_type": "expense", + "reconcile": True, + } + ) + + self.spread = self.env["account.spread"].create( + { + "name": "test", + "debit_account_id": self.spread_account.id, + "credit_account_id": self.expense_account.id, + "period_number": 12, + "period_type": "month", + "spread_date": "2017-02-01", + "estimated_amount": 1000.0, + "journal_id": journal.id, + "invoice_type": "in_invoice", + } + ) + + self.spread2 = self.env["account.spread"].create( + { + "name": "test2", + "debit_account_id": self.spread_account.id, + "credit_account_id": self.expense_account.id, + "period_number": 12, + "period_type": "month", + "spread_date": "2017-02-01", + "estimated_amount": 1000.0, + "journal_id": journal.id, + "invoice_type": "out_invoice", + } + ) + + self.spread3 = self.env["account.spread"].create( + { + "name": "test by cal days", + "debit_account_id": self.spread_account.id, + "credit_account_id": self.expense_account.id, + "period_number": 12, + "period_type": "month", + "spread_date": "2017-02-01", + "estimated_amount": 12000.0, + "journal_id": journal.id, + "invoice_type": "out_invoice", + "days_calc": True, + } + ) + + self.template = self.env["account.spread.template"].create( + { + "name": "test", + "spread_type": "purchase", + "period_number": 5, + "period_type": "month", + "start_date": "2017-01-01", + "spread_account_id": self.spread_account.id, + "spread_journal_id": journal.id, + "days_calc": True, + } + ) + + def test_01_supplier_invoice(self): + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 12) + + self.assertEqual(83.33, spread_lines[0].amount) + self.assertEqual(83.33, spread_lines[1].amount) + self.assertEqual(83.33, spread_lines[2].amount) + self.assertEqual(83.33, spread_lines[3].amount) + self.assertEqual(83.33, spread_lines[4].amount) + self.assertEqual(83.33, spread_lines[5].amount) + self.assertEqual(83.33, spread_lines[6].amount) + self.assertEqual(83.33, spread_lines[7].amount) + self.assertEqual(83.33, spread_lines[8].amount) + self.assertEqual(83.33, spread_lines[9].amount) + self.assertEqual(83.33, spread_lines[10].amount) + self.assertEqual(83.37, spread_lines[11].amount) + + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[10].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[11].date) + + for line in spread_lines: + self.assertFalse(line.move_id) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + for line in spread_lines: + line.create_move() + self.assertTrue(line.move_id) + + self.spread.action_recalculate_spread() + spread_lines = self.spread.line_ids + for line in spread_lines: + self.assertTrue(line.move_id) + + def test_02_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + } + ) + self.spread_account.reconcile = True + self.assertTrue(self.spread_account.reconcile) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 13) + + self.assertEqual(67.20, spread_lines[0].amount) + self.assertEqual(83.33, spread_lines[1].amount) + self.assertEqual(83.33, spread_lines[2].amount) + self.assertEqual(83.33, spread_lines[3].amount) + self.assertEqual(83.33, spread_lines[4].amount) + self.assertEqual(83.33, spread_lines[5].amount) + self.assertEqual(83.33, spread_lines[6].amount) + self.assertEqual(83.33, spread_lines[7].amount) + self.assertEqual(83.33, spread_lines[8].amount) + self.assertEqual(83.33, spread_lines[9].amount) + self.assertEqual(83.33, spread_lines[10].amount) + self.assertEqual(83.33, spread_lines[11].amount) + self.assertEqual(16.17, spread_lines[12].amount) + + self.assertEqual(datetime.date(2017, 1, 31), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[10].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[11].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[12].date) + + for line in spread_lines: + self.assertFalse(line.move_id) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + self.spread.line_ids.create_and_reconcile_moves() + for line in self.spread.line_ids: + self.assertTrue(line.move_id) + + def test_03_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 31), + "move_line_auto_post": False, + } + ) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 13) + self.assertEqual(2.69, spread_lines[0].amount) + self.assertEqual(83.33, spread_lines[1].amount) + self.assertEqual(83.33, spread_lines[2].amount) + self.assertEqual(83.33, spread_lines[3].amount) + self.assertEqual(83.33, spread_lines[4].amount) + self.assertEqual(83.33, spread_lines[5].amount) + self.assertEqual(83.33, spread_lines[6].amount) + self.assertEqual(83.33, spread_lines[7].amount) + self.assertEqual(83.33, spread_lines[8].amount) + self.assertEqual(83.33, spread_lines[9].amount) + self.assertEqual(83.33, spread_lines[10].amount) + self.assertEqual(83.33, spread_lines[11].amount) + self.assertEqual(80.68, spread_lines[12].amount) + + self.assertEqual(datetime.date(2017, 1, 31), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[10].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[11].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[12].date) + + for line in spread_lines: + self.assertFalse(line.move_id) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + spread_lines[0].create_move() + spread_lines[1].create_move() + spread_lines[2].create_move() + self.assertTrue(any(line.move_id for line in spread_lines)) + self.assertTrue(any(not line.move_id for line in spread_lines)) + + self.spread._compute_amounts() + self.assertEqual(self.spread.unspread_amount, 830.65) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 13) + self.assertEqual(2.69, spread_lines[0].amount) + self.assertEqual(83.33, spread_lines[1].amount) + self.assertEqual(83.33, spread_lines[2].amount) + self.assertEqual(83.33, spread_lines[3].amount) + self.assertEqual(83.33, spread_lines[4].amount) + self.assertEqual(83.33, spread_lines[5].amount) + self.assertEqual(83.33, spread_lines[6].amount) + self.assertEqual(83.33, spread_lines[7].amount) + self.assertEqual(83.33, spread_lines[8].amount) + self.assertEqual(83.33, spread_lines[9].amount) + self.assertEqual(83.33, spread_lines[10].amount) + self.assertEqual(83.33, spread_lines[11].amount) + self.assertEqual(80.68, spread_lines[12].amount) + + self.assertEqual(datetime.date(2017, 1, 31), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[10].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[11].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[12].date) + + def test_04_supplier_invoice(self): + self.spread.write( + { + "credit_account_id": self.expense_account.id, + "debit_account_id": self.spread_account.id, + "period_number": 3, + "period_type": "year", + "spread_date": datetime.date(2018, 10, 24), + } + ) + + # change the state of invoice to open by clicking Validate button + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 4) + self.assertEqual(333.33, spread_lines[1].amount) + self.assertEqual(333.33, spread_lines[2].amount) + first_amount = spread_lines[0].amount + last_amount = spread_lines[3].amount + remaining_amount = first_amount + last_amount + self.assertAlmostEqual(remaining_amount, 333.34, places=2) + total_line_amount = 0.0 + for line in spread_lines: + total_line_amount += line.amount + self.assertAlmostEqual(total_line_amount, 1000.0, places=2) + + for line in spread_lines: + self.assertFalse(line.move_id) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_05_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 2, 1), + } + ) + + self.spread.compute_spread_board() + + # create moves for all the spread lines and open them + self.spread.line_ids.create_and_reconcile_moves() + for spread_line in self.spread.line_ids: + attrs = spread_line.open_move() + self.assertTrue(isinstance(attrs, dict)) + + # unlink all created moves + self.spread.line_ids.unlink_move() + for spread_line in self.spread.line_ids: + self.assertFalse(spread_line.move_id) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_06_supplier_invoice(self): + # spread date set + self.spread.write( + {"period_number": 3, "period_type": "quarter", "move_line_auto_post": False} + ) + + self.spread.compute_spread_board() + + # create moves for all the spread lines and open them + self.spread.line_ids.create_and_reconcile_moves() + + # check move lines + for spread_line in self.spread.line_ids: + for move_line in spread_line.move_id.line_ids: + spread_account = self.spread.debit_account_id + if move_line.account_id == spread_account: + debit = move_line.debit + self.assertAlmostEqual(debit, spread_line.amount) + + for line in self.spread.line_ids: + self.assertTrue(line.move_id) + self.assertFalse(line.move_id.state == "posted") + + self.assertEqual(self.spread.unspread_amount, 0.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + # try to create move lines again: an error is raised + for line in self.spread.line_ids: + with self.assertRaises(UserError): + line.create_move() + + self.spread.write({"move_line_auto_post": True}) + self.spread.action_recalculate_spread() + + for line in self.spread.line_ids: + self.assertTrue(line.move_id) + self.assertTrue(line.move_id.state == "posted") + + self.assertEqual(self.spread.unspread_amount, 0.0) + self.assertEqual(self.spread.unposted_amount, 0.0) + + def test_07_supplier_invoice(self): + self.spread.write( + { + "period_number": 3, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 1), + "estimated_amount": 345.96, + } + ) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 3) + self.assertAlmostEqual(115.32, spread_lines[0].amount) + self.assertAlmostEqual(115.32, spread_lines[1].amount) + self.assertAlmostEqual(115.32, spread_lines[2].amount) + self.assertEqual(datetime.date(2017, 1, 31), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[2].date) + + for line in spread_lines: + self.assertFalse(line.move_id) + + self.assertEqual(self.spread.unspread_amount, 345.96) + self.assertEqual(self.spread.unposted_amount, 345.96) + + def test_08_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 2, 1), + } + ) + + self.spread.compute_spread_board() + self.assertTrue(self.spread.line_ids) + self.spread.action_undo_spread() + self.assertFalse(self.spread.line_ids) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_09_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 2, 1), + } + ) + + self.spread.compute_spread_board() + for line in self.spread.line_ids: + line.create_move() + self.assertTrue(line.move_id) + action = line.open_move() + self.assertTrue(action) + + self.spread.line_ids.unlink_move() + for line in self.spread.line_ids: + self.assertFalse(line.move_id) + self.assertTrue(self.spread.line_ids) + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_10_create_entries(self): + self.env["account.spread.line"]._create_entries() + self.assertFalse(self.spread.line_ids) + + self.spread.compute_spread_board() + self.env["account.spread.line"]._create_entries() + self.assertTrue(self.spread.line_ids) + for line in self.spread.line_ids: + self.assertTrue(line.move_id) + + def test_11_create_move_sale_invoice(self): + self.spread2.move_line_auto_post = False + self.spread2.compute_spread_board() + for line in self.spread2.line_ids: + self.assertFalse(line.move_id) + line.create_move() + self.assertTrue(line.move_id) + self.assertFalse(line.move_id.state == "posted") + + self.spread2.action_undo_spread() + for line in self.spread2.line_ids: + self.assertFalse(line.move_id) + + self.spread2.action_recalculate_spread() + for line in self.spread2.line_ids: + self.assertTrue(line.move_id) + self.assertTrue(line.move_id) + self.assertFalse(line.move_id.state == "posted") + # try to create move lines again: an error is raised + with self.assertRaises(UserError): + line.create_move() + + def test_12_supplier_invoice_auto_post(self): + # spread date set + self.spread.write( + {"period_number": 8, "period_type": "month", "move_line_auto_post": True} + ) + + self.spread.compute_spread_board() + + # create moves for all the spread lines and open them + self.spread.line_ids.create_and_reconcile_moves() + + # check move lines + for spread_line in self.spread.line_ids: + for move_line in spread_line.move_id.line_ids: + spread_account = self.spread.debit_account_id + if move_line.account_id == spread_account: + debit = move_line.debit + self.assertAlmostEqual(debit, spread_line.amount) + + self.assertTrue(self.spread.move_line_auto_post) + for line in self.spread.line_ids: + self.assertTrue(line.move_id) + self.assertTrue(line.move_id.state == "posted") + + self.assertEqual(self.spread.unspread_amount, 0.0) + self.assertEqual(self.spread.unposted_amount, 0.0) + + def test_13_create_move_in_invoice_auto_post(self): + self.spread2.write({"period_number": 4, "move_line_auto_post": True}) + self.spread_account.reconcile = True + self.assertTrue(self.spread_account.reconcile) + + self.spread2.compute_spread_board() + for line in self.spread2.line_ids: + self.assertFalse(line.move_id) + line.create_move() + self.assertTrue(line.move_id) + self.assertTrue(line.move_id.state == "posted") + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_14_negative_amount(self): + # spread date set + self.spread.write( + { + "estimated_amount": -1000.0, + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + } + ) + self.spread.compute_spread_board() + + spread_lines = self.spread.line_ids + self.assertTrue(spread_lines) + + def test_15_compute_spread_board_line_account_deprecated(self): + self.spread.debit_account_id.deprecated = True + self.assertTrue(self.spread.debit_account_id.deprecated) + + self.assertTrue(self.spread.is_debit_account_deprecated) + self.spread.compute_spread_board() + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_16_compute_spread_board_line_account_deprecated(self): + self.spread.credit_account_id.deprecated = True + self.assertTrue(self.spread.credit_account_id.deprecated) + + self.assertTrue(self.spread.is_credit_account_deprecated) + self.spread.compute_spread_board() + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_17_compute_spread_board_line_account_deprecated(self): + self.spread.compute_spread_board() + self.spread.debit_account_id.deprecated = True + self.assertTrue(self.spread.debit_account_id.deprecated) + + for line in self.spread.line_ids: + self.assertFalse(line.move_id) + with self.assertRaises(UserError): + line.create_move() + + self.assertEqual(self.spread.unspread_amount, 1000.0) + self.assertEqual(self.spread.unposted_amount, 1000.0) + + def test_18_supplier_invoice(self): + # spread date set + self.spread.write( + { + "period_number": 12, + "period_type": "month", + "spread_date": datetime.date(2017, 1, 7), + } + ) + self.spread_account.reconcile = True + self.assertTrue(self.spread_account.reconcile) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 13) + + for line in spread_lines: + self.assertFalse(line.move_id) + + spread_lines[0]._create_moves().action_post() + spread_lines[1]._create_moves().action_post() + spread_lines[2]._create_moves().action_post() + spread_lines[3]._create_moves().action_post() + + self.assertEqual(spread_lines[0].move_id.state, "posted") + self.assertEqual(spread_lines[1].move_id.state, "posted") + self.assertEqual(spread_lines[2].move_id.state, "posted") + self.assertEqual(spread_lines[3].move_id.state, "posted") + + self.assertAlmostEqual(self.spread.unspread_amount, 682.81) + self.assertAlmostEqual(self.spread.unposted_amount, 682.81) + + self.spread.compute_spread_board() + spread_lines = self.spread.line_ids + self.assertEqual(len(spread_lines), 13) + + self.assertEqual(67.20, spread_lines[0].amount) + self.assertEqual(83.33, spread_lines[1].amount) + self.assertEqual(83.33, spread_lines[2].amount) + self.assertEqual(83.33, spread_lines[3].amount) + self.assertEqual(83.33, spread_lines[4].amount) + self.assertEqual(83.33, spread_lines[5].amount) + self.assertEqual(83.33, spread_lines[6].amount) + self.assertEqual(83.33, spread_lines[7].amount) + self.assertEqual(83.33, spread_lines[8].amount) + self.assertEqual(83.33, spread_lines[9].amount) + self.assertEqual(83.33, spread_lines[10].amount) + self.assertEqual(83.33, spread_lines[11].amount) + self.assertEqual(16.17, spread_lines[12].amount) + + self.assertEqual(datetime.date(2017, 1, 31), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[10].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[11].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[12].date) + + self.assertAlmostEqual(self.spread.unspread_amount, 682.81) + self.assertAlmostEqual(self.spread.unposted_amount, 682.81) + + def test_19_supplier_invoice_calc_day(self): + self.assertTrue(self.spread3.days_calc) + self.spread3.compute_spread_board() + spread_lines = self.spread3.line_ids + self.assertEqual(len(spread_lines), 12) + # Calculate by day has formula: + # (amount spread cost / all spread cost day) * day of + self.assertAlmostEqual(920.55, spread_lines[0].amount) + self.assertAlmostEqual(1019.18, spread_lines[1].amount) + self.assertAlmostEqual(986.30, spread_lines[2].amount) + self.assertAlmostEqual(1019.18, spread_lines[3].amount) + self.assertAlmostEqual(986.30, spread_lines[4].amount) + self.assertAlmostEqual(1019.18, spread_lines[5].amount) + self.assertAlmostEqual(1019.18, spread_lines[6].amount) + self.assertAlmostEqual(986.30, spread_lines[7].amount) + self.assertAlmostEqual(1019.18, spread_lines[8].amount) + self.assertAlmostEqual(986.30, spread_lines[9].amount) + self.assertAlmostEqual(1019.18, spread_lines[10].amount) + self.assertAlmostEqual(1019.17, spread_lines[11].amount) # total left + + self.assertEqual(datetime.date(2017, 2, 28), spread_lines[0].date) + self.assertEqual(datetime.date(2017, 3, 31), spread_lines[1].date) + self.assertEqual(datetime.date(2017, 4, 30), spread_lines[2].date) + self.assertEqual(datetime.date(2017, 5, 31), spread_lines[3].date) + self.assertEqual(datetime.date(2017, 6, 30), spread_lines[4].date) + self.assertEqual(datetime.date(2017, 7, 31), spread_lines[5].date) + self.assertEqual(datetime.date(2017, 8, 31), spread_lines[6].date) + self.assertEqual(datetime.date(2017, 9, 30), spread_lines[7].date) + self.assertEqual(datetime.date(2017, 10, 31), spread_lines[8].date) + self.assertEqual(datetime.date(2017, 11, 30), spread_lines[9].date) + self.assertEqual(datetime.date(2017, 12, 31), spread_lines[10].date) + self.assertEqual(datetime.date(2018, 1, 31), spread_lines[11].date) + + # Period Type is 'Quarter' + self.spread3.period_type = "quarter" + self.spread3.compute_spread_board() + spread_lines = self.spread3.line_ids + self.assertEqual(len(spread_lines), 12) + self.assertAlmostEqual(325.27, spread_lines[0].amount) + self.assertAlmostEqual(1068.73, spread_lines[1].amount) + self.assertAlmostEqual(1068.73, spread_lines[2].amount) + self.assertAlmostEqual(1057.12, spread_lines[3].amount) + self.assertAlmostEqual(1045.50, spread_lines[4].amount) + self.assertAlmostEqual(1068.73, spread_lines[5].amount) + self.assertAlmostEqual(1068.73, spread_lines[6].amount) + self.assertAlmostEqual(1057.12, spread_lines[7].amount) + self.assertAlmostEqual(1045.50, spread_lines[8].amount) + self.assertAlmostEqual(1068.73, spread_lines[9].amount) + self.assertAlmostEqual(1068.73, spread_lines[10].amount) + self.assertAlmostEqual(1057.11, spread_lines[11].amount) # total left + + # Period Type is 'Year' and spread date is not first month + self.spread3.period_type = "year" + self.spread3.spread_date = "2017-02-02" + self.spread3.compute_spread_board() + spread_lines = self.spread3.line_ids + self.assertEqual(len(spread_lines), 13) + self.assertAlmostEqual(73.92, spread_lines[0].amount) + self.assertAlmostEqual(999.32, spread_lines[1].amount) + self.assertAlmostEqual(999.32, spread_lines[2].amount) + self.assertAlmostEqual(1002.05, spread_lines[3].amount) + self.assertAlmostEqual(999.32, spread_lines[4].amount) + self.assertAlmostEqual(999.32, spread_lines[5].amount) + self.assertAlmostEqual(999.32, spread_lines[6].amount) + self.assertAlmostEqual(1002.05, spread_lines[7].amount) + self.assertAlmostEqual(999.32, spread_lines[8].amount) + self.assertAlmostEqual(999.32, spread_lines[9].amount) + self.assertAlmostEqual(999.32, spread_lines[10].amount) + self.assertAlmostEqual(1002.05, spread_lines[11].amount) + self.assertAlmostEqual(925.37, spread_lines[12].amount) + + def test_20_supplier_invoice_template(self): + """Test onchange template""" + self.assertEqual(self.spread3.invoice_type, "out_invoice") + with Form(self.spread3) as sp: + sp.template_id = self.template + sp.credit_account_id = self.expense_account + sp.save() + self.assertEqual(self.spread3.invoice_type, "in_invoice") diff --git a/account_spread_cost_revenue/views/account_move.xml b/account_spread_cost_revenue/views/account_move.xml new file mode 100644 index 00000000..bf99920b --- /dev/null +++ b/account_spread_cost_revenue/views/account_move.xml @@ -0,0 +1,68 @@ + + + + account.move + + + + + + + +
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +