From 80d02a1c884af13f5b7396aef5549ef0a272c3c1 Mon Sep 17 00:00:00 2001 From: szalatyzuzanna Date: Mon, 30 Sep 2024 14:26:11 +0200 Subject: [PATCH 1/3] [ADD] bc3_importer --- bc3_importer/README.rst | 80 ++ bc3_importer/__init__.py | 2 + bc3_importer/__manifest__.py | 22 + bc3_importer/data/bc3_version_data.xml | 259 ++++ bc3_importer/data/product_data.xml | 99 ++ bc3_importer/data/uom_data.xml | 9 + bc3_importer/i18n/bc3_importer.pot | 577 +++++++++ bc3_importer/i18n/es.po | 580 +++++++++ bc3_importer/models/__init__.py | 2 + bc3_importer/models/bc3_version.py | 166 +++ bc3_importer/models/sale_order.py | 23 + bc3_importer/readme/CONTRIBUTORS.rst | 4 + bc3_importer/readme/DESCRIPTION.rst | 2 + bc3_importer/security/bc3_file_security.xml | 27 + bc3_importer/security/ir.model.access.csv | 9 + bc3_importer/static/description/icon.png | Bin 0 -> 8776 bytes bc3_importer/static/description/index.html | 430 +++++++ bc3_importer/tests/__init__.py | 2 + bc3_importer/tests/bc3_file_test.bc3 | 4 + bc3_importer/tests/test_bc3_import_wizard.py | 32 + bc3_importer/tests/test_bc3_version.py | 60 + bc3_importer/views/bc3_version_views.xml | 161 +++ bc3_importer/views/sale_order_views.xml | 91 ++ bc3_importer/wizard/__init__.py | 1 + bc3_importer/wizard/bc3_import_wizard.py | 1041 +++++++++++++++++ .../wizard/bc3_import_wizard_views.xml | 62 + 26 files changed, 3745 insertions(+) create mode 100644 bc3_importer/README.rst create mode 100644 bc3_importer/__init__.py create mode 100644 bc3_importer/__manifest__.py create mode 100644 bc3_importer/data/bc3_version_data.xml create mode 100644 bc3_importer/data/product_data.xml create mode 100644 bc3_importer/data/uom_data.xml create mode 100644 bc3_importer/i18n/bc3_importer.pot create mode 100644 bc3_importer/i18n/es.po create mode 100644 bc3_importer/models/__init__.py create mode 100644 bc3_importer/models/bc3_version.py create mode 100644 bc3_importer/models/sale_order.py create mode 100755 bc3_importer/readme/CONTRIBUTORS.rst create mode 100755 bc3_importer/readme/DESCRIPTION.rst create mode 100644 bc3_importer/security/bc3_file_security.xml create mode 100644 bc3_importer/security/ir.model.access.csv create mode 100644 bc3_importer/static/description/icon.png create mode 100755 bc3_importer/static/description/index.html create mode 100644 bc3_importer/tests/__init__.py create mode 100644 bc3_importer/tests/bc3_file_test.bc3 create mode 100644 bc3_importer/tests/test_bc3_import_wizard.py create mode 100644 bc3_importer/tests/test_bc3_version.py create mode 100644 bc3_importer/views/bc3_version_views.xml create mode 100644 bc3_importer/views/sale_order_views.xml create mode 100644 bc3_importer/wizard/__init__.py create mode 100644 bc3_importer/wizard/bc3_import_wizard.py create mode 100644 bc3_importer/wizard/bc3_import_wizard_views.xml diff --git a/bc3_importer/README.rst b/bc3_importer/README.rst new file mode 100644 index 0000000..12b92f7 --- /dev/null +++ b/bc3_importer/README.rst @@ -0,0 +1,80 @@ +================== +BC3 files importer +================== + +.. + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + !! This file is generated by oca-gen-addon-readme !! + !! changes will be overwritten. !! + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + !! source digest: sha256:7daee495c7ca99f6178a9535d2bee76b39dd8ee4d83d4515714c7614a99abaf9 + !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! + +.. |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%2Fvertical--construction-lightgray.png?logo=github + :target: https://github.com/OCA/vertical-construction/tree/14.0/bc3_importer + :alt: OCA/vertical-construction +.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png + :target: https://translation.odoo-community.org/projects/vertical-construction-14-0/vertical-construction-14-0-bc3_importer + :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/vertical-construction&target_branch=14.0 + :alt: Try me on Runboat + +|badge1| |badge2| |badge3| |badge4| |badge5| + +Importer of quotations in bc3 format. + + +**Table of contents** + +.. contents:: + :local: + +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 +~~~~~~~ + +* Binhex + +Contributors +~~~~~~~~~~~~ + +* `Binhex `_: + + * Zuzanna Elzbieta Szalaty Szalaty + + +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/vertical-construction `_ project on GitHub. + +You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute. diff --git a/bc3_importer/__init__.py b/bc3_importer/__init__.py new file mode 100644 index 0000000..9b42961 --- /dev/null +++ b/bc3_importer/__init__.py @@ -0,0 +1,2 @@ +from . import models +from . import wizard diff --git a/bc3_importer/__manifest__.py b/bc3_importer/__manifest__.py new file mode 100644 index 0000000..f5aeddd --- /dev/null +++ b/bc3_importer/__manifest__.py @@ -0,0 +1,22 @@ +{ + "name": "BC3 files importer", + "author": "Binhex, Odoo Community Association (OCA)", + "website": "https://github.com/OCA/vertical-construction", + "category": "BC3", + "version": "14.0.1.0.0", + "license": "AGPL-3", + "depends": ["project", "sale_management"], + "data": [ + "security/bc3_file_security.xml", + "security/ir.model.access.csv", + "wizard/bc3_import_wizard_views.xml", + "views/bc3_version_views.xml", + "data/bc3_version_data.xml", + "views/sale_order_views.xml", + "data/uom_data.xml", + "data/product_data.xml", + ], + "external_dependencies": { + "python": ["iteration_utilities", "chardet"], + }, +} diff --git a/bc3_importer/data/bc3_version_data.xml b/bc3_importer/data/bc3_version_data.xml new file mode 100644 index 0000000..347da23 --- /dev/null +++ b/bc3_importer/data/bc3_version_data.xml @@ -0,0 +1,259 @@ + + + + FIEBDC-3-2020v2 + + + + 1 + + False + + + + 2 + + False + + + + 3 + + True + + + + 4 + + False + + + + 5 + + False + + + + 6 + + True + + + + 7 + + False + + + + 8 + + False + + + + 9 + + False + + + + 10 + + False + + + + 11 + + False + + + + 12 + + False + + + + v + ~V | [ PROPIEDAD_ARCHIVO ] | VERSION_FORMATO [ \ DDMMAAAA ] | [ +PROGRAMA_EMISION ] | [ CABECERA ] \ { ROTULO_IDENTIFICACION \ } | [ +JUEGO_CARACTERES ] | [ COMENTARIO ] | [ TIPO INFORMACIÓN ] | [ NÚMERO +CERTIFICACIÓN ] | [ FECHA CERTIFICACIÓN ] | [ URL_BASE ] | + + + + + + + 1 + + False + + + + 2 + + True + + + + 3 + + False + + + + 4 + + False + + + + 5 + + False + + + + 6 + False + + + 7 + + False + + + + c + ~C | CODIGO { \ CODIGO } | [ UNIDAD ] | [ RESUMEN ] | { PRECIO \ } | { FECHA \ } | [ TIPO ] | + + + + + + + 1 + + False + + + 2 + + False + + True + + + + 3 + True + + + + + 4 + + True + + + + + 5 + False + + + 6 + True + + + 7 + True + + + 8 + + True + + + + d + ~D | CODIGO_PADRE | < CODIGO_HIJO \ [ FACTOR ] \ [ RENDIMIENTO ] \ > | < CODIGO_HIJO \ [ FACTOR ] \ [ RENDIMIENTO ] \ {CODIGO_PORCENTAJE ; } \ > | + + + True + + + + + 1 + + True + + + + 2 + + + + + t + ~T | CODIGO_CONCEPTO | TEXTO_DESCRIPTIVO | + + + True + + + + + + + + + + + + + + + + diff --git a/bc3_importer/data/product_data.xml b/bc3_importer/data/product_data.xml new file mode 100644 index 0000000..3cdac78 --- /dev/null +++ b/bc3_importer/data/product_data.xml @@ -0,0 +1,99 @@ + + + + BC3 Template Product (Units) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Template Product (Meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Template Product (Square meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Template Product (Cubic meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Template Product (g) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Template Product (L) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (Units) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (Meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (Square meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (Cubic meter) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (g) + + + BC3 product that will be used if imported product does not exist. + + + BC3 Product (L) + + + BC3 product that will be used if imported product does not exist. + + diff --git a/bc3_importer/data/uom_data.xml b/bc3_importer/data/uom_data.xml new file mode 100644 index 0000000..fe22881 --- /dev/null +++ b/bc3_importer/data/uom_data.xml @@ -0,0 +1,9 @@ + + + + + m2 + + bigger + + diff --git a/bc3_importer/i18n/bc3_importer.pot b/bc3_importer/i18n/bc3_importer.pot new file mode 100644 index 0000000..1e9b539 --- /dev/null +++ b/bc3_importer/i18n/bc3_importer.pot @@ -0,0 +1,577 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * bc3_importer +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 14.0-20231106\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2024-09-30 10:09+0000\n" +"PO-Revision-Date: 2024-09-30 10:09+0000\n" +"Last-Translator: \n" +"Language-Team: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: \n" +"Plural-Forms: \n" + +#. module: bc3_importer +#: model:res.groups,name:bc3_importer.group_bc3_manager +msgid "Administrator" +msgstr "" + +#. module: bc3_importer +#: model:ir.module.category,name:bc3_importer.module_bc3_importer +#: model:ir.module.category,name:bc3_importer.module_bc3_importer_bc3 +#: model:ir.ui.menu,name:bc3_importer.bc3_files +#: model:ir.ui.menu,name:bc3_importer.bc3_menuitem +msgid "BC3" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.view_sales_order_bc3 +msgid "BC3 Info" +msgstr "" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_orders_show +msgid "BC3 Orders" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_cubic_meter +#: model:product.template,name:bc3_importer.product_product_product_cubic_meter_product_template +msgid "BC3 Product (Cubic meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_l +#: model:product.template,name:bc3_importer.product_product_product_l_product_template +msgid "BC3 Product (L)" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_meter +#: model:product.template,name:bc3_importer.product_product_product_meter_product_template +msgid "BC3 Product (Meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_square_meter +#: model:product.template,name:bc3_importer.product_product_product_square_meter_product_template +msgid "BC3 Product (Square meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_units +#: model:product.template,name:bc3_importer.product_product_product_units_product_template +msgid "BC3 Product (Units)" +msgstr "" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_g +#: model:product.template,name:bc3_importer.product_product_product_g_product_template +msgid "BC3 Product (g)" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.action_quotations_bc3 +#: model:ir.ui.menu,name:bc3_importer.bc3_quotations_show +msgid "BC3 Quotations" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_cubic_meter +msgid "BC3 Template Product (Cubic meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_l +msgid "BC3 Template Product (L)" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_meter +msgid "BC3 Template Product (Meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_square_meter +msgid "BC3 Template Product (Square meter)" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_units +msgid "BC3 Template Product (Units)" +msgstr "" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_g +msgid "BC3 Template Product (g)" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_action +#: model:ir.model,name:bc3_importer.model_bc3_version +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "BC3 Version" +msgstr "" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_version_register +msgid "BC3 Version Register" +msgstr "" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_version_register_rule +msgid "BC3 Version Register Rule" +msgstr "" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_version_show +msgid "BC3 Versions" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__bc3_file +msgid "BC3 file" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__bc3_file_name +msgid "BC3 file name" +msgstr "" + +#. module: bc3_importer +#: model:product.product,description_sale:bc3_importer.product_product_product_cubic_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_g +#: model:product.product,description_sale:bc3_importer.product_product_product_l +#: model:product.product,description_sale:bc3_importer.product_product_product_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_square_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_units +#: model:product.template,description_sale:bc3_importer.product_product_product_cubic_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_g_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_l_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_square_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_template_cubic_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_g +#: model:product.template,description_sale:bc3_importer.product_product_product_template_l +#: model:product.template,description_sale:bc3_importer.product_product_product_template_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_square_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_units +#: model:product.template,description_sale:bc3_importer.product_product_product_units_product_template +msgid "BC3 product that will be used if imported product does not exist." +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3 +msgid "BC3 sale order" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_base_url +msgid "Base url" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_import_wizard_form +msgid "Cancel" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_certification_date +msgid "Certification date" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_certification_number +msgid "Certification number" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_character_set +msgid "Character set" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__is_child +msgid "Child" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__code +msgid "Code" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_comment +msgid "Comment" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.action_quotations_bc3 +msgid "Create a new quotation, the first step of a new sale!" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_products +msgid "Create non-existent products" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__create_uid +msgid "Created by" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__create_date +msgid "Created on" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__partner_id +msgid "Customer/Vendor" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__date +msgid "Date" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__product_id +msgid "Default product" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Description" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__display_name +msgid "Display Name" +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Dynamic Product " +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/models/bc3_version.py:0 +#, python-format +msgid "Error in register description or not enough rules" +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Error parsing the file" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__field_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__field_ids +msgid "Field" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_file_property +msgid "File property" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_header +msgid "Header" +msgstr "" + +#. module: bc3_importer +#: model:ir.module.category,description:bc3_importer.module_bc3_importer +msgid "Helps you handle your bc3 files, versions and registers." +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__id +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__id +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__id +msgid "ID" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_identifying_label +msgid "Identifying label" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_import_wizard_form +msgid "Import" +msgstr "" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_files_import +msgid "Import BC3" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_import_wizard_action +msgid "Import BC3 File" +msgstr "" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_import_wizard +msgid "Import BC3 file" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_information_type +msgid "Information Type" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line____last_update +msgid "Last Modified on" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__write_uid +msgid "Last Updated by" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__write_date +msgid "Last Updated on" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__model_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__model_id +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Model" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__name +msgid "Name" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_action +msgid "No bc3 version found. Let's create one!" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_register_action +msgid "No register found. Let's create one!" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_register_rule_action +msgid "No register rule found. Let's create one!" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.action_quotations_bc3 +msgid "" +"Once the quotation is confirmed by the customer, it becomes a sales " +"order.
You will be able to create an invoice and collect the payment." +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Parsing error, missing data" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__primary_key +msgid "Primary key" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_program +msgid "Program" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__project_id +msgid "Project" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__register_id +msgid "Register" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_register_rule_action +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_rule_form_view +msgid "Register Rule" +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/models/bc3_version.py:0 +#, python-format +msgid "Register name should unique" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__register_ids +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "Registers" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__regular_expression +msgid "Regular expression" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__description +msgid "Rule Description" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__rule_ids +msgid "Rule Lines" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Rules" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__sale_id +msgid "Sale Order" +msgstr "" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_sale_order +msgid "Sales Order" +msgstr "" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_sale_order_line +msgid "Sales Order Line" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.action_orders_bc3 +msgid "Sales Orders" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,help:bc3_importer.field_bc3_import_wizard__product_id +msgid "Select a product which will be used in the BC3 file." +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__sequence +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__sequence +msgid "Sequence" +msgstr "" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Show Sale Order" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__edit_existent +msgid "The register may edit existent records" +msgstr "" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_units +#: model:product.template,uom_name:bc3_importer.product_product_product_template_units +#: model:product.template,uom_name:bc3_importer.product_product_product_units_product_template +msgid "Units" +msgstr "" + +#. module: bc3_importer +#: model:res.groups,name:bc3_importer.group_bc3_user +msgid "User" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__version_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__version_id +msgid "Version" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_version_format +msgid "Version / Format" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.view_sales_order_bc3 +msgid "Version Information" +msgstr "" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_register_action +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Version Register" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_version_date +msgid "Version date" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "e.g. FIEBDC-3-2020v2" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "e.g. ~K" +msgstr "" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_square_meter +#: model:product.template,uom_name:bc3_importer.product_product_product_square_meter_product_template +#: model:product.template,uom_name:bc3_importer.product_product_product_template_square_meter +#: model:uom.uom,name:bc3_importer.product_uom_square_meter +msgid "m2" +msgstr "" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_cubic_meter +#: model:product.template,uom_name:bc3_importer.product_product_product_cubic_meter_product_template +#: model:product.template,uom_name:bc3_importer.product_product_product_template_cubic_meter +msgid "m³" +msgstr "" diff --git a/bc3_importer/i18n/es.po b/bc3_importer/i18n/es.po new file mode 100644 index 0000000..4d3f4b6 --- /dev/null +++ b/bc3_importer/i18n/es.po @@ -0,0 +1,580 @@ +# Translation of Odoo Server. +# This file contains the translation of the following modules: +# * bc3_importer +# +msgid "" +msgstr "" +"Project-Id-Version: Odoo Server 14.0-20231106\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2024-09-30 10:14+0000\n" +"PO-Revision-Date: 2024-09-30 12:33+0200\n" +"Last-Translator: \n" +"Language-Team: \n" +"Language: es\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" +"X-Generator: Poedit 3.5\n" + +#. module: bc3_importer +#: model:res.groups,name:bc3_importer.group_bc3_manager +msgid "Administrator" +msgstr "" + +#. module: bc3_importer +#: model:ir.module.category,name:bc3_importer.module_bc3_importer +#: model:ir.module.category,name:bc3_importer.module_bc3_importer_bc3 +#: model:ir.ui.menu,name:bc3_importer.bc3_files +#: model:ir.ui.menu,name:bc3_importer.bc3_menuitem +msgid "BC3" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.view_sales_order_bc3 +msgid "BC3 Info" +msgstr "" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_orders_show +msgid "BC3 Orders" +msgstr "Pedidos BC3" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_cubic_meter +#: model:product.template,name:bc3_importer.product_product_product_cubic_meter_product_template +msgid "BC3 Product (Cubic meter)" +msgstr "Producto BC3 (metro cúbico)" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_l +#: model:product.template,name:bc3_importer.product_product_product_l_product_template +msgid "BC3 Product (L)" +msgstr "Producto BC3 (L)" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_meter +#: model:product.template,name:bc3_importer.product_product_product_meter_product_template +msgid "BC3 Product (Meter)" +msgstr "Producto BC3 (Metro)" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_square_meter +#: model:product.template,name:bc3_importer.product_product_product_square_meter_product_template +msgid "BC3 Product (Square meter)" +msgstr "BC3 Producto (metro cuadrado)" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_units +#: model:product.template,name:bc3_importer.product_product_product_units_product_template +msgid "BC3 Product (Units)" +msgstr "BC3 Producto (Unidades)" + +#. module: bc3_importer +#: model:product.product,name:bc3_importer.product_product_product_g +#: model:product.template,name:bc3_importer.product_product_product_g_product_template +msgid "BC3 Product (g)" +msgstr "BC3 Producto (g)" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.action_quotations_bc3 +#: model:ir.ui.menu,name:bc3_importer.bc3_quotations_show +msgid "BC3 Quotations" +msgstr "Presupuestos BC3" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_cubic_meter +msgid "BC3 Template Product (Cubic meter)" +msgstr "Plantilla BC3 Producto (metro cúbico)" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_l +msgid "BC3 Template Product (L)" +msgstr "Plantilla BC3 Producto (L)" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_meter +msgid "BC3 Template Product (Meter)" +msgstr "Plantilla BC3 Producto (Metro)" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_square_meter +msgid "BC3 Template Product (Square meter)" +msgstr "Plantilla BC3 Producto (metro cuadrado)" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_units +msgid "BC3 Template Product (Units)" +msgstr "Cuenta de gastos en plantilla producto" + +#. module: bc3_importer +#: model:product.template,name:bc3_importer.product_product_product_template_g +msgid "BC3 Template Product (g)" +msgstr "Plantilla BC3 Producto (g)" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_action +#: model:ir.model,name:bc3_importer.model_bc3_version +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "BC3 Version" +msgstr "Versión BC3" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_version_register +msgid "BC3 Version Register" +msgstr "Registro de versión BC3" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_version_register_rule +msgid "BC3 Version Register Rule" +msgstr "Regla de registro de la versión BC3" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_version_show +msgid "BC3 Versions" +msgstr "Versiones BC3" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__bc3_file +msgid "BC3 file" +msgstr "Archivo BC3" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__bc3_file_name +msgid "BC3 file name" +msgstr "Nombre del archivo BC3" + +#. module: bc3_importer +#: model:product.product,description_sale:bc3_importer.product_product_product_cubic_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_g +#: model:product.product,description_sale:bc3_importer.product_product_product_l +#: model:product.product,description_sale:bc3_importer.product_product_product_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_square_meter +#: model:product.product,description_sale:bc3_importer.product_product_product_units +#: model:product.template,description_sale:bc3_importer.product_product_product_cubic_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_g_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_l_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_square_meter_product_template +#: model:product.template,description_sale:bc3_importer.product_product_product_template_cubic_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_g +#: model:product.template,description_sale:bc3_importer.product_product_product_template_l +#: model:product.template,description_sale:bc3_importer.product_product_product_template_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_square_meter +#: model:product.template,description_sale:bc3_importer.product_product_product_template_units +#: model:product.template,description_sale:bc3_importer.product_product_product_units_product_template +msgid "BC3 product that will be used if imported product does not exist." +msgstr "Producto BC3 que se utilizará si no existe el producto importado." + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3 +msgid "BC3 sale order" +msgstr "Pedido de venta BC3" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_base_url +msgid "Base url" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_import_wizard_form +msgid "Cancel" +msgstr "Cancelar" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_certification_date +msgid "Certification date" +msgstr "Fecha de certificación" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_certification_number +msgid "Certification number" +msgstr "Número de certificación" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_character_set +msgid "Character set" +msgstr "Conjunto de caracteres" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__is_child +msgid "Child" +msgstr "Hijo" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__code +msgid "Code" +msgstr "Código" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_comment +msgid "Comment" +msgstr "Comentario" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.action_quotations_bc3 +msgid "Create a new quotation, the first step of a new sale!" +msgstr "Crear un nuevo presupuesto, ¡el primer paso de una nueva venta!" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_products +msgid "Create non-existent products" +msgstr "Crear productos no existentes" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__create_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__create_uid +msgid "Created by" +msgstr "Creado por" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__create_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__create_date +msgid "Created on" +msgstr "Creado el" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__partner_id +msgid "Customer/Vendor" +msgstr "Cliente/Proveedor" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__date +msgid "Date" +msgstr "Fecha" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__product_id +msgid "Default product" +msgstr "Producto por defecto" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Description" +msgstr "Descripción" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__display_name +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__display_name +msgid "Display Name" +msgstr "Nombre mostrado" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Dynamic Product " +msgstr "Producto dinámico " + +#. module: bc3_importer +#: code:addons/bc3_importer/models/bc3_version.py:0 +#, python-format +msgid "Error in register description or not enough rules" +msgstr "Error en la descripción del registro o reglas insuficientes" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Error parsing the file" +msgstr "Error al analizar el archivo" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__field_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__field_ids +msgid "Field" +msgstr "Campo" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_file_property +msgid "File property" +msgstr "Propiedad del archivo" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_header +msgid "Header" +msgstr "Encabezado" + +#. module: bc3_importer +#: model:ir.module.category,description:bc3_importer.module_bc3_importer +msgid "Helps you handle your bc3 files, versions and registers." +msgstr "Le ayuda a manejar sus archivos bc3, versiones y registros." + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__id +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__id +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line__id +msgid "ID" +msgstr "" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_identifying_label +msgid "Identifying label" +msgstr "Etiqueta identificativa" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_import_wizard_form +msgid "Import" +msgstr "Importar" + +#. module: bc3_importer +#: model:ir.ui.menu,name:bc3_importer.bc3_files_import +msgid "Import BC3" +msgstr "Importar BC3" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_import_wizard_action +msgid "Import BC3 File" +msgstr "Importar archivo BC3" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_bc3_import_wizard +msgid "Import BC3 file" +msgstr "Importar archivo BC3" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_information_type +msgid "Information Type" +msgstr "Tipo de información" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order____last_update +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order_line____last_update +msgid "Last Modified on" +msgstr "Última modificación el" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__write_uid +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__write_uid +msgid "Last Updated by" +msgstr "Última actualización por" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__write_date +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__write_date +msgid "Last Updated on" +msgstr "Última actualización el" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__model_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__model_id +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Model" +msgstr "Modelo" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__name +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__name +msgid "Name" +msgstr "Nombre" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_action +msgid "No bc3 version found. Let's create one!" +msgstr "No se ha encontrado ninguna versión de bc3. ¡Vamos a crear una!" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_register_action +msgid "No register found. Let's create one!" +msgstr "No se ha encontrado ningún registro. ¡Vamos a crear uno!" + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.bc3_version_register_rule_action +msgid "No register rule found. Let's create one!" +msgstr "No se ha encontrado ninguna regla de registro. Creemos una." + +#. module: bc3_importer +#: model_terms:ir.actions.act_window,help:bc3_importer.action_quotations_bc3 +msgid "" +"Once the quotation is confirmed by the customer, it becomes a sales order." +"
You will be able to create an invoice and collect the payment." +msgstr "" +"Una vez que el presupuesto es confirmado por el cliente, se convierte en un " +"pedido de venta.
Podrás crear una factura y cobrar el pago." + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Parsing error, missing data" +msgstr "Error de análisis sintáctico, faltan datos" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__primary_key +msgid "Primary key" +msgstr "Clave principal" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_program +msgid "Program" +msgstr "Programa" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__project_id +msgid "Project" +msgstr "Proyecto" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__register_id +msgid "Register" +msgstr "Registro" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_register_rule_action +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_rule_form_view +msgid "Register Rule" +msgstr "Regla de registro" + +#. module: bc3_importer +#: code:addons/bc3_importer/models/bc3_version.py:0 +#, python-format +msgid "Register name should unique" +msgstr "El nombre de registro debe ser único" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version__register_ids +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "Registers" +msgstr "Registros" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__regular_expression +msgid "Regular expression" +msgstr "Expresión regular" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__description +msgid "Rule Description" +msgstr "Descripción de la regla" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__rule_ids +msgid "Rule Lines" +msgstr "Líneas de la regla" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Rules" +msgstr "Reglas" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__sale_id +msgid "Sale Order" +msgstr "Pedido de venta" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_sale_order +msgid "Sales Order" +msgstr "Pedido de venta" + +#. module: bc3_importer +#: model:ir.model,name:bc3_importer.model_sale_order_line +msgid "Sales Order Line" +msgstr "Línea de pedido de venta" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.action_orders_bc3 +msgid "Sales Orders" +msgstr "Pedidos de ventas" + +#. module: bc3_importer +#: model:ir.model.fields,help:bc3_importer.field_bc3_import_wizard__product_id +msgid "Select a product which will be used in the BC3 file." +msgstr "Seleccione el producto que se utilizará en el archivo BC3." + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__sequence +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register_rule__sequence +msgid "Sequence" +msgstr "Secuencia" + +#. module: bc3_importer +#: code:addons/bc3_importer/wizard/bc3_import_wizard.py:0 +#, python-format +msgid "Show Sale Order" +msgstr "Mostrar pedido de venta" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__edit_existent +msgid "The register may edit existent records" +msgstr "El registro puede editar registros existentes" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_units +#: model:product.template,uom_name:bc3_importer.product_product_product_template_units +#: model:product.template,uom_name:bc3_importer.product_product_product_units_product_template +msgid "Units" +msgstr "Unidades" + +#. module: bc3_importer +#: model:res.groups,name:bc3_importer.group_bc3_user +msgid "User" +msgstr "Usuario" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_import_wizard__version_id +#: model:ir.model.fields,field_description:bc3_importer.field_bc3_version_register__version_id +msgid "Version" +msgstr "Versión BC3" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_version_format +msgid "Version / Format" +msgstr "Versión / Formato" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.view_sales_order_bc3 +msgid "Version Information" +msgstr "Información sobre la versión" + +#. module: bc3_importer +#: model:ir.actions.act_window,name:bc3_importer.bc3_version_register_action +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "Version Register" +msgstr "Registro de versiones" + +#. module: bc3_importer +#: model:ir.model.fields,field_description:bc3_importer.field_sale_order__bc3_version_date +msgid "Version date" +msgstr "Fecha de la versión" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_form_view +msgid "e.g. FIEBDC-3-2020v2" +msgstr "" + +#. module: bc3_importer +#: model_terms:ir.ui.view,arch_db:bc3_importer.bc3_version_register_form_view +msgid "e.g. ~K" +msgstr "" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_square_meter +#: model:product.template,uom_name:bc3_importer.product_product_product_square_meter_product_template +#: model:product.template,uom_name:bc3_importer.product_product_product_template_square_meter +#: model:uom.uom,name:bc3_importer.product_uom_square_meter +msgid "m2" +msgstr "" + +#. module: bc3_importer +#: model:product.product,uom_name:bc3_importer.product_product_product_cubic_meter +#: model:product.template,uom_name:bc3_importer.product_product_product_cubic_meter_product_template +#: model:product.template,uom_name:bc3_importer.product_product_product_template_cubic_meter +msgid "m³" +msgstr "" diff --git a/bc3_importer/models/__init__.py b/bc3_importer/models/__init__.py new file mode 100644 index 0000000..51d3907 --- /dev/null +++ b/bc3_importer/models/__init__.py @@ -0,0 +1,2 @@ +from . import bc3_version +from . import sale_order diff --git a/bc3_importer/models/bc3_version.py b/bc3_importer/models/bc3_version.py new file mode 100644 index 0000000..1dabe96 --- /dev/null +++ b/bc3_importer/models/bc3_version.py @@ -0,0 +1,166 @@ +import logging +import re + +from iteration_utilities import duplicates + +from odoo import _, api, fields, models +from odoo.exceptions import ValidationError + +_logger = logging.getLogger(__name__) + + +class Bc3Version(models.Model): + _name = "bc3.version" + _description = "BC3 Version" + _order = "name" + name = fields.Char("Name", required=True) + register_ids = fields.One2many( + "bc3.version.register", "version_id", string="Registers" + ) + + @api.constrains("register_ids") + def _check_registers(self): + for record in self: + if record.register_ids: + register_name = record.register_ids.mapped("name") + if len(list(duplicates(register_name))) > 0: + raise ValidationError(_("Register name should unique")) + + +class Bc3VersionRegister(models.Model): + _name = "bc3.version.register" + _description = "BC3 Version Register" + _order = "name" + name = fields.Selection( + selection=[ + ("v", "~V"), + ("k", "~K"), + ("c", "~C"), + ("d", "~D"), + ("t", "~T"), + ("g", "~G"), + ("f", "~F"), + ], + string="Name", + required=True, + ) + description = fields.Text("Rule Description") + rule_ids = fields.One2many( + "bc3.version.register.rule", "register_id", string="Rule Lines" + ) + version_id = fields.Many2one("bc3.version", string="Version", ondelete="cascade") + model_id = fields.Many2one( + "ir.model", + "Model", + required=True, + ondelete="cascade", + domain=[ + "|", + "|", + ("model", "=", "sale.order"), + ("model", "=", "sale.order.line"), + ("model", "=", "product.product"), + ], + ) + edit_existent = fields.Boolean("The register may edit existent records") + + @api.onchange("description", "rule_ids") + def get_regular_expression(self): + if self.description and self.rule_ids: + self.description[0].lower() + register_line = self.description[1:].rstrip().strip().split("|") + register_line.pop(0) + len_rule_child = len(self.rule_ids.filtered(lambda x: not x.is_child)) + if len(register_line) > len_rule_child: + del register_line[-1] + if not len(register_line) == len( + self.rule_ids.filtered(lambda x: not x.is_child) + ): + raise ValidationError( + _("Error in register description or not enough rules") + ) + i = 0 + for rule in self.rule_ids.filtered(lambda x: not x.is_child): + rule.generate_regular_expression(register_line[i]) + i += 1 + + +class Bc3VersionRegisterRule(models.Model): + _name = "bc3.version.register.rule" + _description = "BC3 Version Register Rule" + _order = "sequence" + + sequence = fields.Integer(string="Sequence") + model_id = fields.Many2one("ir.model", string="Model", ondelete="cascade") + field_id = fields.Many2one( + "ir.model.fields", + "Field", + domain=[ + ("model_id", "=", model_id), + ( + "ttype", + "not in", + [ + "many2one_reference", + "reference", + "serialized", + "job_serialized", + "selection", + ], + ), + ], + ondelete="cascade", + ) + register_id = fields.Many2one( + "bc3.version.register", string="Register", ondelete="cascade" + ) + is_child = fields.Boolean("Child") + regular_expression = fields.Char("Regular expression") + primary_key = fields.Boolean("Primary key") + field_ids = fields.Many2many( + "ir.model.fields", + string="Field", + domain=[ + ( + "ttype", + "not in", + [ + "many2one_reference", + "reference", + "serialized", + "job_serialized", + "selection", + ], + ), + ], + ondelete="cascade", + ) + + def generate_regular_expression(self, line): + code = line + code = code.replace(" ", "").replace("\\", "\\\\?") + pattern3 = r"[^<>\\\[\]{}?]+" + replacement2 = r'([à-ü-À-Üa-zA-Z0-9_.+#;,":/\ \-\%\²\³\=\€\ª\º]+)' + html = re.sub(pattern3, replacement2, code) + pattern6 = r"\{" + replacement6 = "(" + pattern7 = r"\}" + replacement7 = ")*" + html = re.sub(pattern6, replacement6, html) + html = re.sub(pattern7, replacement7, html) + pattern8 = r"\(\\.*\)\*" + replacement8 = '(\\?[à-ü-À-Üa-zA-Z0-9_+.#;,":/\\ \\-\\%\\²\\³\\=\\€\\ª\\º]+)*' + html = re.sub(pattern8, replacement8, html) + html = html.replace("(\\?", "(\\\\?") + pattern9 = r"\[\([^?]*\)\]" + replacement9 = '([à-ü-À-Üa-zA-Z0-9_+.#,:";/\\ \\-\\%\\²\\³\\=\\€\\ª\\º]+)*' + html = re.sub(pattern9, replacement9, html) + pattern10 = r"\[\\.*\+\)\]" + replacement10 = '(\\?[à-ü-À-Üa-zA-Z0-9_+.#,:";/\\ \\-\\%\\²\\³\\=\\€\\ª\\º]+)*' + html = re.sub(pattern10, replacement10, html) + html = html.replace("(\\?", "(\\\\?") + pattern11 = r"\(\(.*\+\)\\\\\?\)\*" + replacement11 = r'([à-ü-À-Üa-zA-Z0-9_+.#,:";/\ \-\%\²\³\=\€\ª\º]+\\\\?)*' + html = re.sub(pattern11, replacement11, html) + html = html.replace("<", "").replace(">", "") + self.regular_expression = html diff --git a/bc3_importer/models/sale_order.py b/bc3_importer/models/sale_order.py new file mode 100644 index 0000000..8ead1d8 --- /dev/null +++ b/bc3_importer/models/sale_order.py @@ -0,0 +1,23 @@ +from odoo import fields, models + + +class SaleOrder(models.Model): + _inherit = "sale.order" + bc3 = fields.Boolean("BC3 sale order") + bc3_file_property = fields.Char("File property") + bc3_version_format = fields.Char("Version / Format") + bc3_version_date = fields.Date("Version date") + bc3_program = fields.Char("Program") + bc3_header = fields.Char("Header") + bc3_identifying_label = fields.Char("Identifying label") + bc3_character_set = fields.Char("Character set") + bc3_comment = fields.Text("Comment") + bc3_information_type = fields.Char("Information Type") + bc3_certification_number = fields.Char("Certification number") + bc3_certification_date = fields.Date("Certification date") + bc3_base_url = fields.Char("Base url") + + +class SaleOrderLine(models.Model): + _inherit = "sale.order.line" + bc3_code = fields.Char("Code") diff --git a/bc3_importer/readme/CONTRIBUTORS.rst b/bc3_importer/readme/CONTRIBUTORS.rst new file mode 100755 index 0000000..97be4f5 --- /dev/null +++ b/bc3_importer/readme/CONTRIBUTORS.rst @@ -0,0 +1,4 @@ +* `Binhex `_: + + * Zuzanna Elzbieta Szalaty Szalaty + diff --git a/bc3_importer/readme/DESCRIPTION.rst b/bc3_importer/readme/DESCRIPTION.rst new file mode 100755 index 0000000..bf862cf --- /dev/null +++ b/bc3_importer/readme/DESCRIPTION.rst @@ -0,0 +1,2 @@ +Importer of quotations in bc3 format. + diff --git a/bc3_importer/security/bc3_file_security.xml b/bc3_importer/security/bc3_file_security.xml new file mode 100644 index 0000000..820b271 --- /dev/null +++ b/bc3_importer/security/bc3_file_security.xml @@ -0,0 +1,27 @@ + + + + BC3 + + Helps you handle your bc3 files, versions and registers. + 10 + + + + User + + + + + + Administrator + + + + + diff --git a/bc3_importer/security/ir.model.access.csv b/bc3_importer/security/ir.model.access.csv new file mode 100644 index 0000000..313adac --- /dev/null +++ b/bc3_importer/security/ir.model.access.csv @@ -0,0 +1,9 @@ +id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink +access_bc3_import_wizard,bc3.import.wizard,model_bc3_import_wizard,bc3_importer.group_bc3_user,1,0,0,0 +access_bc3_version,bc3.version,model_bc3_version,bc3_importer.group_bc3_user,1,0,0,0 +access_bc3_version_register,bc3.version.register,model_bc3_version_register,bc3_importer.group_bc3_user,1,0,0,0 +access_bc3_version_register_rule,bc3.version.register.rule,model_bc3_version_register_rule,bc3_importer.group_bc3_user,1,0,0,0 +access_bc3_import_wizard_manager,bc3.import.wizard.manager,model_bc3_import_wizard,bc3_importer.group_bc3_manager,1,1,1,1 +access_bc3_version_manager,bc3.version-manager,model_bc3_version,bc3_importer.group_bc3_manager,1,1,1,1 +access_bc3_version_register_manager,bc3.version.register.manager,model_bc3_version_register,bc3_importer.group_bc3_manager,1,1,1,1 +access_bc3_version_register_rule_manager,bc3.version.register.rule.manager,model_bc3_version_register_rule,bc3_importer.group_bc3_manager,1,1,1,1 diff --git a/bc3_importer/static/description/icon.png b/bc3_importer/static/description/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..45b34226c46bb5170193e322cd8642623d7ae4fe GIT binary patch literal 8776 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 H75YB_vXmfr literal 0 HcmV?d00001 diff --git a/bc3_importer/static/description/index.html b/bc3_importer/static/description/index.html new file mode 100755 index 0000000..b56f16b --- /dev/null +++ b/bc3_importer/static/description/index.html @@ -0,0 +1,430 @@ + + + + + + +BC3 files importer + + + +
+

