add payment_redsys_preauth
This commit is contained in:
parent
0f2c8c0565
commit
08e34c1426
18 changed files with 1043 additions and 0 deletions
133
payment_redsys_preauth/README.rst
Normal file
133
payment_redsys_preauth/README.rst
Normal file
|
|
@ -0,0 +1,133 @@
|
||||||
|
===========================================
|
||||||
|
Pasarela de pago Redsys con preautorización
|
||||||
|
===========================================
|
||||||
|
|
||||||
|
..
|
||||||
|
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
|
!! This file is generated by oca-gen-addon-readme !!
|
||||||
|
!! changes will be overwritten. !!
|
||||||
|
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
|
!! source digest: sha256:1eb9535d052a619aa545a383869076ca1dc1fade22746cb3fe13afa726c3e3a3
|
||||||
|
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
|
|
||||||
|
.. |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-Criptomart%2Ffoodcoopbcn-lightgray.png?logo=github
|
||||||
|
:target: https://github.com/Criptomart/foodcoopbcn/tree/12.0/payment_redsys_preauth
|
||||||
|
:alt: Criptomart/foodcoopbcn
|
||||||
|
|
||||||
|
|badge1| |badge2| |badge3|
|
||||||
|
|
||||||
|
Este módulo añade la opción de pago a través de la pasarela de Redsys con preautorización con tarjeta bancaria.
|
||||||
|
|
||||||
|
**Table of contents**
|
||||||
|
|
||||||
|
.. contents::
|
||||||
|
:local:
|
||||||
|
|
||||||
|
Configuration
|
||||||
|
=============
|
||||||
|
|
||||||
|
Parámetros
|
||||||
|
~~~~~~~~~~
|
||||||
|
|
||||||
|
* **Nombre del comercio**: Indicaremos el nombre del comercio.
|
||||||
|
|
||||||
|
* **Número de comercio (FUC)**: Indicaremos el número de comercio que
|
||||||
|
nuestra entidad nos ha comunicado.
|
||||||
|
|
||||||
|
* **Clave secreta de encriptación**: Indicaremos la clave de encriptación
|
||||||
|
que tiene el comercio.
|
||||||
|
|
||||||
|
* **Número de terminal**: Indicaremos el terminal del TPV.
|
||||||
|
|
||||||
|
* **Tipo de firma**: Seleccionaremos el tipo de firma del comercio.
|
||||||
|
|
||||||
|
* **Tipo de moneda**: Seleccionaremos la moneda de nuestro terminal TPV
|
||||||
|
(Normalmente EUR - Euros).
|
||||||
|
|
||||||
|
* **Tipo de transacción**: Indicaremos el tipo de transacción, 1.
|
||||||
|
|
||||||
|
* **Idioma TPV**: Indicaremos el idioma en el TPV.
|
||||||
|
|
||||||
|
* **Método de pago**: Indicaremos que tipo de pago se debe aceptar, pago con
|
||||||
|
tarjeta, Bizum u otro de los disponibles.
|
||||||
|
|
||||||
|
* **URL_OK/URL_KO**: Durante el proceso del pago, y una vez que
|
||||||
|
se muestra al cliente la pantalla con el resultado del mismo, es
|
||||||
|
posible redirigir su navegador a una URL para las transacciones
|
||||||
|
autorizadas y a otra si la transacción ha sido denegada. A éstas
|
||||||
|
se las denomina URL_OK y URL_KO, respectivamente. Se trata
|
||||||
|
de dos URLs que pueden ser proporcionadas por el comercio.
|
||||||
|
|
||||||
|
* **Porcentaje de pago**: Indicar el porcentaje de pago que se permite, si
|
||||||
|
se deja a 0.0 se entiende 100%.
|
||||||
|
|
||||||
|
Nota
|
||||||
|
~~~~
|
||||||
|
|
||||||
|
Se tiene que verificar la configuración del comercio en el
|
||||||
|
módulo de administración de Redsys, donde la opción “Parámetros en las
|
||||||
|
URLs” debe tener el valor “SI”.
|
||||||
|
|
||||||
|
En caso de que exista más de una base de datos en la instalación, cuando la
|
||||||
|
pasarela de pago envía el formulario a "/payment/redsys/return" odoo no sabe
|
||||||
|
con que base de datos procesar esta información, por lo que hay que establecer
|
||||||
|
los parametros **dbfilter** y **dbname** en el archivo de configuración.
|
||||||
|
|
||||||
|
Para mostrar simultáneamente en el comercio electrónico varios de los métodos
|
||||||
|
de pago que proporciona Redsys, como pago con tarjeta y Bizum por ejemplo,
|
||||||
|
debemos duplicar el medio de pago y escoger en el campo método de pago el que
|
||||||
|
corresponda en cada caso.
|
||||||
|
|
||||||
|
En los pagos con preautorización, el titular del TPV deberá solicitar al banco su activación.
|
||||||
|
|
||||||
|
|
||||||
|
Known issues / Roadmap
|
||||||
|
======================
|
||||||
|
|
||||||
|
De acuerdo a los requisitos de Redsys, el tamaño máximo del número de pedido
|
||||||
|
resultante (``Ds_Order``) es de 12 caracteres. Este addon trunca dicho
|
||||||
|
dato en el comienzo de la transacción, con el resultado de que, aunque Redsys
|
||||||
|
la aceptará, no se finalizará el pedido pedido en Odoo al retornar y entregará
|
||||||
|
un Error 500 a Redsys.
|
||||||
|
Para evitar esto, es recomendable seleccionar secuencias de pedido que se
|
||||||
|
ajusten a esta limitación, en particular de 10 o menos caracteres, al ser la
|
||||||
|
referencia un número extendido a partir del pedido, que incluye un guion y un
|
||||||
|
número secuencial para posibles repeticiones de pago.
|
||||||
|
|
||||||
|
Bug Tracker
|
||||||
|
===========
|
||||||
|
|
||||||
|
Bugs are tracked on `GitHub Issues <https://github.com/Criptomart/foodcoopbcn/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/Criptomart/foodcoopbcn/issues/new?body=module:%20payment_redsys_preauth%0Aversion:%2012.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
|
||||||
|
~~~~~~~
|
||||||
|
|
||||||
|
* Criptomart
|
||||||
|
|
||||||
|
Contributors
|
||||||
|
~~~~~~~~~~~~
|
||||||
|
|
||||||
|
* `Criptomart <https://www.criptomart.net>`_:
|
||||||
|
|
||||||
|
* Santi Noreña
|
||||||
|
|
||||||
|
Maintainers
|
||||||
|
~~~~~~~~~~~
|
||||||
|
|
||||||
|
This module is part of the `Criptomart/foodcoopbcn <https://github.com/Criptomart/foodcoopbcn/tree/12.0/payment_redsys_preauth>`_ project on GitHub.
|
||||||
|
|
||||||
|
You are welcome to contribute.
|
||||||
4
payment_redsys_preauth/__init__.py
Normal file
4
payment_redsys_preauth/__init__.py
Normal file
|
|
@ -0,0 +1,4 @@
|
||||||
|
# License AGPL-3 - See https://www.gnu.org/licenses/agpl-3.0.html
|
||||||
|
|
||||||
|
from . import models
|
||||||
|
from . import controllers
|
||||||
15
payment_redsys_preauth/__manifest__.py
Normal file
15
payment_redsys_preauth/__manifest__.py
Normal file
|
|
@ -0,0 +1,15 @@
|
||||||
|
# Copyright 2024 - 2025 Criptomart
|
||||||
|
{
|
||||||
|
"name": "Pasarela de pago Redsys con preautorización",
|
||||||
|
"category": "Payment Acquirer",
|
||||||
|
"summary": "Payment Acquirer: Redsys Implementation with Preauthorization",
|
||||||
|
"version": "16.0.0.0.1",
|
||||||
|
"author": "Criptomart",
|
||||||
|
"website": "https://git.criptomart.net/foodcoopbcn",
|
||||||
|
"depends": ["payment_redsys","sale_order_invoice_amount"],
|
||||||
|
"data": [
|
||||||
|
"data/payment_redsys.xml"
|
||||||
|
],
|
||||||
|
"license": "AGPL-3",
|
||||||
|
"installable": True,
|
||||||
|
}
|
||||||
2
payment_redsys_preauth/controllers/__init__.py
Normal file
2
payment_redsys_preauth/controllers/__init__.py
Normal file
|
|
@ -0,0 +1,2 @@
|
||||||
|
|
||||||
|
from . import main
|
||||||
29
payment_redsys_preauth/controllers/main.py
Normal file
29
payment_redsys_preauth/controllers/main.py
Normal file
|
|
@ -0,0 +1,29 @@
|
||||||
|
# © 2024 - 2025 criptomart.net
|
||||||
|
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||||
|
|
||||||
|
import logging
|
||||||
|
import pprint
|
||||||
|
|
||||||
|
from odoo import http
|
||||||
|
from odoo.http import request
|
||||||
|
from odoo.addons.payment_redsys.controllers.main import RedsysController
|
||||||
|
|
||||||
|
_logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class RedsysController(RedsysController):
|
||||||
|
_return_url = '/payment/redsys/return'
|
||||||
|
_cancel_url = '/payment/redsys/cancel'
|
||||||
|
_exception_url = '/payment/redsys/error'
|
||||||
|
_reject_url = '/payment/redsys/reject'
|
||||||
|
|
||||||
|
|
||||||
|
@http.route(['/payment/redsys/result/<page>'], type='http', auth='public',methods=['GET'], website=True)
|
||||||
|
def redsys_result(self, page, **post):
|
||||||
|
_logger.info('________ Redsys return sync: %s -- %s',
|
||||||
|
pprint.pformat(post), page)
|
||||||
|
# double check
|
||||||
|
if post:
|
||||||
|
request.env['payment.transaction'].sudo()._handle_notification_data('redsys', post)
|
||||||
|
return request.redirect('/payment/status')
|
||||||
26
payment_redsys_preauth/data/payment_redsys.xml
Normal file
26
payment_redsys_preauth/data/payment_redsys.xml
Normal file
|
|
@ -0,0 +1,26 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<!-- Copyright 2024-2025 Criptomart
|
||||||
|
License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl-3). -->
|
||||||
|
<odoo noupdate="1">
|
||||||
|
|
||||||
|
<record id="payment_provider_redsys_preauth" model="payment.provider">
|
||||||
|
<field name="name">Redsys Preautorización </field>
|
||||||
|
<field name="image_128" type="base64" file="payment_redsys_preauth/static/description/icon.png"/>
|
||||||
|
<field name="code">redsys</field>
|
||||||
|
<field name="company_id" ref="base.main_company"/>
|
||||||
|
<field name="redsys_merchant_name">Bussines name</field>
|
||||||
|
<field name="redsys_merchant_code">8888888</field>
|
||||||
|
<field name="redsys_merchant_description">Bussines description</field>
|
||||||
|
<field name="redsys_secret_key">xxxxxxxxxxxx -- SHA256</field>
|
||||||
|
<field name="redsys_terminal">001</field>
|
||||||
|
<field name="redsys_transaction_type">1</field>
|
||||||
|
<field name="module_id" ref="base.module_payment_redsys_preauth"/>
|
||||||
|
<field name="pre_msg"><![CDATA[<p>You will be redirected to the Redsys payment gateway after clicking on the payment button.</p>]]></field>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
<record id="payment_icon_cc_bizum" model="payment.icon">
|
||||||
|
<field name="name">Bizum</field>
|
||||||
|
<field name="image" type="base64" file="payment_redsys_preauth/static/img/bizum.png"/>
|
||||||
|
</record>
|
||||||
|
|
||||||
|
</odoo>
|
||||||
2
payment_redsys_preauth/models/__init__.py
Normal file
2
payment_redsys_preauth/models/__init__.py
Normal file
|
|
@ -0,0 +1,2 @@
|
||||||
|
from . import payment_provider
|
||||||
|
from . import payment_transaction
|
||||||
135
payment_redsys_preauth/models/payment_provider.py
Normal file
135
payment_redsys_preauth/models/payment_provider.py
Normal file
|
|
@ -0,0 +1,135 @@
|
||||||
|
# © 2024 - 2025 criptomart
|
||||||
|
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||||
|
|
||||||
|
import logging
|
||||||
|
import json
|
||||||
|
import pprint
|
||||||
|
import requests
|
||||||
|
import urllib
|
||||||
|
|
||||||
|
from odoo import models, api, exceptions, fields
|
||||||
|
from odoo.addons.payment.models.payment_provider import ValidationError
|
||||||
|
from odoo.tools.float_utils import float_compare
|
||||||
|
from odoo.tools.translate import _
|
||||||
|
import odoo.exceptions
|
||||||
|
|
||||||
|
_logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
class PaymentProvider(models.Model):
|
||||||
|
_inherit = 'payment.provider'
|
||||||
|
|
||||||
|
@api.depends('code')
|
||||||
|
def _compute_feature_support_fields(self):
|
||||||
|
super()._compute_feature_support_fields()
|
||||||
|
self.update({
|
||||||
|
'support_manual_capture': 'partial',
|
||||||
|
})
|
||||||
|
|
||||||
|
def get_redsys_rest_urls(self, environment):
|
||||||
|
""" Redsys Rest URLs
|
||||||
|
"""
|
||||||
|
if environment == 'prod':
|
||||||
|
return {
|
||||||
|
'redsys_rest_url':
|
||||||
|
'https://sis.redsys.es/sis/rest/trataPeticionREST',
|
||||||
|
}
|
||||||
|
else:
|
||||||
|
# redsys no acepta preautorizaciones en test, pero puede que cambie...
|
||||||
|
return {
|
||||||
|
'redsys_rest_url':
|
||||||
|
'https://sis-t.redsys.es:25443/sis/rest/trataPeticionREST',
|
||||||
|
}
|
||||||
|
|
||||||
|
def _prepare_merchant_parameters(self, tx_values):
|
||||||
|
base_url = self._get_website_url()
|
||||||
|
callback_url = "http://botiga.foodcoopbcn.cat"
|
||||||
|
values = {
|
||||||
|
"Ds_Sermepa_Url": self._redsys_get_api_url(),
|
||||||
|
"Ds_Merchant_Amount": str(int(round(tx_values["amount"] * 100))),
|
||||||
|
"Ds_Merchant_Currency": self.redsys_currency or "978",
|
||||||
|
"Ds_Merchant_Order": (
|
||||||
|
tx_values["reference"] and tx_values["reference"][-12:] or False
|
||||||
|
),
|
||||||
|
"Ds_Merchant_MerchantCode": (
|
||||||
|
self.redsys_merchant_code and self.redsys_merchant_code[:9]
|
||||||
|
),
|
||||||
|
"Ds_Merchant_Terminal": self.redsys_terminal or "1",
|
||||||
|
"Ds_Merchant_TransactionType": (self.redsys_transaction_type or "1"),
|
||||||
|
"Ds_Merchant_Titular": tx_values.get(
|
||||||
|
"billing_partner", self.env.user.partner_id
|
||||||
|
).display_name[:60],
|
||||||
|
"Ds_Merchant_MerchantName": (
|
||||||
|
self.redsys_merchant_name and self.redsys_merchant_name[:25]
|
||||||
|
),
|
||||||
|
"Ds_Merchant_MerchantUrl": (
|
||||||
|
"%s/payment/redsys/return" % (callback_url or base_url)
|
||||||
|
)[:250],
|
||||||
|
"Ds_Merchant_MerchantData": self.redsys_merchant_data or "",
|
||||||
|
"Ds_Merchant_ProductDescription": (
|
||||||
|
self.redsys_merchant_description
|
||||||
|
and self.redsys_merchant_description[:125]
|
||||||
|
),
|
||||||
|
"Ds_Merchant_ConsumerLanguage": (self.redsys_merchant_lang or "001"),
|
||||||
|
"Ds_Merchant_UrlOk": "%s/payment/redsys/result/redsys_result_ok" % base_url,
|
||||||
|
"Ds_Merchant_UrlKo": "%s/payment/redsys/result/redsys_result_ko" % base_url,
|
||||||
|
"Ds_Merchant_Paymethods": self.redsys_pay_method or "T",
|
||||||
|
}
|
||||||
|
return self._url_encode64(json.dumps(values)).decode("utf-8")
|
||||||
|
|
||||||
|
def _prepare_s2s_merchant_parameters(self, tx_values):
|
||||||
|
values = {
|
||||||
|
'Ds_Merchant_Amount': str(int(round(tx_values['amount'] * 100))),
|
||||||
|
'Ds_Merchant_Currency': self.redsys_currency or '978',
|
||||||
|
'Ds_Merchant_Order': (
|
||||||
|
tx_values['reference'] and tx_values['reference'][-12:] or
|
||||||
|
False),
|
||||||
|
'Ds_Merchant_MerchantCode': (
|
||||||
|
self.redsys_merchant_code and
|
||||||
|
self.redsys_merchant_code[:9]),
|
||||||
|
'Ds_Merchant_Terminal': self.redsys_terminal or '1',
|
||||||
|
}
|
||||||
|
if 'transaction_type' in tx_values:
|
||||||
|
values.update({'Ds_Merchant_TransactionType': tx_values['transaction_type']})
|
||||||
|
else:
|
||||||
|
values.update({'Ds_Merchant_TransactionType':
|
||||||
|
(self.redsys_transaction_type or '2')}),
|
||||||
|
return self._url_encode64(json.dumps(values))
|
||||||
|
|
||||||
|
def redsys_s2s_create_transaction(self, values):
|
||||||
|
self.ensure_one()
|
||||||
|
redsys_values = dict()
|
||||||
|
merchant_parameters = self._prepare_s2s_merchant_parameters(values)
|
||||||
|
redsys_values.update({
|
||||||
|
'Ds_SignatureVersion': str(self.redsys_signature_version),
|
||||||
|
'Ds_MerchantParameters': merchant_parameters,
|
||||||
|
'Ds_Signature': self.sign_parameters(
|
||||||
|
self.redsys_secret_key, merchant_parameters),
|
||||||
|
})
|
||||||
|
return redsys_values
|
||||||
|
|
||||||
|
def redsys_send_s2s_msg(self, values):
|
||||||
|
toSend = self.redsys_s2s_create_transaction(values)
|
||||||
|
url = self.get_redsys_rest_urls('prod')['redsys_rest_url']
|
||||||
|
_logger.info('Redsys: sending rest values:\n%s', pprint.pformat(toSend))
|
||||||
|
try:
|
||||||
|
if toSend and url:
|
||||||
|
response = requests.post(url, data=toSend)
|
||||||
|
else:
|
||||||
|
raise exceptions.ValidationError('Error en los parámetros de la petición rest')
|
||||||
|
except requests.exceptions.RequestException as e:
|
||||||
|
_logger.error('Redsys: Error sending rest transaction %s:\n%s', values['reference'], str(e))
|
||||||
|
return False
|
||||||
|
if response and response.status_code != 200:
|
||||||
|
_logger.error('Redsys: Error sending rest transaction %s: %s', values['reference'], response.status_code)
|
||||||
|
return False
|
||||||
|
_logger.info('Redsys: rest response:\n%s', pprint.pformat(response.text))
|
||||||
|
try:
|
||||||
|
errorCheck = response.json()
|
||||||
|
if errorCheck.get('errorCode', ''):
|
||||||
|
_logger.error('Redsys: Error recibido tx %s: %s', values['reference'], errorCheck.get('errorCode'))
|
||||||
|
except json.JSONDecodeError:
|
||||||
|
_logger.error('Error al decodificar la respuesta JSON para la transacción %s', values['reference'])
|
||||||
|
return False
|
||||||
|
return errorCheck
|
||||||
|
|
||||||
150
payment_redsys_preauth/models/payment_transaction.py
Normal file
150
payment_redsys_preauth/models/payment_transaction.py
Normal file
|
|
@ -0,0 +1,150 @@
|
||||||
|
# © 2024 - 2025 criptomart
|
||||||
|
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
|
||||||
|
|
||||||
|
import logging
|
||||||
|
import json
|
||||||
|
import pprint
|
||||||
|
import requests
|
||||||
|
|
||||||
|
from odoo import models, api, exceptions, fields
|
||||||
|
from odoo.addons.payment.models.payment_provider import ValidationError
|
||||||
|
from odoo.tools.float_utils import float_compare
|
||||||
|
from odoo.tools.translate import _
|
||||||
|
|
||||||
|
|
||||||
|
_logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
class TxRedsysPreAuth(models.Model):
|
||||||
|
_inherit = 'payment.transaction'
|
||||||
|
|
||||||
|
def _get_specific_rendering_values(self, processing_values):
|
||||||
|
if self.provider_code != "redsys":
|
||||||
|
return super()._get_specific_rendering_values(processing_values)
|
||||||
|
redsys_values = dict(processing_values)
|
||||||
|
merchant_parameters = self.provider_id._prepare_merchant_parameters(
|
||||||
|
processing_values
|
||||||
|
)
|
||||||
|
redsys_values.update(
|
||||||
|
{
|
||||||
|
"api_url": self.provider_id._redsys_get_api_url(),
|
||||||
|
"Ds_SignatureVersion": str(self.provider_id.redsys_signature_version),
|
||||||
|
"Ds_MerchantParameters": merchant_parameters,
|
||||||
|
"Ds_Signature": self.provider_id.sign_parameters(
|
||||||
|
self.provider_id.redsys_secret_key, merchant_parameters
|
||||||
|
),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
return redsys_values
|
||||||
|
|
||||||
|
# chequea que el usuario cancele el pago 9915. cambia el stado de done a authorized
|
||||||
|
@api.model
|
||||||
|
def _get_redsys_state(self, status_code):
|
||||||
|
if 0 <= status_code <= 100:
|
||||||
|
return "authorized"
|
||||||
|
elif status_code <= 203:
|
||||||
|
return "pending"
|
||||||
|
elif status_code == 400:
|
||||||
|
return "cancel"
|
||||||
|
elif status_code == 900:
|
||||||
|
return "done"
|
||||||
|
elif 912 <= status_code <= 9915:
|
||||||
|
return "cancel"
|
||||||
|
else:
|
||||||
|
return "error"
|
||||||
|
|
||||||
|
def _process_notification_data(self, data):
|
||||||
|
if self.provider_code != "redsys":
|
||||||
|
return super()._process_notification_data(data)
|
||||||
|
params = self.merchant_params_json2dict(data)
|
||||||
|
status_code = int(params.get('Ds_Response', '29999'))
|
||||||
|
state = self._get_redsys_state(status_code)
|
||||||
|
vals = {
|
||||||
|
'state': state,
|
||||||
|
'redsys_txnid': params.get('Ds_AuthorisationCode'),
|
||||||
|
}
|
||||||
|
state_message = ""
|
||||||
|
feedback_error = False
|
||||||
|
if state == 'done':
|
||||||
|
vals['state_message'] = _('Ok: %s') % params.get('Ds_Response')
|
||||||
|
self._set_done()
|
||||||
|
self._finalize_post_processing()
|
||||||
|
if state == 'authorized':
|
||||||
|
vals['state_message'] = _('Auth Ok: %s') % params.get('Ds_Response')
|
||||||
|
self._set_authorized()
|
||||||
|
self._finalize_post_processing()
|
||||||
|
elif state == 'pending': # 'Payment error: code: %s.'
|
||||||
|
state_message = _("Redsys: feedback error: %s" %(status_code))
|
||||||
|
self._set_pending()
|
||||||
|
elif state == 'cancel': # 'Payment error: bank unavailable.'
|
||||||
|
state_message = _("Redsys: feedback error: %s" %(status_code))
|
||||||
|
self._set_canceled()
|
||||||
|
else:
|
||||||
|
state_message = _("Redsys: feedback error: %s" %(status_code))
|
||||||
|
self._set_error(state_message)
|
||||||
|
feedback_error = True
|
||||||
|
if state_message:
|
||||||
|
vals['state_message'] = state_message % {
|
||||||
|
"status_code": params.get("Ds_Response"),
|
||||||
|
"error_code": params.get("Ds_ErrorCode"),
|
||||||
|
}
|
||||||
|
if state == 'error':
|
||||||
|
_logger.warning(vals['state_message'])
|
||||||
|
self.write(vals)
|
||||||
|
|
||||||
|
def _send_capture_request(self, amount_to_capture=None):
|
||||||
|
self.ensure_one()
|
||||||
|
self._ensure_provider_is_not_disabled()
|
||||||
|
_logger.info('Redsys: Capturing transaction %s -- %s', self.reference, amount_to_capture)
|
||||||
|
try:
|
||||||
|
if amount_to_capture:
|
||||||
|
values = {'amount': amount_to_capture}
|
||||||
|
else:
|
||||||
|
values = {'amount': sum(order.invoiced_amount for order in self.sale_order_ids)}
|
||||||
|
values.update({'reference': self.reference})
|
||||||
|
values.update({'transaction_type': '2'})
|
||||||
|
response = self.provider_id.redsys_send_s2s_msg(values)
|
||||||
|
if not response:
|
||||||
|
raise exceptions.ValidationError('Error mandando mensaje rest');
|
||||||
|
if response.get('errorCode', ''):
|
||||||
|
raise exceptions.ValidationError('Ref %s: Error Code %s' %(self.reference, response.get('errorCode')))
|
||||||
|
params = self.merchant_params_json2dict(response)
|
||||||
|
_logger.info('Redsys: parameters received:\n%s', pprint.pformat(params))
|
||||||
|
if params['Ds_Response'] == '0900' and params['Ds_Order'] == self.reference:
|
||||||
|
self.provider_reference = params['Ds_AuthorisationCode']
|
||||||
|
self._set_done()
|
||||||
|
_logger.info('Confirmacion de preautorizacion realizada con exito para la transaccion %s', self.reference)
|
||||||
|
message = ('Preautorizacion confirmada')
|
||||||
|
self.sale_order_ids.message_post(body=message)
|
||||||
|
else:
|
||||||
|
raise exceptions.ValidationError('Error en confirmacion de preautorizacion tx: %s - %s', self.reference, params['Ds_Response'])
|
||||||
|
except Exception as e:
|
||||||
|
_logger.exception('Redsys: Error capturando preautorización transacción %s:\n%s', self.reference, str(e))
|
||||||
|
raise exceptions.UserError(_('Error capturing preauthorization for transaction %s:\n%s') % (self.reference, str(e)))
|
||||||
|
|
||||||
|
def _send_void_request(self, amount_to_void=None):
|
||||||
|
self.ensure_one()
|
||||||
|
self._ensure_provider_is_not_disabled()
|
||||||
|
_logger.info('Redsys: Preauthorization cancel for transaction %s', self.reference)
|
||||||
|
try:
|
||||||
|
if amount_to_void:
|
||||||
|
values = {'amount': amount_to_void}
|
||||||
|
else:
|
||||||
|
values = {'amount': self.amount}
|
||||||
|
values.update({'reference': self.reference})
|
||||||
|
values.update({'transaction_type': '9'})
|
||||||
|
response = self.provider_id.redsys_send_s2s_msg(values)
|
||||||
|
if not response:
|
||||||
|
raise exceptions.ValidationError(_('error redsys_s2s_msg'))
|
||||||
|
if response.get('errorCode', ''):
|
||||||
|
raise exceptions.ValidationError('Ref %s: Error Code %s' % (self.reference, response.get('errorCode')))
|
||||||
|
params = self.merchant_params_json2dict(response)
|
||||||
|
_logger.info('Redsys: parameters received):\n%s', pprint.pformat(params))
|
||||||
|
if params['Ds_Response'] == '0400' and params['Ds_Order'] == self.reference:
|
||||||
|
self._set_canceled()
|
||||||
|
_logger.info('Preautorización cancelada con éxito para la transacción %s', self.reference)
|
||||||
|
else:
|
||||||
|
raise exceptions.ValidationError('No se pudo cancelar la preautorización para la transacción %s - %s', self.reference, params['Ds_Response'])
|
||||||
|
except Exception as e:
|
||||||
|
_logger.exception('Redsys Error cancelando preautorización tx %s:\n%s', self.reference, str(e))
|
||||||
|
raise exceptions.UserError(_('Error cancelling preauthorization for transaction %s:\n%s') % (self.reference, str(e)))
|
||||||
54
payment_redsys_preauth/readme/CONFIGURE.rst
Normal file
54
payment_redsys_preauth/readme/CONFIGURE.rst
Normal file
|
|
@ -0,0 +1,54 @@
|
||||||
|
Parámetros
|
||||||
|
~~~~~~~~~~
|
||||||
|
|
||||||
|
* **Nombre del comercio**: Indicaremos el nombre del comercio.
|
||||||
|
|
||||||
|
* **Número de comercio (FUC)**: Indicaremos el número de comercio que
|
||||||
|
nuestra entidad nos ha comunicado.
|
||||||
|
|
||||||
|
* **Clave secreta de encriptación**: Indicaremos la clave de encriptación
|
||||||
|
que tiene el comercio.
|
||||||
|
|
||||||
|
* **Número de terminal**: Indicaremos el terminal del TPV.
|
||||||
|
|
||||||
|
* **Tipo de firma**: Seleccionaremos el tipo de firma del comercio.
|
||||||
|
|
||||||
|
* **Tipo de moneda**: Seleccionaremos la moneda de nuestro terminal TPV
|
||||||
|
(Normalmente EUR - Euros).
|
||||||
|
|
||||||
|
* **Tipo de transacción**: Indicaremos el tipo de transacción, 1.
|
||||||
|
|
||||||
|
* **Idioma TPV**: Indicaremos el idioma en el TPV.
|
||||||
|
|
||||||
|
* **Método de pago**: Indicaremos que tipo de pago se debe aceptar, pago con
|
||||||
|
tarjeta, Bizum u otro de los disponibles.
|
||||||
|
|
||||||
|
* **URL_OK/URL_KO**: Durante el proceso del pago, y una vez que
|
||||||
|
se muestra al cliente la pantalla con el resultado del mismo, es
|
||||||
|
posible redirigir su navegador a una URL para las transacciones
|
||||||
|
autorizadas y a otra si la transacción ha sido denegada. A éstas
|
||||||
|
se las denomina URL_OK y URL_KO, respectivamente. Se trata
|
||||||
|
de dos URLs que pueden ser proporcionadas por el comercio.
|
||||||
|
|
||||||
|
* **Porcentaje de pago**: Indicar el porcentaje de pago que se permite, si
|
||||||
|
se deja a 0.0 se entiende 100%.
|
||||||
|
|
||||||
|
Nota
|
||||||
|
~~~~
|
||||||
|
|
||||||
|
Se tiene que verificar la configuración del comercio en el
|
||||||
|
módulo de administración de Redsys, donde la opción “Parámetros en las
|
||||||
|
URLs” debe tener el valor “SI”.
|
||||||
|
|
||||||
|
En caso de que exista más de una base de datos en la instalación, cuando la
|
||||||
|
pasarela de pago envía el formulario a "/payment/redsys/return" odoo no sabe
|
||||||
|
con que base de datos procesar esta información, por lo que hay que establecer
|
||||||
|
los parametros **dbfilter** y **dbname** en el archivo de configuración.
|
||||||
|
|
||||||
|
Para mostrar simultáneamente en el comercio electrónico varios de los métodos
|
||||||
|
de pago que proporciona Redsys, como pago con tarjeta y Bizum por ejemplo,
|
||||||
|
debemos duplicar el medio de pago y escoger en el campo método de pago el que
|
||||||
|
corresponda en cada caso.
|
||||||
|
|
||||||
|
En los pagos con preautorización, el titular del TPV deberá solicitar al banco su activación.
|
||||||
|
|
||||||
3
payment_redsys_preauth/readme/CONTRIBUTORS.rst
Normal file
3
payment_redsys_preauth/readme/CONTRIBUTORS.rst
Normal file
|
|
@ -0,0 +1,3 @@
|
||||||
|
* `Criptomart <https://www.criptomart.net>`_:
|
||||||
|
|
||||||
|
* Santi Noreña
|
||||||
1
payment_redsys_preauth/readme/DESCRIPTION.rst
Normal file
1
payment_redsys_preauth/readme/DESCRIPTION.rst
Normal file
|
|
@ -0,0 +1 @@
|
||||||
|
Este módulo añade la opción de pago a través de la pasarela de Redsys con preautorización con tarjeta bancaria.
|
||||||
0
payment_redsys_preauth/readme/INSTALL.rst
Normal file
0
payment_redsys_preauth/readme/INSTALL.rst
Normal file
9
payment_redsys_preauth/readme/ROADMAP.rst
Normal file
9
payment_redsys_preauth/readme/ROADMAP.rst
Normal file
|
|
@ -0,0 +1,9 @@
|
||||||
|
De acuerdo a los requisitos de Redsys, el tamaño máximo del número de pedido
|
||||||
|
resultante (``Ds_Order``) es de 12 caracteres. Este addon trunca dicho
|
||||||
|
dato en el comienzo de la transacción, con el resultado de que, aunque Redsys
|
||||||
|
la aceptará, no se finalizará el pedido pedido en Odoo al retornar y entregará
|
||||||
|
un Error 500 a Redsys.
|
||||||
|
Para evitar esto, es recomendable seleccionar secuencias de pedido que se
|
||||||
|
ajusten a esta limitación, en particular de 10 o menos caracteres, al ser la
|
||||||
|
referencia un número extendido a partir del pedido, que incluye un guion y un
|
||||||
|
número secuencial para posibles repeticiones de pago.
|
||||||
BIN
payment_redsys_preauth/static/description/icon.png
Normal file
BIN
payment_redsys_preauth/static/description/icon.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 27 KiB |
480
payment_redsys_preauth/static/description/index.html
Normal file
480
payment_redsys_preauth/static/description/index.html
Normal file
|
|
@ -0,0 +1,480 @@
|
||||||
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||||
|
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||||
|
<meta name="generator" content="Docutils: http://docutils.sourceforge.net/" />
|
||||||
|
<title>Pasarela de pago Redsys con preautorización</title>
|
||||||
|
<style type="text/css">
|
||||||
|
|
||||||
|
/*
|
||||||
|
:Author: David Goodger (goodger@python.org)
|
||||||
|
:Id: $Id: html4css1.css 7952 2016-07-26 18:15:59Z milde $
|
||||||
|
:Copyright: This stylesheet has been placed in the public domain.
|
||||||
|
|
||||||
|
Default cascading style sheet for the HTML output of Docutils.
|
||||||
|
|
||||||
|
See http://docutils.sf.net/docs/howto/html-stylesheets.html for how to
|
||||||
|
customize this style sheet.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* used to remove borders from tables and images */
|
||||||
|
.borderless, table.borderless td, table.borderless th {
|
||||||
|
border: 0 }
|
||||||
|
|
||||||
|
table.borderless td, table.borderless th {
|
||||||
|
/* Override padding for "table.docutils td" with "! important".
|
||||||
|
The right padding separates the table cells. */
|
||||||
|
padding: 0 0.5em 0 0 ! important }
|
||||||
|
|
||||||
|
.first {
|
||||||
|
/* Override more specific margin styles with "! important". */
|
||||||
|
margin-top: 0 ! important }
|
||||||
|
|
||||||
|
.last, .with-subtitle {
|
||||||
|
margin-bottom: 0 ! important }
|
||||||
|
|
||||||
|
.hidden {
|
||||||
|
display: none }
|
||||||
|
|
||||||
|
.subscript {
|
||||||
|
vertical-align: sub;
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
.superscript {
|
||||||
|
vertical-align: super;
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
a.toc-backref {
|
||||||
|
text-decoration: none ;
|
||||||
|
color: black }
|
||||||
|
|
||||||
|
blockquote.epigraph {
|
||||||
|
margin: 2em 5em ; }
|
||||||
|
|
||||||
|
dl.docutils dd {
|
||||||
|
margin-bottom: 0.5em }
|
||||||
|
|
||||||
|
object[type="image/svg+xml"], object[type="application/x-shockwave-flash"] {
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Uncomment (and remove this text!) to get bold-faced definition list terms
|
||||||
|
dl.docutils dt {
|
||||||
|
font-weight: bold }
|
||||||
|
*/
|
||||||
|
|
||||||
|
div.abstract {
|
||||||
|
margin: 2em 5em }
|
||||||
|
|
||||||
|
div.abstract p.topic-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
div.admonition, div.attention, div.caution, div.danger, div.error,
|
||||||
|
div.hint, div.important, div.note, div.tip, div.warning {
|
||||||
|
margin: 2em ;
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 1em }
|
||||||
|
|
||||||
|
div.admonition p.admonition-title, div.hint p.admonition-title,
|
||||||
|
div.important p.admonition-title, div.note p.admonition-title,
|
||||||
|
div.tip p.admonition-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
div.attention p.admonition-title, div.caution p.admonition-title,
|
||||||
|
div.danger p.admonition-title, div.error p.admonition-title,
|
||||||
|
div.warning p.admonition-title, .code .error {
|
||||||
|
color: red ;
|
||||||
|
font-weight: bold ;
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
/* Uncomment (and remove this text!) to get reduced vertical space in
|
||||||
|
compound paragraphs.
|
||||||
|
div.compound .compound-first, div.compound .compound-middle {
|
||||||
|
margin-bottom: 0.5em }
|
||||||
|
|
||||||
|
div.compound .compound-last, div.compound .compound-middle {
|
||||||
|
margin-top: 0.5em }
|
||||||
|
*/
|
||||||
|
|
||||||
|
div.dedication {
|
||||||
|
margin: 2em 5em ;
|
||||||
|
text-align: center ;
|
||||||
|
font-style: italic }
|
||||||
|
|
||||||
|
div.dedication p.topic-title {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-style: normal }
|
||||||
|
|
||||||
|
div.figure {
|
||||||
|
margin-left: 2em ;
|
||||||
|
margin-right: 2em }
|
||||||
|
|
||||||
|
div.footer, div.header {
|
||||||
|
clear: both;
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
div.line-block {
|
||||||
|
display: block ;
|
||||||
|
margin-top: 1em ;
|
||||||
|
margin-bottom: 1em }
|
||||||
|
|
||||||
|
div.line-block div.line-block {
|
||||||
|
margin-top: 0 ;
|
||||||
|
margin-bottom: 0 ;
|
||||||
|
margin-left: 1.5em }
|
||||||
|
|
||||||
|
div.sidebar {
|
||||||
|
margin: 0 0 0.5em 1em ;
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 1em ;
|
||||||
|
background-color: #ffffee ;
|
||||||
|
width: 40% ;
|
||||||
|
float: right ;
|
||||||
|
clear: right }
|
||||||
|
|
||||||
|
div.sidebar p.rubric {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-size: medium }
|
||||||
|
|
||||||
|
div.system-messages {
|
||||||
|
margin: 5em }
|
||||||
|
|
||||||
|
div.system-messages h1 {
|
||||||
|
color: red }
|
||||||
|
|
||||||
|
div.system-message {
|
||||||
|
border: medium outset ;
|
||||||
|
padding: 1em }
|
||||||
|
|
||||||
|
div.system-message p.system-message-title {
|
||||||
|
color: red ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
div.topic {
|
||||||
|
margin: 2em }
|
||||||
|
|
||||||
|
h1.section-subtitle, h2.section-subtitle, h3.section-subtitle,
|
||||||
|
h4.section-subtitle, h5.section-subtitle, h6.section-subtitle {
|
||||||
|
margin-top: 0.4em }
|
||||||
|
|
||||||
|
h1.title {
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
h2.subtitle {
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
hr.docutils {
|
||||||
|
width: 75% }
|
||||||
|
|
||||||
|
img.align-left, .figure.align-left, object.align-left, table.align-left {
|
||||||
|
clear: left ;
|
||||||
|
float: left ;
|
||||||
|
margin-right: 1em }
|
||||||
|
|
||||||
|
img.align-right, .figure.align-right, object.align-right, table.align-right {
|
||||||
|
clear: right ;
|
||||||
|
float: right ;
|
||||||
|
margin-left: 1em }
|
||||||
|
|
||||||
|
img.align-center, .figure.align-center, object.align-center {
|
||||||
|
display: block;
|
||||||
|
margin-left: auto;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
table.align-center {
|
||||||
|
margin-left: auto;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.align-left {
|
||||||
|
text-align: left }
|
||||||
|
|
||||||
|
.align-center {
|
||||||
|
clear: both ;
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
.align-right {
|
||||||
|
text-align: right }
|
||||||
|
|
||||||
|
/* reset inner alignment in figures */
|
||||||
|
div.align-right {
|
||||||
|
text-align: inherit }
|
||||||
|
|
||||||
|
/* div.align-center * { */
|
||||||
|
/* text-align: left } */
|
||||||
|
|
||||||
|
.align-top {
|
||||||
|
vertical-align: top }
|
||||||
|
|
||||||
|
.align-middle {
|
||||||
|
vertical-align: middle }
|
||||||
|
|
||||||
|
.align-bottom {
|
||||||
|
vertical-align: bottom }
|
||||||
|
|
||||||
|
ol.simple, ul.simple {
|
||||||
|
margin-bottom: 1em }
|
||||||
|
|
||||||
|
ol.arabic {
|
||||||
|
list-style: decimal }
|
||||||
|
|
||||||
|
ol.loweralpha {
|
||||||
|
list-style: lower-alpha }
|
||||||
|
|
||||||
|
ol.upperalpha {
|
||||||
|
list-style: upper-alpha }
|
||||||
|
|
||||||
|
ol.lowerroman {
|
||||||
|
list-style: lower-roman }
|
||||||
|
|
||||||
|
ol.upperroman {
|
||||||
|
list-style: upper-roman }
|
||||||
|
|
||||||
|
p.attribution {
|
||||||
|
text-align: right ;
|
||||||
|
margin-left: 50% }
|
||||||
|
|
||||||
|
p.caption {
|
||||||
|
font-style: italic }
|
||||||
|
|
||||||
|
p.credits {
|
||||||
|
font-style: italic ;
|
||||||
|
font-size: smaller }
|
||||||
|
|
||||||
|
p.label {
|
||||||
|
white-space: nowrap }
|
||||||
|
|
||||||
|
p.rubric {
|
||||||
|
font-weight: bold ;
|
||||||
|
font-size: larger ;
|
||||||
|
color: maroon ;
|
||||||
|
text-align: center }
|
||||||
|
|
||||||
|
p.sidebar-title {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold ;
|
||||||
|
font-size: larger }
|
||||||
|
|
||||||
|
p.sidebar-subtitle {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
p.topic-title {
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
pre.address {
|
||||||
|
margin-bottom: 0 ;
|
||||||
|
margin-top: 0 ;
|
||||||
|
font: inherit }
|
||||||
|
|
||||||
|
pre.literal-block, pre.doctest-block, pre.math, pre.code {
|
||||||
|
margin-left: 2em ;
|
||||||
|
margin-right: 2em }
|
||||||
|
|
||||||
|
pre.code .ln { color: grey; } /* line numbers */
|
||||||
|
pre.code, code { background-color: #eeeeee }
|
||||||
|
pre.code .comment, code .comment { color: #5C6576 }
|
||||||
|
pre.code .keyword, code .keyword { color: #3B0D06; font-weight: bold }
|
||||||
|
pre.code .literal.string, code .literal.string { color: #0C5404 }
|
||||||
|
pre.code .name.builtin, code .name.builtin { color: #352B84 }
|
||||||
|
pre.code .deleted, code .deleted { background-color: #DEB0A1}
|
||||||
|
pre.code .inserted, code .inserted { background-color: #A3D289}
|
||||||
|
|
||||||
|
span.classifier {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-style: oblique }
|
||||||
|
|
||||||
|
span.classifier-delimiter {
|
||||||
|
font-family: sans-serif ;
|
||||||
|
font-weight: bold }
|
||||||
|
|
||||||
|
span.interpreted {
|
||||||
|
font-family: sans-serif }
|
||||||
|
|
||||||
|
span.option {
|
||||||
|
white-space: nowrap }
|
||||||
|
|
||||||
|
span.pre {
|
||||||
|
white-space: pre }
|
||||||
|
|
||||||
|
span.problematic {
|
||||||
|
color: red }
|
||||||
|
|
||||||
|
span.section-subtitle {
|
||||||
|
/* font-size relative to parent (h1..h6 element) */
|
||||||
|
font-size: 80% }
|
||||||
|
|
||||||
|
table.citation {
|
||||||
|
border-left: solid 1px gray;
|
||||||
|
margin-left: 1px }
|
||||||
|
|
||||||
|
table.docinfo {
|
||||||
|
margin: 2em 4em }
|
||||||
|
|
||||||
|
table.docutils {
|
||||||
|
margin-top: 0.5em ;
|
||||||
|
margin-bottom: 0.5em }
|
||||||
|
|
||||||
|
table.footnote {
|
||||||
|
border-left: solid 1px black;
|
||||||
|
margin-left: 1px }
|
||||||
|
|
||||||
|
table.docutils td, table.docutils th,
|
||||||
|
table.docinfo td, table.docinfo th {
|
||||||
|
padding-left: 0.5em ;
|
||||||
|
padding-right: 0.5em ;
|
||||||
|
vertical-align: top }
|
||||||
|
|
||||||
|
table.docutils th.field-name, table.docinfo th.docinfo-name {
|
||||||
|
font-weight: bold ;
|
||||||
|
text-align: left ;
|
||||||
|
white-space: nowrap ;
|
||||||
|
padding-left: 0 }
|
||||||
|
|
||||||
|
/* "booktabs" style (no vertical lines) */
|
||||||
|
table.docutils.booktabs {
|
||||||
|
border: 0px;
|
||||||
|
border-top: 2px solid;
|
||||||
|
border-bottom: 2px solid;
|
||||||
|
border-collapse: collapse;
|
||||||
|
}
|
||||||
|
table.docutils.booktabs * {
|
||||||
|
border: 0px;
|
||||||
|
}
|
||||||
|
table.docutils.booktabs th {
|
||||||
|
border-bottom: thin solid;
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
h1 tt.docutils, h2 tt.docutils, h3 tt.docutils,
|
||||||
|
h4 tt.docutils, h5 tt.docutils, h6 tt.docutils {
|
||||||
|
font-size: 100% }
|
||||||
|
|
||||||
|
ul.auto-toc {
|
||||||
|
list-style-type: none }
|
||||||
|
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="document" id="pasarela-de-pago-redsys-con-preautorizacion">
|
||||||
|
<h1 class="title">Pasarela de pago Redsys con preautorización</h1>
|
||||||
|
|
||||||
|
<!-- !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
|
!! This file is generated by oca-gen-addon-readme !!
|
||||||
|
!! changes will be overwritten. !!
|
||||||
|
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
||||||
|
!! source digest: sha256:1eb9535d052a619aa545a383869076ca1dc1fade22746cb3fe13afa726c3e3a3
|
||||||
|
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! -->
|
||||||
|
<p><a class="reference external" href="https://odoo-community.org/page/development-status"><img alt="Beta" src="https://img.shields.io/badge/maturity-Beta-yellow.png" /></a> <a class="reference external" href="http://www.gnu.org/licenses/agpl-3.0-standalone.html"><img alt="License: AGPL-3" src="https://img.shields.io/badge/licence-AGPL--3-blue.png" /></a> <a class="reference external" href="https://github.com/Criptomart/foodcoopbcn/tree/12.0/payment_redsys_preauth"><img alt="Criptomart/foodcoopbcn" src="https://img.shields.io/badge/github-Criptomart%2Ffoodcoopbcn-lightgray.png?logo=github" /></a></p>
|
||||||
|
<p>Este módulo añade la opción de pago a través de la pasarela de Redsys con preautorización con tarjeta bancaria.</p>
|
||||||
|
<p><strong>Table of contents</strong></p>
|
||||||
|
<div class="contents local topic" id="contents">
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference internal" href="#configuration" id="id1">Configuration</a><ul>
|
||||||
|
<li><a class="reference internal" href="#parametros" id="id2">Parámetros</a></li>
|
||||||
|
<li><a class="reference internal" href="#nota" id="id3">Nota</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#known-issues-roadmap" id="id4">Known issues / Roadmap</a></li>
|
||||||
|
<li><a class="reference internal" href="#bug-tracker" id="id5">Bug Tracker</a></li>
|
||||||
|
<li><a class="reference internal" href="#credits" id="id6">Credits</a><ul>
|
||||||
|
<li><a class="reference internal" href="#authors" id="id7">Authors</a></li>
|
||||||
|
<li><a class="reference internal" href="#contributors" id="id8">Contributors</a></li>
|
||||||
|
<li><a class="reference internal" href="#maintainers" id="id9">Maintainers</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="configuration">
|
||||||
|
<h1><a class="toc-backref" href="#id1">Configuration</a></h1>
|
||||||
|
<div class="section" id="parametros">
|
||||||
|
<h2><a class="toc-backref" href="#id2">Parámetros</a></h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><strong>Nombre del comercio</strong>: Indicaremos el nombre del comercio.</li>
|
||||||
|
<li><strong>Número de comercio (FUC)</strong>: Indicaremos el número de comercio que
|
||||||
|
nuestra entidad nos ha comunicado.</li>
|
||||||
|
<li><strong>Clave secreta de encriptación</strong>: Indicaremos la clave de encriptación
|
||||||
|
que tiene el comercio.</li>
|
||||||
|
<li><strong>Número de terminal</strong>: Indicaremos el terminal del TPV.</li>
|
||||||
|
<li><strong>Tipo de firma</strong>: Seleccionaremos el tipo de firma del comercio.</li>
|
||||||
|
<li><strong>Tipo de moneda</strong>: Seleccionaremos la moneda de nuestro terminal TPV
|
||||||
|
(Normalmente EUR - Euros).</li>
|
||||||
|
<li><strong>Tipo de transacción</strong>: Indicaremos el tipo de transacción, 1.</li>
|
||||||
|
<li><strong>Idioma TPV</strong>: Indicaremos el idioma en el TPV.</li>
|
||||||
|
<li><strong>Método de pago</strong>: Indicaremos que tipo de pago se debe aceptar, pago con
|
||||||
|
tarjeta, Bizum u otro de los disponibles.</li>
|
||||||
|
<li><strong>URL_OK/URL_KO</strong>: Durante el proceso del pago, y una vez que
|
||||||
|
se muestra al cliente la pantalla con el resultado del mismo, es
|
||||||
|
posible redirigir su navegador a una URL para las transacciones
|
||||||
|
autorizadas y a otra si la transacción ha sido denegada. A éstas
|
||||||
|
se las denomina URL_OK y URL_KO, respectivamente. Se trata
|
||||||
|
de dos URLs que pueden ser proporcionadas por el comercio.</li>
|
||||||
|
<li><strong>Porcentaje de pago</strong>: Indicar el porcentaje de pago que se permite, si
|
||||||
|
se deja a 0.0 se entiende 100%.</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="nota">
|
||||||
|
<h2><a class="toc-backref" href="#id3">Nota</a></h2>
|
||||||
|
<p>Se tiene que verificar la configuración del comercio en el
|
||||||
|
módulo de administración de Redsys, donde la opción “Parámetros en las
|
||||||
|
URLs” debe tener el valor “SI”.</p>
|
||||||
|
<p>En caso de que exista más de una base de datos en la instalación, cuando la
|
||||||
|
pasarela de pago envía el formulario a “/payment/redsys/return” odoo no sabe
|
||||||
|
con que base de datos procesar esta información, por lo que hay que establecer
|
||||||
|
los parametros <strong>dbfilter</strong> y <strong>dbname</strong> en el archivo de configuración.</p>
|
||||||
|
<p>Para mostrar simultáneamente en el comercio electrónico varios de los métodos
|
||||||
|
de pago que proporciona Redsys, como pago con tarjeta y Bizum por ejemplo,
|
||||||
|
debemos duplicar el medio de pago y escoger en el campo método de pago el que
|
||||||
|
corresponda en cada caso.</p>
|
||||||
|
<p>En los pagos con preautorización, el titular del TPV deberá solicitar al banco su activación.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="known-issues-roadmap">
|
||||||
|
<h1><a class="toc-backref" href="#id4">Known issues / Roadmap</a></h1>
|
||||||
|
<p>De acuerdo a los requisitos de Redsys, el tamaño máximo del número de pedido
|
||||||
|
resultante (<tt class="docutils literal">Ds_Order</tt>) es de 12 caracteres. Este addon trunca dicho
|
||||||
|
dato en el comienzo de la transacción, con el resultado de que, aunque Redsys
|
||||||
|
la aceptará, no se finalizará el pedido pedido en Odoo al retornar y entregará
|
||||||
|
un Error 500 a Redsys.
|
||||||
|
Para evitar esto, es recomendable seleccionar secuencias de pedido que se
|
||||||
|
ajusten a esta limitación, en particular de 10 o menos caracteres, al ser la
|
||||||
|
referencia un número extendido a partir del pedido, que incluye un guion y un
|
||||||
|
número secuencial para posibles repeticiones de pago.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="bug-tracker">
|
||||||
|
<h1><a class="toc-backref" href="#id5">Bug Tracker</a></h1>
|
||||||
|
<p>Bugs are tracked on <a class="reference external" href="https://github.com/Criptomart/foodcoopbcn/issues">GitHub Issues</a>.
|
||||||
|
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
|
||||||
|
<a class="reference external" href="https://github.com/Criptomart/foodcoopbcn/issues/new?body=module:%20payment_redsys_preauth%0Aversion:%2012.0%0A%0A**Steps%20to%20reproduce**%0A-%20...%0A%0A**Current%20behavior**%0A%0A**Expected%20behavior**">feedback</a>.</p>
|
||||||
|
<p>Do not contact contributors directly about support or help with technical issues.</p>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="credits">
|
||||||
|
<h1><a class="toc-backref" href="#id6">Credits</a></h1>
|
||||||
|
<div class="section" id="authors">
|
||||||
|
<h2><a class="toc-backref" href="#id7">Authors</a></h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li>Criptomart</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="contributors">
|
||||||
|
<h2><a class="toc-backref" href="#id8">Contributors</a></h2>
|
||||||
|
<ul class="simple">
|
||||||
|
<li><a class="reference external" href="https://www.criptomart.net">Criptomart</a>:<ul>
|
||||||
|
<li>Santi Noreña</li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div class="section" id="maintainers">
|
||||||
|
<h2><a class="toc-backref" href="#id9">Maintainers</a></h2>
|
||||||
|
<p>This module is part of the <a class="reference external" href="https://github.com/Criptomart/foodcoopbcn/tree/12.0/payment_redsys_preauth">Criptomart/foodcoopbcn</a> project on GitHub.</p>
|
||||||
|
<p>You are welcome to contribute.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
BIN
payment_redsys_preauth/static/img/bizum.png
Normal file
BIN
payment_redsys_preauth/static/img/bizum.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 4.8 KiB |
BIN
payment_redsys_preauth/static/src/img/redsys_icon.png
Normal file
BIN
payment_redsys_preauth/static/src/img/redsys_icon.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 11 KiB |
Loading…
Add table
Add a link
Reference in a new issue