diff --git a/l10n_it_fatturapa_out/models/account.py b/l10n_it_fatturapa_out/models/account.py index e036a368a496..2955e7e6c14c 100644 --- a/l10n_it_fatturapa_out/models/account.py +++ b/l10n_it_fatturapa_out/models/account.py @@ -49,12 +49,26 @@ def _compute_fatturapa_state(self): def preventive_checks(self): for invoice in self: + if invoice.state != "posted": + raise UserError( + _("Impossible to generate XML: invoice not posted: %s") + % invoice.name + ) + if not invoice.is_sale_document(): raise UserError( _("Impossible to generate XML: not a customer invoice: %s") % invoice.name ) + if not invoice.fiscal_document_type_id: + raise UserError( + _( + "Invoice %s fiscal document type must be set", + invoice.name, + ) + ) + if ( invoice.invoice_payment_term_id and invoice.invoice_payment_term_id.fatturapa_pt_id.code is False @@ -81,6 +95,28 @@ def preventive_checks(self): ) ) + if not invoice.partner_id.city: + raise UserError(_("Invoice %s partner city must be set", invoice.name)) + + if not invoice.company_id.partner_id.city: + raise UserError( + _( + "Invoice %s city in our company's partner must be set", + invoice.name, + ) + ) + + if ( + invoice.company_id.fatturapa_stabile_organizzazione + and not invoice.company_id.fatturapa_stabile_organizzazione.city + ): + raise UserError( + _( + "Invoice %s city in our company's Stable Organization must be set", + invoice.name, + ) + ) + if not all( aml.tax_ids for aml in invoice.invoice_line_ids if aml.product_id ): diff --git a/l10n_it_fatturapa_out/tests/test_fatturapa_out_noteline.py b/l10n_it_fatturapa_out/tests/test_fatturapa_out_noteline.py index a2d054cec475..7d9004d1b65e 100644 --- a/l10n_it_fatturapa_out/tests/test_fatturapa_out_noteline.py +++ b/l10n_it_fatturapa_out/tests/test_fatturapa_out_noteline.py @@ -47,6 +47,7 @@ def test_1_note_taxes(self): line_form.name = "just a note" line_form.account_id = self.env["account.account"] invoice = move_form.save() + invoice.action_post() res = self.run_wizard(invoice.id) self.assertTrue(res) @@ -85,6 +86,7 @@ def test_2_note_taxes(self): line_form.name = "just a note" line_form.account_id = self.env["account.account"] invoice = move_form.save() + invoice.action_post() res = self.run_wizard(invoice.id) self.assertTrue(res) @@ -131,6 +133,7 @@ def test_3_note_taxes(self): line_form.name = "just a note" line_form.account_id = self.env["account.account"] invoice = move_form.save() + invoice.action_post() res = self.run_wizard(invoice.id) self.assertTrue(res) @@ -184,6 +187,7 @@ def test_4_note_taxes(self): with move_form.invoice_line_ids.edit(0) as line_form: line_form.price_unit = 0.0 + invoice.action_post() res = self.run_wizard(invoice.id) self.assertTrue(res) @@ -221,6 +225,7 @@ def test_5_note_tax_kind_id(self): line_form.name = "just a note" line_form.account_id = self.env["account.account"] invoice = move_form.save() + invoice.action_post() res = self.run_wizard(invoice.id) self.assertTrue(res) diff --git a/l10n_it_fatturapa_out/tests/test_fatturapa_xml_validation.py b/l10n_it_fatturapa_out/tests/test_fatturapa_xml_validation.py index ce5fbd49da73..4eac786700ce 100644 --- a/l10n_it_fatturapa_out/tests/test_fatturapa_xml_validation.py +++ b/l10n_it_fatturapa_out/tests/test_fatturapa_xml_validation.py @@ -832,6 +832,7 @@ def test_multicompany_fail(self): company_form = Form(self.env["res.company"].sudo(True)) company_form.name = "YourCompany 2" company_form.vat = "IT07973780013" + company_form.city = "Roma" company_form.fatturapa_fiscal_position_id = ( self.env.company.fatturapa_fiscal_position_id ) @@ -1009,3 +1010,118 @@ def test_max_invoice_in_xml(self): res = self.run_wizard(invoices.ids) attachments = self.attach_model.browse(res["res_id"]) self.assertEqual(len(attachments), 1) + + def test_preventive_checks(self): + invoice_form = Form( + self.env["account.move"].with_context({"default_move_type": "in_invoice"}) + ) + invoice_form.partner_id = self.res_partner_fatturapa_0 + invoice_form.invoice_date = fields.Date.today() + with invoice_form.line_ids.new() as line_form: + line_form.product_id = self.product_product_10 + line_form.account_id = self.a_sale + line_form.tax_ids.clear() + line_form.tax_ids.add(self.tax_22) + invoice = invoice_form.save() + + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn("invoice not posted", ue.exception.args[0]) + + invoice.action_post() + + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn("not a customer invoice", ue.exception.args[0]) + + # everything's fine with this invoice + invoice_form = Form( + self.env["account.move"].with_context({"default_move_type": "out_invoice"}) + ) + invoice_form.partner_id = self.res_partner_fatturapa_0 + invoice_form.invoice_payment_term_id = self.account_payment_term + with invoice_form.line_ids.new() as line_form: + line_form.product_id = self.product_product_10 + line_form.account_id = self.a_sale + line_form.tax_ids.clear() + line_form.tax_ids.add(self.tax_22) + invoice = invoice_form.save() + invoice.action_post() + res = self.run_wizard(invoice.ids) + attachments = self.attach_model.browse(res["res_id"]) + self.assertEqual(len(attachments), 1) + + # change/remove something and see if preventive_checks() catches it + invoice = invoice.copy() + fiscal_document_type_id = invoice.fiscal_document_type_id + invoice.fiscal_document_type_id = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn("fiscal document type must be set", ue.exception.args[0]) + invoice.fiscal_document_type_id = fiscal_document_type_id + + invoice = invoice.copy() + pt_id = invoice.invoice_payment_term_id.fatturapa_pt_id + invoice.invoice_payment_term_id.fatturapa_pt_id = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn( + "fiscal payment term must be set for the selected payment term", + ue.exception.args[0], + ) + invoice.invoice_payment_term_id.fatturapa_pt_id = pt_id + + invoice = invoice.copy() + pm_id = invoice.invoice_payment_term_id.fatturapa_pm_id + invoice.invoice_payment_term_id.fatturapa_pm_id = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn( + "fiscal payment method must be set for the selected payment term", + ue.exception.args[0], + ) + invoice.invoice_payment_term_id.fatturapa_pm_id = pm_id + + invoice = invoice.copy() + city = invoice.partner_id.city + invoice.partner_id.city = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn("city must be set", ue.exception.args[0]) + invoice.partner_id.city = city + + invoice = invoice.copy() + city = invoice.company_id.partner_id.city + invoice.company_id.partner_id.city = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn("city in our company's partner must be set", ue.exception.args[0]) + invoice.company_id.partner_id.city = city + + invoice = invoice.copy() + invoice.company_id.fatturapa_stabile_organizzazione = ( + invoice.company_id.partner_id.copy() + ) + city = invoice.company_id.fatturapa_stabile_organizzazione.city + invoice.company_id.fatturapa_stabile_organizzazione.city = False + invoice.action_post() + with self.assertRaises(UserError) as ue: + self.run_wizard(invoice.id) + self.assertIn(invoice.name, ue.exception.args[0]) + self.assertIn( + "city in our company's Stable Organization must be set", + ue.exception.args[0], + ) + invoice.company_id.fatturapa_stabile_organizzazione.city = city