BC3 files importer

+ + +

Beta License: AGPL-3 OCA/vertical-construction Translate me on Weblate Try me on Runboat

+

Importer of quotations in bc3 format.

+

Table of contents

+ +
+

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

+
    +
  • Binhex
  • +
+
+
+

Contributors

+ +
+
+

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/vertical-construction project on GitHub.

+

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

+
+
+
+ + diff --git a/bc3_importer/tests/__init__.py b/bc3_importer/tests/__init__.py new file mode 100644 index 0000000..ce1d18d --- /dev/null +++ b/bc3_importer/tests/__init__.py @@ -0,0 +1,2 @@ +from . import test_bc3_import_wizard +from . import test_bc3_version diff --git a/bc3_importer/tests/bc3_file_test.bc3 b/bc3_importer/tests/bc3_file_test.bc3 new file mode 100644 index 0000000..fb06cb6 --- /dev/null +++ b/bc3_importer/tests/bc3_file_test.bc3 @@ -0,0 +1,4 @@ +~V|SOFT S.A.|FIEBDC-3/2002|Presto 8.8||ANSI|\n' +'~K|\2\2\3\2\2\2\2\EUR\|0|\n' +'~C|%0.03||Medios Auxiliares|10|030223|0|\n' +'~C|A03B0010|m³|Hormigón aligerado de cemento y picón.|38.34|011222|3| diff --git a/bc3_importer/tests/test_bc3_import_wizard.py b/bc3_importer/tests/test_bc3_import_wizard.py new file mode 100644 index 0000000..153e16d --- /dev/null +++ b/bc3_importer/tests/test_bc3_import_wizard.py @@ -0,0 +1,32 @@ +import base64 +import os + +from odoo.tests.common import TransactionCase + +__location__ = os.path.realpath(os.path.join(os.getcwd(), os.path.dirname(__file__))) + + +class TestBC3ImportWizard(TransactionCase): + def setUp(self): + super(TestBC3ImportWizard, self).setUp() + with open(os.path.join(__location__, "bc3_file_test.bc3"), "rb") as file: + bc3_content = file.read() + self.bc3_import_wizard = self.env["bc3.import.wizard"].create( + { + "bc3_file": base64.b64encode(bc3_content), + "bc3_file_name": "test.bc3", + "project_id": self.env.ref("project.project_project_1").id, + "version_id": self.env.ref("bc3_importer.bc3_version_2020_v2").id, + "partner_id": self.env.ref("base.res_partner_1").id, + "create_products": False, + "sale_id": self.env.ref("sale.sale_order_1").id, + } + ) + + def test_do_action(self): + result = self.bc3_import_wizard.do_action() + self.assertEqual(result["res_model"], "sale.order", "Wrong model") + self.assertEqual(result["res_id"], self.bc3_import_wizard.sale_id.id) + self.assertEqual(result["view_mode"], "form") + self.assertEqual(result["target"], "current") + self.assertEqual(result["type"], "ir.actions.act_window") diff --git a/bc3_importer/tests/test_bc3_version.py b/bc3_importer/tests/test_bc3_version.py new file mode 100644 index 0000000..e72394c --- /dev/null +++ b/bc3_importer/tests/test_bc3_version.py @@ -0,0 +1,60 @@ +from odoo.exceptions import ValidationError +from odoo.tests.common import TransactionCase + + +class TestBC3Version(TransactionCase): + def setUp(self): + super(TestBC3Version, self).setUp() + self.bc3_version = self.env["bc3.version"].create({"name": "Test Version"}) + self.bc3_version_register = self.env["bc3.version.register"].create( + { + "name": "v", + "description": "v|rule1|rule2|rule3", + "version_id": self.bc3_version.id, + "model_id": self.env.ref("base.model_res_partner").id, + } + ) + self.bc3_version_register_rule_1 = self.env["bc3.version.register.rule"].create( + { + "sequence": 1, + "model_id": self.env.ref("base.model_res_partner").id, + "field_id": self.env.ref("base.field_res_partner__name").id, + "register_id": self.bc3_version_register.id, + "is_child": False, + } + ) + self.bc3_version_register_rule_2 = self.env["bc3.version.register.rule"].create( + { + "sequence": 2, + "model_id": self.env.ref("base.model_res_partner").id, + "field_id": self.env.ref("base.field_res_partner__email").id, + "register_id": self.bc3_version_register.id, + "is_child": False, + } + ) + self.bc3_version_register_rule_3 = self.env["bc3.version.register.rule"].create( + { + "sequence": 3, + "model_id": self.env.ref("base.model_res_partner").id, + "field_id": self.env.ref("base.field_res_partner__phone").id, + "register_id": self.bc3_version_register.id, + "is_child": False, + } + ) + + def test_get_regular_expression_success(self): + self.bc3_version_register.get_regular_expression() + self.assertTrue(self.bc3_version_register_rule_1.regular_expression) + self.assertTrue(self.bc3_version_register_rule_2.regular_expression) + self.assertTrue(self.bc3_version_register_rule_3.regular_expression) + + def test_get_regular_expression_error_in_description(self): + self.bc3_version_register.description = "v|rule1" + with self.assertRaises(ValidationError): + self.bc3_version_register.get_regular_expression() + + def test_get_regular_expression_not_enough_rules(self): + self.bc3_version_register_rule_2.unlink() + self.bc3_version_register_rule_3.unlink() + with self.assertRaises(ValidationError): + self.bc3_version_register.get_regular_expression() diff --git a/bc3_importer/views/bc3_version_views.xml b/bc3_importer/views/bc3_version_views.xml new file mode 100644 index 0000000..032cbba --- /dev/null +++ b/bc3_importer/views/bc3_version_views.xml @@ -0,0 +1,161 @@ + + + + + BC3 Version + bc3.version + tree,form + +

