[IMP] payment: allow custom providers to follow standard payment logic

* Generate account payments (and require a journal)
* Be displayed as their custom mode instead of always 'Custom'
...

Commit also includes some side bugfixes/cleanup

task-3347338

closes odoo/odoo#126929

Related: odoo/enterprise#43418
Related: odoo/upgrade#4944
Signed-off-by: Antoine Vandevenne (anv) <anv@odoo.com>
This commit is contained in:
Victor Feyens
2023-07-20 03:56:19 +02:00
committed by Antoine Vandevenne (anv)
parent 8ffca9da77
commit fd2fb212c5
6 changed files with 62 additions and 23 deletions
@@ -22,7 +22,7 @@ class PaymentProvider(models.Model):
for provider in self:
payment_method = self.env['account.payment.method.line'].search([
('journal_id.company_id', '=', provider.company_id.id),
('code', '=', provider.code)
('code', '=', provider._get_code())
], limit=1)
if payment_method:
provider.journal_id = payment_method.journal_id
@@ -31,15 +31,14 @@ class PaymentProvider(models.Model):
def _inverse_journal_id(self):
for provider in self:
code = provider._get_code()
payment_method_line = self.env['account.payment.method.line'].search([
('journal_id.company_id', '=', provider.company_id.id),
('code', '=', provider.code),
('code', '=', code),
], limit=1)
if provider.journal_id:
if not payment_method_line:
default_payment_method_id = provider._get_default_payment_method_id(
provider.code
)
default_payment_method_id = provider._get_default_payment_method_id(code)
existing_payment_method_line = self.env['account.payment.method.line'].search([
('payment_method_id', '=', default_payment_method_id),
('journal_id', '=', provider.journal_id.id),
@@ -145,7 +145,7 @@ class PaymentTransaction(models.Model):
)
payment_method_line = self.provider_id.journal_id.inbound_payment_method_line_ids\
.filtered(lambda l: l.code == self.provider_code)
.filtered(lambda l: l.code == self.provider_id._get_code())
payment_values = {
'amount': abs(self.amount), # A tx may have a negative amount, but a payment must >= 0
'payment_type': 'inbound' if self.amount > 0 else 'outbound',
+22
View File
@@ -687,3 +687,25 @@ class PaymentProvider(models.Model):
'token_inline_form_view_id': None,
'express_checkout_form_view_id': None,
}
def _get_provider_name(self):
""" Return the translated name of the provider.
Note: self.ensure_one()
:return: The translated name of the provider.
:rtype: str
"""
self.ensure_one()
return dict(self._fields['code']._description_selection(self.env))[self.code]
def _get_code(self):
""" Return the code of the provider.
Note: self.ensure_one()
:return: The code of the provider.
:rtype: str
"""
self.ensure_one()
return self.code
+10 -5
View File
@@ -6,9 +6,11 @@ from unittest.mock import patch
from lxml import objectify
from odoo.fields import Command
from odoo.addons.base.tests.common import BaseCommon
from odoo.osv.expression import AND
from odoo.tools.misc import hmac as hmac_tool
from odoo.addons.base.tests.common import BaseCommon
_logger = logging.getLogger(__name__)
@@ -132,14 +134,13 @@ class PaymentCommon(BaseCommon):
"""
company = company or cls.env.company
update_values = update_values or {}
provider_domain = cls._get_provider_domain(code)
provider = cls.env['payment.provider'].sudo().search(
[('code', '=', code), ('company_id', '=', company.id)], limit=1
AND([provider_domain, [('company_id', '=', company.id)]]), limit=1
)
if not provider:
base_provider = cls.env['payment.provider'].sudo().search(
[('code', '=', code)], limit=1
)
base_provider = cls.env['payment.provider'].sudo().search(provider_domain, limit=1)
if not base_provider:
_logger.error("no payment.provider found for code %s", code)
return cls.env['payment.provider']
@@ -150,6 +151,10 @@ class PaymentCommon(BaseCommon):
provider.write(update_values)
return provider
@classmethod
def _get_provider_domain(cls, code):
return [('code', '=', code)]
def _create_transaction(self, flow, sudo=True, **values):
default_values = {
'amount': self.amount,
+12 -12
View File
@@ -69,7 +69,7 @@
type="radio"
t-att-checked="token.id == default_payment_option_id"
t-att-data-payment-option-id="token.id"
t-att-data-provider="token.provider_code"
t-att-data-provider="provider._get_code()"
data-payment-option-type="token"/>
<!-- === Token name === -->
<span class="payment_option_name" t-esc="token.display_name"/>
@@ -90,8 +90,8 @@
</span>
<div class="ms-4 fst-italic small text-muted">
Managed by
<span t-esc="dict(provider._fields['code']._description_selection(provider.env))[provider.code]"/>
— created on
<span t-out="provider._get_provider_name()"/>
— created on
<span t-esc="token.create_date.date()"/>
</div>
</label>
@@ -126,7 +126,7 @@
t-att-checked="provider.id == default_payment_option_id"
t-att-class="'' if provider_count + token_count > 1 else 'd-none'"
t-att-data-payment-option-id="provider.id"
t-att-data-provider="provider.code"
t-att-data-provider="provider._get_code()"
data-payment-option-type="provider"/>
<!-- === Provider name === -->
<span class="payment_option_name">
@@ -225,7 +225,7 @@
<t t-set="footer_template_id"
t-value="footer_template_id or 'payment.footer'"/>
<!-- === Tokens === -->
<t t-if="token_count > 0">
<t t-if="token_count > 0">
<span class="fs-4">Saved payment methods</span>
<div class="card">
<t t-foreach="tokens" t-as="token">
@@ -239,7 +239,7 @@
t-att-checked="token.id == default_payment_option_id"
t-att-class="'' if bool(assign_token_route) else 'd-none'"
t-att-data-payment-option-id="token.id"
t-att-data-provider="token.provider_code"
t-att-data-provider="provider._get_code()"
data-payment-option-type="token"/>
<!-- === Token name === -->
<span class="payment_option_name" t-esc="token.display_name"/>
@@ -259,11 +259,11 @@
<i class="fa fa-trash"/> Delete
</button>
<div class="fst-italic small text-muted">
Managed by
<span t-esc="dict(provider._fields['code']._description_selection(provider.env))[provider.code]"/>
– created on
<span t-esc="token.create_date.date()"/>
</div>
Managed by
<span t-out="provider._get_provider_name()"/>
— created on
<span t-esc="token.create_date.date()"/>
</div>
</div>
<!-- === Token inline form === -->
<div t-attf-id="o_payment_token_inline_manage_form_{{token.id}}"
@@ -295,7 +295,7 @@
t-att-checked="provider.id == default_payment_option_id"
t-att-class="'' if provider_count + token_count > 1 else 'd-none'"
t-att-data-payment-option-id="provider.id"
t-att-data-provider="provider.code"
t-att-data-provider="provider._get_code()"
data-payment-option-type="provider"/>
<!-- === Provider name === -->
<span class="payment_option_name">
+13
View File
@@ -0,0 +1,13 @@
# Part of Odoo. See LICENSE file for full copyright and licensing details.
from odoo.osv.expression import OR
from odoo.addons.payment.tests.common import PaymentCommon
class PaymentCustomCommon(PaymentCommon):
@classmethod
def _get_provider_domain(cls, code):
domain = super()._get_provider_domain(code)
return OR([domain, [('custom_mode', '=', code)]])