Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[16.0] Add module l10n_ch_credit_control_dunning_fees_qr_report #737

Open
wants to merge 2 commits into
base: 16.0
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
78 changes: 78 additions & 0 deletions l10n_ch_credit_control_dunning_fees_qr_report/README.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
==============================
Swiss Credit Control QR report
==============================

..
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! This file is generated by oca-gen-addon-readme !!
!! changes will be overwritten. !!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! source digest: sha256:ba30572df8df628f948364e9c8208bca61775732ce304582f9f1c900e6c8cef9
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

.. |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%2Fl10n--switzerland-lightgray.png?logo=github
:target: https://github.com/OCA/l10n-switzerland/tree/16.0/l10n_ch_credit_control_dunning_fees_qr_report
:alt: OCA/l10n-switzerland
.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png
:target: https://translation.odoo-community.org/projects/l10n-switzerland-16-0/l10n-switzerland-16-0-l10n_ch_credit_control_dunning_fees_qr_report
: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/l10n-switzerland&target_branch=16.0
:alt: Try me on Runboat

|badge1| |badge2| |badge3| |badge4| |badge5|

This module will ensure dunning fees are considered when generating swiss
QR-bill from credit control lines.

**Table of contents**

.. contents::
:local:

Bug Tracker
===========

Bugs are tracked on `GitHub Issues <https://github.com/OCA/l10n-switzerland/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 <https://github.com/OCA/l10n-switzerland/issues/new?body=module:%20l10n_ch_credit_control_dunning_fees_qr_report%0Aversion:%2016.0%0A%0A**Steps%20to%20reproduce**%0A-%20...%0A%0A**Current%20behavior**%0A%0A**Expected%20behavior**>`_.

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

Credits
=======

Authors
~~~~~~~

* Camptocamp

Contributors
~~~~~~~~~~~~

* Anna Janiszewska <anna.janiszewska@camptocamp.com>
* Akim Juillerat <akim.juillerat@camptocamp.com>

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/l10n-switzerland <https://github.com/OCA/l10n-switzerland/tree/16.0/l10n_ch_credit_control_dunning_fees_qr_report>`_ project on GitHub.

You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute.
1 change: 1 addition & 0 deletions l10n_ch_credit_control_dunning_fees_qr_report/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from . import models
20 changes: 20 additions & 0 deletions l10n_ch_credit_control_dunning_fees_qr_report/__manifest__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# Copyright 2022 Camptocamp SA
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).

{
"name": "Swiss Credit Control QR report",
"version": "16.0.1.0.0",
"author": "Camptocamp, Odoo Community Association (OCA)",
"license": "AGPL-3",
"category": "Finance",
"website": "https://github.com/OCA/l10n-switzerland",
"depends": [
"account_credit_control",
"account_credit_control_dunning_fees",
"l10n_ch",
],
"data": [
"reports/swissqr_report.xml",
"reports/credit_control_summary_report.xml",
],
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
from . import credit_control_communication_report
from . import account_move
from . import ir_actions_report
from . import res_partner_bank
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Copyright 2022 Camptocamp SA
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html)

from odoo import models


class AccountMove(models.Model):
_inherit = "account.move"

def get_qr_amount(self):
qr_dunning_fees_amounts = self.env.context.get("qr_dunning_fees_amounts", {})
if self.id in qr_dunning_fees_amounts:
return "{:,.2f}".format(qr_dunning_fees_amounts[self.id]).replace(

Check warning on line 13 in l10n_ch_credit_control_dunning_fees_qr_report/models/account_move.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/account_move.py#L13

Added line #L13 was not covered by tests
",", "\xa0"
)
else:
return "{:,.2f}".format(self.amount_residual).replace(",", "\xa0")
Comment on lines +12 to +17

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
if self.id in qr_dunning_fees_amounts:
return "{:,.2f}".format(qr_dunning_fees_amounts[self.id]).replace(
",", "\xa0"
)
else:
return "{:,.2f}".format(self.amount_residual).replace(",", "\xa0")
if self.id in qr_dunning_fees_amounts:
return "{:,.2f}".format(qr_dunning_fees_amounts[self.id]).replace(
",", "\xa0"
)
return "{:,.2f}".format(self.amount_residual).replace(",", "\xa0")

any comment to explain why this is needed?

Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# Copyright 2022 Camptocamp SA
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html)
import io
from collections import OrderedDict

from odoo import api, models


class ReportSwissQR(models.AbstractModel):
_inherit = "report.l10n_ch.qr_report_main"

@api.model
def _get_report_values(self, docids, data=None):
"""Replace QR URL to consider dunning fees"""
self = self.with_context(credit_control_run_print_report=True)
res = super()._get_report_values(docids, data=data)
dunning_fees_qr_amounts = self.env.context.get("qr_dunning_fees_amounts", {})
if not dunning_fees_qr_amounts:
return res
qr_code_urls = {}
invoices = self.env["account.move"].browse(docids)

Check warning on line 21 in l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py#L20-L21

Added lines #L20 - L21 were not covered by tests
for invoice in invoices:
if invoice.id not in dunning_fees_qr_amounts:
continue
Comment on lines +21 to +24

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
invoices = self.env["account.move"].browse(docids)
for invoice in invoices:
if invoice.id not in dunning_fees_qr_amounts:
continue
invoices = self.env["account.move"].browse(list(dunning_fees_qr_amounts.keys()))
for invoice in invoices:

You know already the ones to browse no?