+ No bc3 version found. Let's create one! +

+
+
+ + bc3.version.form + bc3.version + +
+ +
+

+ +

+
+ + + +
+
+
+
+ + bc3.version.tree + bc3.version + + + + + + + + + + + + Version Register + bc3.version.register + tree,form + +

+ No register found. Let's create one! +

+
+
+ + bc3.version.form.register + bc3.version.register + +
+ +
+

+ +

+
+ + + + + + + + + + + + + + + + + + + + +
+
+
+
+ + bc3.version.register.tree + bc3.version.register + + + + + + + + + Register Rule + bc3.version.register.rule + tree,form + +

+ No register rule found. Let's create one! +

+
+
+ + + bc3.version.register.rule.form + bc3.version.register.rule + +
+ + + + + + + + + + + +
+
+
+ + bc3.version.register.rule.tree + bc3.version.register.rule + + + + + + + +
diff --git a/bc3_importer/views/sale_order_views.xml b/bc3_importer/views/sale_order_views.xml new file mode 100644 index 0000000..9a81461 --- /dev/null +++ b/bc3_importer/views/sale_order_views.xml @@ -0,0 +1,91 @@ + + + + BC3 Quotations + ir.actions.act_window + sale.order + + tree,kanban,form,calendar,pivot,graph,activity + + [('bc3', '=', True)] + {'default_bc3': 1} + +

+ Create a new quotation, the first step of a new sale! +

+ Once the quotation is confirmed by the customer, it becomes a sales order.
You will be able to create an invoice and collect the payment. +

+
+
+ + Sales Orders + ir.actions.act_window + sale.order + tree,form,calendar,graph,kanban,pivot + + [('state', 'not in', ('draft', 'sent', 'cancel'))] + {'default_bc3': 1} + + + sale.order.form + sale.order + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
diff --git a/bc3_importer/wizard/__init__.py b/bc3_importer/wizard/__init__.py new file mode 100644 index 0000000..2d79918 --- /dev/null +++ b/bc3_importer/wizard/__init__.py @@ -0,0 +1 @@ +from . import bc3_import_wizard diff --git a/bc3_importer/wizard/bc3_import_wizard.py b/bc3_importer/wizard/bc3_import_wizard.py new file mode 100644 index 0000000..0ee8266 --- /dev/null +++ b/bc3_importer/wizard/bc3_import_wizard.py @@ -0,0 +1,1041 @@ +import base64 +import io +import os +import re +import tempfile +from datetime import datetime + +import chardet + +from odoo import _, api, fields, models +from odoo.exceptions import UserError, ValidationError + +BC3_PRODUCTS = {} +created_product = False +parse_later = [] +lines = {} +erase_lines = [] + + +class BC3ImportWizard(models.TransientModel): + _name = "bc3.import.wizard" + _description = "Import BC3 file" + + @api.model + def _default_version(self): + return self.env.ref("bc3_importer.bc3_version_2020_v2") or self.env[ + "bc3.version" + ].search([], limit=1) + + bc3_file = fields.Binary(string="BC3 file", required=True) + bc3_file_name = fields.Char(string="BC3 file name") + project_id = fields.Many2one("project.project", string="Project") + version_id = fields.Many2one( + "bc3.version", string="Version", ondelete="cascade", default=_default_version + ) + partner_id = fields.Many2one( + comodel_name="res.partner", + string="Customer/Vendor", + store=True, + readonly=False, + ondelete="restrict", + domain="['|', ('parent_id','=', False), ('is_company','=', True)]", + check_company=True, + ) + create_products = fields.Boolean("Create non-existent products") + product_id = fields.Many2one( + "product.product", + string="Default product", + ondelete="cascade", + help="Select a product which will be used in the BC3 file.", + ) + sale_id = fields.Many2one("sale.order", "Sale Order") + sequence = fields.Integer() + + def do_action(self): + self.ensure_one() + self.get_uom_products() + self.sequence = 0 + self.sale_id = ( + self.env["sale.order"] + .create({"partner_id": self.partner_id.id, "bc3": True}) + .id + ) + # decode the base64 encoded data + data = base64.decodebytes(self.bc3_file) + # create a temporary file, and save the bc3 + fobj = tempfile.NamedTemporaryFile(delete=False) + fname = fobj.name + fobj.write(data) + fobj.close() + try: + rawdata = open(fname, "rb").read() + encoding = chardet.detect(rawdata)["encoding"] + file_content = list( + filter( + None, + io.open(fname, "rt", encoding=encoding, errors="replace") + .read() + .split("~"), + ) + ) + for f in file_content: + self._parse_register(f) + # do stuff here + finally: + # delete the file when done + os.unlink(fname) + seq = 0 + line_ids = [] + sorted_chapters = dict(sorted(lines.items())) + for key in sorted_chapters: + s = ( + self.env["sale.order.line"] + .sudo() + .search( + [("bc3_code", "=", key), ("order_id", "=", self.sale_id.id)], + limit=1, + ) + ) + if s and ( + (s.price_unit == 1 and s.product_uom_qty == 1) + or (s.price_unit == 0 and s.product_uom_qty == 1) + or ("%" in s.bc3_code) + or (s.price_unit == 1) + ): + s.sudo().unlink() + self.env["sale.order.line"].sudo().search( + [("id", "in", sorted_chapters[key])] + ).unlink() + elif s: + if s.id not in line_ids: + line_ids.append(s.id) + s.write({"sequence": seq}) + seq += 1 + for line in ( + self.env["sale.order.line"] + .sudo() + .search( + [ + ("order_id", "=", self.sale_id.id), + ("id", "in", sorted_chapters[key]), + ] + ) + .sorted("name") + ): + if line: + if ( + (line.price_unit == 1 and line.product_uom_qty == 1) + or (line.price_unit == 0 and line.product_uom_qty == 1) + or ("%" in line.bc3_code) + or (line.price_unit == 1) + or not line.price_subtotal + ): + line.sudo().unlink() + elif line.id not in line_ids: + line_ids.append(line.id) + line.sudo().write({"sequence": seq}) + seq += 1 + elif not s and key == "0": + for line in ( + self.env["sale.order.line"] + .sudo() + .search( + [ + ("order_id", "=", self.sale_id.id), + ("id", "in", sorted_chapters[key]), + ] + ) + .sorted("name") + ): + if line: + if ( + (line.price_unit == 1 and line.product_uom_qty == 1) + or (line.price_unit == 0 and line.product_uom_qty == 1) + or ("%" in line.bc3_code) + or (line.price_unit == 1) + ): + line.sudo().unlink() + else: + line_ids.append(line.id) + line.sudo().write({"sequence": seq}) + seq += 1 + for s in self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id)], order="sequence asc" + ): + if ( + (s.price_unit == 1 and s.product_uom_qty == 1) + or (s.price_unit == 0 and s.product_uom_qty == 1) + or (s.bc3_code and "%" in s.bc3_code) + or (s.price_unit == 1) + ) and not s.display_type: + s.sudo().unlink() + elif s.id not in line_ids and not s.display_type == "line_note": + s.sudo().unlink() + elif s.bc3_code not in lines and s.display_type == "line_section": + s.sudo().unlink() + elif s.display_type == "line_section": + next_sequence = ( + self.env["sale.order.line"] + .sudo() + .search( + [ + ("order_id", "=", self.sale_id.id), + ("display_type", "=", "line_section"), + ("sequence", ">", s.sequence), + ], + limit=1, + ) + ) + if next_sequence and next_sequence.sequence == s.sequence + 1: + s.sudo().unlink() + for c in erase_lines: + line = ( + self.env["sale.order.line"] + .sudo() + .search([("bc3_code", "=", c), ("order_id", "=", self.sale_id.id)]) + ) + if line and not (c in lines): + line.sudo().unlink() + return { + "name": _("Show Sale Order"), + "type": "ir.actions.act_window", + "view_type": "form", + "view_mode": "form", + "res_model": "sale.order", + "views": [(self.env.ref("sale.view_order_form").id, "form")], + "view_id": self.env.ref("sale.view_order_form").id, + "target": "current", + "res_id": self.sale_id.id, + } + + def parse_line(self, line): + split_line = line.rstrip().strip().split("|") + return split_line + + @api.model + def _parse_register_sale_order( + self, parsed_line, rules, current_register, red=False + ): + if len(parsed_line) == len(rules): + i = 0 + for rule in rules: + if len(parsed_line[i]) == 1: + self.sale_id[rule.field_id.name] = self._parse_data( + parsed_line[i][0], rule.field_id.ttype + ) + elif len(parsed_line[i]) > 1: + if self.sale_id[rule.field_id.name]: + self.sale_id[rule.field_id.name] += self._parse_child_data( + parsed_line[i], rule.field_id.ttype + ) + else: + self.sale_id[rule.field_id.name] = self._parse_child_data( + parsed_line[i], rule.field_id.ttype + ) + i += 1 + return True + + # and "\\" not in line[i] + @api.model + def _parse_register_product_product(self, line, rules, current_register, red=False): + return True + + @api.model + def _search_create_product(self, code): + product = self.env["product.template"].search( + [("default_code", "ilike", code[0])], limit=1 + ) + if product: + return product + else: + if self.create_products: + code_temp = "" + if len(code) > 1: + for c in code: + code_temp += c + "-" + else: + code_temp = code + product = self.env["product.template"].create( + { + "name": _("Dynamic Product ") + code_temp, + "default_code": code_temp, + } + ) + else: + # Por defecto se ponen unidades + product = self.env.ref("bc3_importer.product_product_product_units") + return product + + @api.model + def _search_create_uom(self, name): + uom = False + if name == "m3" or name == "M3" or name == "m³": + uom = self.env.ref("uom.product_uom_cubic_meter").id or False + elif name == "m²" or name == "M2" or name == "m2": + uom = self.env.ref("bc3_importer.product_uom_square_meter").id or False + elif name == "ud": + uom = self.env.ref("uom.product_uom_unit").id or False + else: + uom = ( + self.env["uom.uom"] + .search( + [ + "|", + "|", + ("name", "in", name), + ("name", "in", name.upper()), + ("name", "in", name.lower()), + ], + limit=1, + ) + .id + or False + ) + return uom + + def _parse_repeats_line(self, existent_line, temp_line, sale_order_line): + create_line = False + if ( + existent_line + and not existent_line.id == sale_order_line.id + and not existent_line.display_type + and not sale_order_line.display_type + ): + if not self.line_in_any_dict(sale_order_line.id): + erase_lines.append(temp_line["bc3_code"]) + return + if existent_line and not existent_line.id == sale_order_line.id and lines: + if not self.line_in_dict( + existent_line.bc3_code, sale_order_line.id + ) and not (sale_order_line.id in self.sale_id.order_line.ids): + create_line = True + elif self.line_in_any_dict(sale_order_line.id): + create_line = True + if create_line: + sale_order_line = sale_order_line.copy( + { + "order_id": self.sale_id.id, + "price_unit": sale_order_line.price_unit, + } + ) + if ( + sale_order_line + and "price_unit" in temp_line + and float(temp_line["price_unit"]) == 1.0 + ): + temp_line["price_unit"] = sale_order_line.price_unit + sale_order_line.sudo().write(temp_line) + else: + if ( + "product_uom_qty" in temp_line + and float(temp_line["product_uom_qty"]) == 1.0 + and sale_order_line.product_uom_qty + and not sale_order_line.display_type + ): + temp_line["product_uom_qty"] = sale_order_line.product_uom_qty + elif not sale_order_line.product_uom_qty == 1: + temp_line["product_uom_qty"] = ( + float(temp_line["product_uom_qty"]) + + sale_order_line.product_uom_qty + ) + if ( + "price_unit" in temp_line + and float(temp_line["price_unit"]) == 1.0 + and not sale_order_line.display_type + ): + temp_line["price_unit"] = sale_order_line.price_unit + if "name" in temp_line and sale_order_line.name: + temp_line["name"] = sale_order_line.name + "-" + temp_line["name"] + if sale_order_line.display_type: + temp_line["product_uom_qty"] = 0 + temp_line["price_unit"] = 0 + sale_order_line.sudo().write(temp_line) + if ( + existent_line + and not existent_line.id == sale_order_line.id + and existent_line.display_type + and existent_line.display_type == "line_section" + ): + if existent_line.bc3_code in lines: + lines[existent_line.bc3_code].append(sale_order_line.id) + else: + lines[existent_line.bc3_code] = [sale_order_line.id] + + def _parse_repeats_line_product(self, temp_line, seq, existent_line): + product = self.env.ref("bc3_importer.product_product_product_units") + if "bc3_code" in temp_line: + temp_line["name"] = temp_line["bc3_code"] or product.default_code or "Line" + else: + temp_line["name"] = product.default_code or "Line" + temp_line["product_id"] = product.id + temp_line["product_uom"] = product.uom_id.id + temp_line["order_id"] = self.sale_id.id + temp_line["sequence"] = seq + if "price_unit" in temp_line and float(temp_line["price_unit"]) == 1.0: + s = self.env["sale.order.line"].search( + [ + ("order_id", "=", self.sale_id.id), + ("bc3_code", "=", temp_line["bc3_code"]), + ("price_unit", ">", 1), + ], + limit=1, + ) + if s: + temp_line["price_unit"] = s.price_unit + sale_order_line = self.env["sale.order.line"].create(temp_line) + if ( + existent_line + and not existent_line.id == sale_order_line.id + and existent_line.display_type + and existent_line.display_type == "line_section" + ): + if existent_line.bc3_code in lines: + lines[existent_line.bc3_code].append(sale_order_line.id) + else: + lines[existent_line.bc3_code] = [sale_order_line.id] + + def _parse_repeats( + self, rules, i, dependent_rules, parsed_line, line, parent_seq, existent_line + ): + if rules[i] in dependent_rules: + z = 0 + while z < len(parsed_line[i]): + j = i + counter = 0 + temp_line = {} + if parent_seq: + seq = parent_seq + 1 + # self.lines_reorder(seq) + else: + seq = self.sequence + self.sequence += 1 + while counter < len(dependent_rules[rules[i]]): + if len(parsed_line[j]) == 0: + temp_line[ + dependent_rules[rules[i]][counter]["field_id"]["name"] + ] = False + else: + temp_line[ + dependent_rules[rules[i]][counter]["field_id"]["name"] + ] = parsed_line[j][z] + j += 1 + counter += 1 + z += 1 + temp_line["sequence"] = seq + sale_order_line = False + if "bc3_code" in temp_line: + sale_order_line = self.env["sale.order.line"].search( + [ + ("order_id", "=", self.sale_id.id), + ("bc3_code", "=", temp_line["bc3_code"]), + ] + ) + if len(sale_order_line) > 1: + if existent_line: + chapter = existent_line.bc3_code + for s in sale_order_line: + if chapter in lines and s.id in lines[chapter]: + sale_order_line = s + else: + sale_order_line = False + if sale_order_line: + self._parse_repeats_line(existent_line, temp_line, sale_order_line) + else: + self._parse_repeats_line_product(temp_line, seq, existent_line) + + if line: + line = {} + + def _update_line(self, line, seq): + s = False + if "bc3_code" in line: + line["bc3_code"] = line["bc3_code"].replace("#", "") + s = self.env["sale.order.line"].search( + [ + ("order_id", "=", self.sale_id.id), + ("bc3_code", "=", line["bc3_code"].replace("#", "")), + ] + ) + if s: + for sale_order_line in s: + if sale_order_line.bc3_code in erase_lines: + erase_lines.remove(sale_order_line.bc3_code) + if ( + "product_uom_qty" in line + and sale_order_line.product_uom_qty + and not sale_order_line.display_type + ): + line["product_uom_qty"] = float(line["product_uom_qty"]) + float( + sale_order_line.product_uom_qty + ) + if ( + "price_unit" in line + and sale_order_line.price_unit + and sale_order_line.price_unit > 1 + and line["price_unit"] == 1 + and not sale_order_line.display_type + ): + line["price_unit"] = sale_order_line.price_unit + if "name" in line and sale_order_line.name: + if sale_order_line.name not in line["name"]: + line["name"] = sale_order_line.name + "- " + line["name"] + if sale_order_line.display_type: + line["product_uom_qty"] = 0 + line["price_unit"] = 0 + sale_order_line.sudo().write(line) + + else: + product = self.env.ref("bc3_importer.product_product_product_units") + + if "bc3_code" in line: + if "name" in line: + line["name"] = ( + line["bc3_code"] or product.default_code or "Line" + ) + line["name"] + else: + line["name"] = line["bc3_code"] or product.default_code or "Line" + else: + if "name" in line: + line["name"] = (product.default_code or "Line") + line["name"] + else: + line["name"] = product.default_code or "Line" + line["product_id"] = product.id + line["product_uom"] = product.uom_id.id + line["order_id"] = self.sale_id.id + line["sequence"] = seq + sale_order_line = self.env["sale.order.line"].create(line) + + def _parse_register_edit_sale_order_line( + self, parsed_line, rules, dependent_rules, rule_ids, current_register, red=False + ): + if len(parsed_line) == len(rules): + primary_key_id = parsed_line[0][0] + existent_line = self.search_line(primary_key_id.replace("#", "")) + parent_seq = False + # Está dentro de un capítulo + if existent_line: + parent_seq = existent_line.sequence + + elif "#" in primary_key_id and not existent_line: + existent_line = ( + self.env["sale.order.line"] + .sudo() + .create( + { + "name": primary_key_id.replace("#", ""), + "display_type": "line_section", + "bc3_code": primary_key_id.replace("#", ""), + "order_id": self.sale_id.id, + } + ) + ) + + i = 0 + seq = False + line = {} + while i < len(rules): + # Repetidos + if rules[i]["id"] in rule_ids: + self._parse_repeats( + rules, + i, + dependent_rules, + parsed_line, + line, + parent_seq, + existent_line, + ) + # Únicos + else: + if rules[i]["field_id"]["name"]: + if len(parsed_line[i]) > 0: + line[rules[i]["field_id"]["name"]] = parsed_line[i][0] + if parent_seq: + seq = parent_seq + 1 + # self.lines_reorder(seq) + else: + seq = self.sequence + self.sequence += 1 + line["sequence"] = seq + i += 1 + # Solo cuando actualiza un dato -> lo hago para todos + + if line: + self._update_line(line, seq) + + return + + @api.model + def search_seq_line(self, seq): + sale_order_line = self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("bc3_code", "=", seq)], limit=1 + ) + return sale_order_line.sequence or False + + @api.model + def search_line(self, code): + code = code.replace("#", "") + a = self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("bc3_code", "=", code)], limit=1 + ) + if not a: + a = self.env["sale.order.line"].search( + [ + ("order_id", "=", self.sale_id.id), + ("bc3_code", "=", code.split(".")[0]), + ], + limit=1, + ) + return a + + @api.model + def search_lines(self, code): + code = code.replace("#", "") + a = self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("bc3_code", "=", code)] + ) + return a + + @api.model + def lines_reorder(self, seq): + sale_order_line = self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("sequence", "=", seq)], limit=1 + ) + if sale_order_line: + for s in self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("sequence", ">=", seq)] + ): + s.write({"sequence": s.sequence + 1}) + return + + def _parse_register_sale_order_line_sl( + self, rule, parsed_line, line, i, product_name, product + ): + if (not rule.field_id.relation) or ( + rule.field_id.relation and rule.field_id.relation == "product.template" + ): + if ( + not rule.field_id.name == "product_template_id" + and not rule.field_id.name == "categ_id" + ): + if len(parsed_line[i]) == 1 and parsed_line[i]: + line[rule.field_id.name] = self._parse_data( + parsed_line[i][0], rule.field_id.ttype + ) + elif len(parsed_line[i]) > 1: + if rule.field_id.name in line: + line[rule.field_id.name] += self._parse_child_data( + parsed_line[i], rule.field_id.ttype + ) + else: + line[rule.field_id.name] = self._parse_child_data( + parsed_line[i], rule.field_id.ttype + ) + elif rule.field_id.name == "product_template_id": + if len(parsed_line[i]) == 1 and parsed_line[i]: + product_name = self._parse_data( + parsed_line[i][0], rule.field_id.ttype + ) + elif rule.field_id.relation and rule.field_id.relation == "uom.uom": + if len(parsed_line[i]) == 1 and parsed_line[i]: + uom_id = int(self._search_create_uom(parsed_line[i][0])) + line[rule.field_id.name] = uom_id + if product and product.uom_id and not product.uom_id.id == uom_id: + if created_product: + product.uom_id = uom_id + else: + if uom_id in BC3_PRODUCTS: + product = BC3_PRODUCTS[uom_id] + else: + product = self.env.ref( + "bc3_importer.product_product_product_units" + ) + line["product_id"] = product.id + line["product_uom"] = product.uom_id.id + return product_name + + def _parse_line_t(self, line_t, line): + for t in line_t: + if t.display_type: + line["price_unit"] = 0.0 + line["product_id"] = False + line["product_uom_qty"] = 0.0 + + if "display_type" in line and not t.display_type: + if not t.product_uom_qty > 1: + a = t.read(["sequence", "bc3_code"])[0] + a["order_id"] = self.sale_id.id + a.update(line) + t.unlink() + sale_order_line = self.env["sale.order.line"].create(a) + if ( + sale_order_line.display_type + and sale_order_line.display_type == "line_note" + ): + if "0" in lines: + lines["0"].append(sale_order_line.id) + else: + lines["0"] = [sale_order_line.id] + else: + line["display_type"] = False + t.write(line) + + else: + t.write(line) + if t.display_type and line_t.display_type == "line_note": + if "0" in lines: + lines["0"].append(line_t.id) + else: + lines["0"] = [line_t.id] + + @api.model + def _parse_register_sale_order_line( + self, parsed_line, rules, current_register, red=False + ): + product_name = "" + if len(parsed_line) == len(rules): + # Se busca el codigo del producto + if not len(parsed_line[0]) > 0: + return + if len(parsed_line[0]) > 0 and "%" in parsed_line[0][0]: + return + line_t = self.search_lines(parsed_line[0][0]) + product = self._search_create_product(parsed_line[0]) + if not line_t: + line = { + "name": product.default_code or parsed_line[0], + "product_id": product.id, + "product_uom_qty": 1, + "qty_delivered": 1, + "product_uom": product.uom_id.id, + "order_id": self.sale_id.id, + "sequence": self.sequence, + } + self.sequence += 1 + else: + line = {} + i = len(rules) - 1 + for rule in rules.sorted(key="sequence", reverse=True): + # Sale order line + if rule.model_id.model == "sale.order.line": + product_name = self._parse_register_sale_order_line_sl( + rule, parsed_line, line, i, product_name, product + ) + + elif rule.model_id.model == "product.template": + if len(parsed_line[i]) == 1: + line_type = int(self._parse_data(parsed_line[i][0], "char")) + if line_type == 0 and "##" in parsed_line[0][0]: + line["display_type"] = "line_note" + elif line_type == 0 and "#" in parsed_line[0][0]: + line["display_type"] = "line_section" + i -= 1 + line["name"] = "[" + line["bc3_code"] + "] " + product_name + if self.create_products: + product.name = product_name + if not line_t: + if "display_type" in line: + line["price_unit"] = 0.0 + line["product_id"] = False + line["product_uom_qty"] = 0.0 + sale_order_line = self.env["sale.order.line"].create(line) + if ( + sale_order_line.display_type + and sale_order_line.display_type == "line_note" + ): + if "0" in lines: + lines["0"].append(sale_order_line.id) + else: + lines["0"] = [sale_order_line.id] + else: + self._parse_line_t(line_t, line) + return True + + @api.model + def _parse_data(self, data, field_type): + data = data.replace("\\", "").replace("#", "") + if field_type in ["char", "text"]: + return data + if field_type == "date": + # if odd -> 0 + if not len(data) % 2 == 0: + data += "0" + # AA + if len(data) == 2: + return datetime.strptime(data, "%y").date() + # MMAA + elif len(data) == 4: + return datetime.strptime(data, "%m%y").date() + # DDMMAA + elif len(data) == 6: + return datetime.strptime(data, "%d%m%y").date() + # DDMMAAAA + elif len(data) == 8: + return datetime.strptime(data, "%d%m%Y").date() + return data + return data + + @api.model + def _parse_child_data(self, data, field_type): + if field_type == "char" or field_type == "text": + result = "" + for d in data: + d = d.replace("\\", "").replace("\\\\", "") + result += d + ";" + return result + elif field_type == "float": + if len(data) > 0: + return float(data[-1].replace("\\", "")) + else: + return float(data.replace("\\", "")) + return data + + def _parse_register_data( + self, register_rules, register_line, current_register, model, render_func + ): + i = 0 + regular_expression = [] + parser_result = [] + for r in register_rules.filtered(lambda x: not x.is_child): + regular_expression.append(r.regular_expression) + if len(regular_expression) == len(register_line): + i = 0 + while i < len(regular_expression): + parser_result.append( + self._get_results( + regular_expression[i], register_line[i].replace("\n", "") + ) + ) + i += 1 + else: + raise ValidationError(_("Parsing error, missing data")) + if len(parser_result) > 0: + final_result = [] + for i in parser_result: + if len(i) > 1: + for j in i: + final_result.append(j) + elif not len(i) == 0: + final_result.append(i[0]) + else: + final_result.append([]) + if register_rules[0].register_id.edit_existent: + repeat_value_rule = {} + rule_ids = [] + temp_r = [] + for r in register_rules: + if r.field_ids: + for a in register_rules.filtered( + lambda rule: rule.field_id in r.field_ids + ): + temp_r.append(a) + temp_r.insert(0, r) + repeat_value_rule[r] = temp_r + rule_ids.append(r.id) + rule_ids += register_rules.filtered( + lambda rule: rule.field_id in r.field_ids + ).ids + + render_func = getattr(self, "_parse_register_edit_" + model, None) + if not render_func: + raise UserError(_("Error parsing the file")) + render_func( + final_result, + register_rules, + repeat_value_rule, + rule_ids, + current_register, + ) + return + else: + render_func(final_result, register_rules, current_register) + + def _parse_register(self, line): + register_type = line[0].lower() + current_register = register_type + register_line = ( + line[1:] + .rstrip() + .replace("�", "") + .replace("(", ",") + .replace(")", ",") + .replace("[", ",") + .replace("]", ",") + .strip() + .split("|") + ) + register_rules = ( + self.env["bc3.version.register"] + .search( + [ + ("name", "ilike", register_type), + ("version_id", "=", self.version_id.id), + ], + limit=1, + ) + .rule_ids + ) + + if ( + register_rules + and register_rules[0] + and register_rules[0].register_id.model_id + ): + model = register_rules[0].register_id.model_id.model.replace(".", "_") + register_line.pop(0) + if len(register_line) < len( + register_rules.filtered(lambda x: not x.is_child) + ): + for _i in range( + abs( + len(register_rules.filtered(lambda x: not x.is_child)) + - len(register_line) + ) + ): + register_line.append("") + elif len(register_line) > len( + register_rules.filtered(lambda x: not x.is_child) + ): + for _i in range( + abs( + len(register_rules.filtered(lambda x: not x.is_child)) + - len(register_line) + ) + ): + register_line.pop() + render_func = getattr(self, "_parse_register_" + model, None) + if not render_func: + raise UserError(_("Error parsing the file")) + + self._parse_register_data( + register_rules, register_line, current_register, model, render_func + ) + + # Parseo + def get_groups_matches(self, group_id, check_list, text, group_pattern): + # Hay que revisar las substring: + for a in check_list: + t = text[a[0] : a[1]] + matches = re.finditer(group_pattern[group_id]["expression"], t) + last_index = (0, 0) + for match in matches: + if match.lastindex: + for index in range(1, match.lastindex + 1): + group_pattern[str(group_id)]["groups"].insert( + 0, match.group(index) + ) + if not last_index[0] == match.span(index)[0]: + group_pattern[str(group_id)]["check"].append( + (last_index[0], match.span(index)[0]) + ) + group_pattern[str(group_id)]["check"].remove(a) + if len(group_pattern[group_id]["check"]) > 0: + self.get_groups_matches( + group_id, group_pattern[group_id]["check"], t, group_pattern + ) + else: + return True + + def _parse_matches(self, matches, group_pattern): + for match in matches: + # Recorro los grupos + # Empiezo en 1 porque el primer grupo es todo el match, no me interesa + last_index = (0, 0) + if match.lastindex: + if match.lastindex > 1: + for index in range(1, match.lastindex + 1): + if str(index) in group_pattern and match.group(index): + group_pattern[str(index)]["groups"].append( + match.group(index) + ) + # Es el primer grupo + if index == 1: + last_index = match.span(index) + else: + if not last_index[1] == match.span(index)[0]: + group_pattern[str(index)]["check"].append( + (last_index[1], match.span(index)[0]) + ) + last_index = match.span(index) + else: + for index in range(1, match.lastindex + 1): + if str(index) in group_pattern and match.group(index): + group_pattern[str(index)]["groups"].append( + match.group(index) + ) + if not last_index[1] == match.span(index)[0]: + group_pattern[str(index)]["check"].append( + (last_index[1], match.span(index)[0]) + ) + last_index = match.span(index) + return group_pattern + + def _get_results(self, pattern, text): + text = text.rstrip() + result = [] + if pattern: + pattern_2 = pattern.split("(") + group_pattern = {} + counter = 1 + for p in pattern_2: + if p: + group_pattern[str(counter)] = { + "expression": "(" + p, + "groups": [], + "check": [], + } + counter += 1 + matches = re.finditer(pattern, text) + group_pattern = self._parse_matches(matches, group_pattern) + + # Reviso los checks + for i in group_pattern: + if len(group_pattern[i]["check"]) > 0: + self.get_groups_matches( + i, group_pattern[i]["check"], text, group_pattern + ) + for i in group_pattern: + result.append(group_pattern[i]["groups"]) + return result + + @api.model + def get_uom_products(self): + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_units").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_units") + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_meter").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_meter") + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_square_meter").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_square_meter") + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_cubic_meter").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_cubic_meter") + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_g").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_g") + BC3_PRODUCTS[ + self.env.ref("bc3_importer.product_product_product_l").uom_id.id + ] = self.env.ref("bc3_importer.product_product_product_l") + + @api.model + def line_in_dict(self, code, line_id): + if code in lines and line_id in lines[code]: + return True + return False + + @api.model + def line_in_any_dict(self, line_id): + a = self.env["sale.order.line"].search( + [("order_id", "=", self.sale_id.id), ("id", "=", int(line_id))] + ) + if a: + if a in lines: + return True + else: + for d in lines: + if line_id in lines[d]: + return True + return False diff --git a/bc3_importer/wizard/bc3_import_wizard_views.xml b/bc3_importer/wizard/bc3_import_wizard_views.xml new file mode 100644 index 0000000..a24243c --- /dev/null +++ b/bc3_importer/wizard/bc3_import_wizard_views.xml @@ -0,0 +1,62 @@ + + + + bc3.import.wizard.wizard.form + bc3.import.wizard + +
+ + + + + + + + + + + +
+
+
+
+
+ + Import BC3 File + bc3.import.wizard + form + new + + + + + +
From 2ae293f4ad71fbde217fb5671955346f23bed1b9 Mon Sep 17 00:00:00 2001 From: szalatyzuzanna Date: Mon, 30 Sep 2024 16:07:07 +0200 Subject: [PATCH 2/3] [IMP] : black, isort, prettier --- requirements.txt | 3 +++ setup/bc3_importer/odoo/addons/bc3_importer | 1 + setup/bc3_importer/setup.py | 6 ++++++ 3 files changed, 10 insertions(+) create mode 100644 requirements.txt create mode 120000 setup/bc3_importer/odoo/addons/bc3_importer create mode 100644 setup/bc3_importer/setup.py diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..39acb10 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,3 @@ +# generated from manifests external_dependencies +chardet +iteration_utilities diff --git a/setup/bc3_importer/odoo/addons/bc3_importer b/setup/bc3_importer/odoo/addons/bc3_importer new file mode 120000 index 0000000..98e58ed --- /dev/null +++ b/setup/bc3_importer/odoo/addons/bc3_importer @@ -0,0 +1 @@ +../../../../bc3_importer \ No newline at end of file diff --git a/setup/bc3_importer/setup.py b/setup/bc3_importer/setup.py new file mode 100644 index 0000000..28c57bb --- /dev/null +++ b/setup/bc3_importer/setup.py @@ -0,0 +1,6 @@ +import setuptools + +setuptools.setup( + setup_requires=['setuptools-odoo'], + odoo_addon=True, +) From fa9a41d6960d56764a2a58b69b52575615679445 Mon Sep 17 00:00:00 2001 From: szalatyzuzanna Date: Mon, 30 Sep 2024 16:14:32 +0200 Subject: [PATCH 3/3] [MIG] bc3_importer: Migration to 15.0 --- bc3_importer/README.rst | 12 ++++++------ bc3_importer/__manifest__.py | 2 +- bc3_importer/models/bc3_version.py | 7 +++---- bc3_importer/static/description/index.html | 8 ++++---- 4 files changed, 14 insertions(+), 15 deletions(-) diff --git a/bc3_importer/README.rst b/bc3_importer/README.rst index 12b92f7..53b2579 100644 --- a/bc3_importer/README.rst +++ b/bc3_importer/README.rst @@ -7,7 +7,7 @@ BC3 files importer !! This file is generated by oca-gen-addon-readme !! !! changes will be overwritten. !! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! - !! source digest: sha256:7daee495c7ca99f6178a9535d2bee76b39dd8ee4d83d4515714c7614a99abaf9 + !! source digest: sha256:8a4bde5a231ae421d0dfff998e5965e0beb4a08527805b41ad0d3f40a3781be4 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! .. |badge1| image:: https://img.shields.io/badge/maturity-Beta-yellow.png @@ -17,13 +17,13 @@ BC3 files importer :target: http://www.gnu.org/licenses/agpl-3.0-standalone.html :alt: License: AGPL-3 .. |badge3| image:: https://img.shields.io/badge/github-OCA%2Fvertical--construction-lightgray.png?logo=github - :target: https://github.com/OCA/vertical-construction/tree/14.0/bc3_importer + :target: https://github.com/OCA/vertical-construction/tree/15.0/bc3_importer :alt: OCA/vertical-construction .. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png - :target: https://translation.odoo-community.org/projects/vertical-construction-14-0/vertical-construction-14-0-bc3_importer + :target: https://translation.odoo-community.org/projects/vertical-construction-15-0/vertical-construction-15-0-bc3_importer :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/vertical-construction&target_branch=14.0 + :target: https://runboat.odoo-community.org/builds?repo=OCA/vertical-construction&target_branch=15.0 :alt: Try me on Runboat |badge1| |badge2| |badge3| |badge4| |badge5| @@ -42,7 +42,7 @@ Bug Tracker Bugs are tracked on `GitHub Issues `_. In case of trouble, please check there if your issue has already been reported. If you spotted it first, help us to smash it by providing a detailed and welcomed -`feedback `_. +`feedback `_. Do not contact contributors directly about support or help with technical issues. @@ -75,6 +75,6 @@ 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/vertical-construction `_ project on GitHub. +This module is part of the `OCA/vertical-construction `_ project on GitHub. You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute. diff --git a/bc3_importer/__manifest__.py b/bc3_importer/__manifest__.py index f5aeddd..ce24938 100644 --- a/bc3_importer/__manifest__.py +++ b/bc3_importer/__manifest__.py @@ -3,7 +3,7 @@ "author": "Binhex, Odoo Community Association (OCA)", "website": "https://github.com/OCA/vertical-construction", "category": "BC3", - "version": "14.0.1.0.0", + "version": "15.0.1.0.0", "license": "AGPL-3", "depends": ["project", "sale_management"], "data": [ diff --git a/bc3_importer/models/bc3_version.py b/bc3_importer/models/bc3_version.py index 1dabe96..274f90d 100644 --- a/bc3_importer/models/bc3_version.py +++ b/bc3_importer/models/bc3_version.py @@ -13,7 +13,7 @@ class Bc3Version(models.Model): _name = "bc3.version" _description = "BC3 Version" _order = "name" - name = fields.Char("Name", required=True) + name = fields.Char(required=True) register_ids = fields.One2many( "bc3.version.register", "version_id", string="Registers" ) @@ -41,7 +41,6 @@ class Bc3VersionRegister(models.Model): ("g", "~G"), ("f", "~F"), ], - string="Name", required=True, ) description = fields.Text("Rule Description") @@ -90,8 +89,8 @@ class Bc3VersionRegisterRule(models.Model): _description = "BC3 Version Register Rule" _order = "sequence" - sequence = fields.Integer(string="Sequence") - model_id = fields.Many2one("ir.model", string="Model", ondelete="cascade") + sequence = fields.Integer() + model_id = fields.Many2one("ir.model", ondelete="cascade") field_id = fields.Many2one( "ir.model.fields", "Field", diff --git a/bc3_importer/static/description/index.html b/bc3_importer/static/description/index.html index b56f16b..75893fa 100755 --- a/bc3_importer/static/description/index.html +++ b/bc3_importer/static/description/index.html @@ -368,9 +368,9 @@

BC3 files importer

!! This file is generated by oca-gen-addon-readme !! !! changes will be overwritten. !! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! -!! source digest: sha256:7daee495c7ca99f6178a9535d2bee76b39dd8ee4d83d4515714c7614a99abaf9 +!! source digest: sha256:8a4bde5a231ae421d0dfff998e5965e0beb4a08527805b41ad0d3f40a3781be4 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! --> -

Beta License: AGPL-3 OCA/vertical-construction Translate me on Weblate Try me on Runboat

+

Beta License: AGPL-3 OCA/vertical-construction Translate me on Weblate Try me on Runboat

Importer of quotations in bc3 format.

Table of contents

@@ -389,7 +389,7 @@

Bug Tracker

Bugs are tracked on GitHub Issues. In case of trouble, please check there if your issue has already been reported. If you spotted it first, help us to smash it by providing a detailed and welcomed -feedback.

+feedback.

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

@@ -421,7 +421,7 @@

Maintainers

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/vertical-construction project on GitHub.

+

This module is part of the OCA/vertical-construction project on GitHub.

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