qr_code_urls[invoice.id] = invoice.partner_bank_id.build_qr_code_base64(

Check warning on line 25 in l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py#L24-L25

Added lines #L24 - L25 were not covered by tests
dunning_fees_qr_amounts[invoice.id],
invoice.ref or invoice.name,
invoice.payment_reference,
invoice.currency_id,
invoice.partner_id,
qr_method="ch_qr",
silent_errors=False,
)
res["qr_code_urls"].update(qr_code_urls)
return res

Check warning on line 35 in l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/credit_control_communication_report.py#L34-L35

Added lines #L34 - L35 were not covered by tests
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
# Copyright 2024 Camptocamp SA
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl)
from odoo import models


class Report(models.Model):
"""Print pay slip form credit line"""

_inherit = "ir.actions.report"

def _render_qweb_pdf_prepare_streams(self, report_ref, data, res_ids=None):
credit_control_communication_report_name = (

Check warning on line 12 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L12

Added line #L12 was not covered by tests
"account_credit_control.report_credit_control_summary"
)
report = self._get_report(report_ref)
report_name = report.report_name

Check warning on line 16 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L15-L16

Added lines #L15 - L16 were not covered by tests
if report_name != credit_control_communication_report_name:
return super()._render_qweb_pdf_prepare_streams(

Check warning on line 18 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L18

Added line #L18 was not covered by tests
report_ref, data, res_ids=res_ids
)

collected_streams = OrderedDict()
communications = self.env["credit.control.communication"].browse(res_ids)

Check warning on line 23 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L22-L23

Added lines #L22 - L23 were not covered by tests

communications_streams = super()._render_qweb_pdf_prepare_streams(

Check warning on line 25 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L25

Added line #L25 was not covered by tests
self.env["ir.actions.report"]._get_report_from_name(
credit_control_communication_report_name
),
data,
res_ids=communications.ids,
)

for com_id, com_streams in communications_streams.items():
collected_streams[com_id] = [com_streams["stream"]]

Check warning on line 34 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L34

Added line #L34 was not covered by tests

for communication in communications:
dunning_fees_qr_amounts = {}

Check warning on line 37 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L37

Added line #L37 was not covered by tests
for cr_line in communication.credit_control_line_ids:
if not cr_line.move_line_id:
continue

Check warning on line 40 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L40

Added line #L40 was not covered by tests

invoice = cr_line.invoice_id
dunning_fees_qr_amounts[invoice.id] = cr_line.balance_due_total

Check warning on line 43 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L42-L43

Added lines #L42 - L43 were not covered by tests

# generate QR slips for each communication as the QR report doesn't
# include valid outlines to split the QRs for each communication afterwards
invoice_ids = list(dunning_fees_qr_amounts.keys())
qr_streams = super(

Check warning on line 48 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L47-L48

Added lines #L47 - L48 were not covered by tests
Report,
self.with_context(
active_ids=invoice_ids,
qr_dunning_fees_amounts=dunning_fees_qr_amounts,
),
)._render_qweb_pdf_prepare_streams(
"l10n_ch.qr_report_main", data, res_ids=invoice_ids
)
qr_streams_to_merge = [
x["stream"] for x in qr_streams.values() if x["stream"]
]
# attach QR reports to related communication report
collected_streams[communication.id].extend(qr_streams_to_merge)

Check warning on line 61 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L61

Added line #L61 was not covered by tests

# merge streams by communication
for com_id, streams_to_merge in collected_streams.items():
result_stream = io.BytesIO()

Check warning on line 65 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L65

Added line #L65 was not covered by tests
with self._merge_pdfs(streams_to_merge) as pdf_merged_stream:
# Write result stream in a new buffer because the result is added to the array
# passed as argument and we want to close streams in this array
result_stream.write(pdf_merged_stream.getvalue())

Check warning on line 69 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L69

Added line #L69 was not covered by tests

for stream in streams_to_merge:
stream.close()

Check warning on line 72 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L72

Added line #L72 was not covered by tests

collected_streams[com_id] = {"stream": result_stream, "attachment": None}

Check warning on line 74 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L74

Added line #L74 was not covered by tests

return collected_streams

Check warning on line 76 in l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py

View check run for this annotation

Codecov / codecov/patch

l10n_ch_credit_control_dunning_fees_qr_report/models/ir_actions_report.py#L76

Added line #L76 was not covered by tests
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
from odoo import models


class ResPartnerBank(models.Model):
_inherit = "res.partner.bank"

def _eligible_for_qr_code(
self, qr_method, debtor_partner, currency, raises_error=True
):
if self.env.context.get("credit_control_run_print_report"):
raises_error = False
res = super()._eligible_for_qr_code(
qr_method, debtor_partner, currency, raises_error=raises_error
)
return res
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
* Anna Janiszewska <anna.janiszewska@camptocamp.com>
* Akim Juillerat <akim.juillerat@camptocamp.com>
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
This module will ensure dunning fees are considered when generating swiss
QR-bill from credit control lines.
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<?xml version="1.0" encoding="utf-8" ?>
<odoo>
<template
id="report_credit_control_summary_document_fees_formatting"
inherit_id="account_credit_control_dunning_fees.report_credit_control_summary_document_fees"
>
<xpath expr="//span[@t-field='l.dunning_fees_amount']" position="attributes">
<attribute
name="t-options"
>{"widget": "monetary", "display_currency": doc.currency_id}</attribute>
</xpath>
</template>

</odoo>
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8" ?>
<odoo>
<template
id="l10n_ch_swissqr_template_inherit"
inherit_id="l10n_ch.l10n_ch_swissqr_template"
>
<xpath expr="//t[@t-set='formated_amount']" position="attributes">
<attribute name="t-value">o.get_qr_amount()</attribute>
</xpath>
</template>
</odoo>
Loading
Loading