payment_transaction.py 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. # Part of Odoo. See LICENSE file for full copyright and licensing details.
  2. from werkzeug import urls
  3. from odoo import _, api, models
  4. from odoo.exceptions import ValidationError
  5. from odoo.addons.payment import utils as payment_utils
  6. from odoo.addons.payment_payumoney.controllers.main import PayUMoneyController
  7. class PaymentTransaction(models.Model):
  8. _inherit = 'payment.transaction'
  9. def _get_specific_rendering_values(self, processing_values):
  10. """ Override of payment to return Payumoney-specific rendering values.
  11. Note: self.ensure_one() from `_get_processing_values`
  12. :param dict processing_values: The generic and specific processing values of the transaction
  13. :return: The dict of provider-specific processing values
  14. :rtype: dict
  15. """
  16. res = super()._get_specific_rendering_values(processing_values)
  17. if self.provider_code != 'payumoney':
  18. return res
  19. first_name, last_name = payment_utils.split_partner_name(self.partner_id.name)
  20. api_url = 'https://secure.payu.in/_payment' if self.provider_id.state == 'enabled' \
  21. else 'https://sandboxsecure.payu.in/_payment'
  22. payumoney_values = {
  23. 'key': self.provider_id.payumoney_merchant_key,
  24. 'txnid': self.reference,
  25. 'amount': self.amount,
  26. 'productinfo': self.reference,
  27. 'firstname': first_name,
  28. 'lastname': last_name,
  29. 'email': self.partner_email,
  30. 'phone': self.partner_phone,
  31. 'return_url': urls.url_join(self.get_base_url(), PayUMoneyController._return_url),
  32. 'api_url': api_url,
  33. }
  34. payumoney_values['hash'] = self.provider_id._payumoney_generate_sign(
  35. payumoney_values, incoming=False,
  36. )
  37. return payumoney_values
  38. def _get_tx_from_notification_data(self, provider_code, notification_data):
  39. """ Override of payment to find the transaction based on Payumoney data.
  40. :param str provider_code: The code of the provider that handled the transaction
  41. :param dict notification_data: The notification data sent by the provider
  42. :return: The transaction if found
  43. :rtype: recordset of `payment.transaction`
  44. :raise: ValidationError if inconsistent data were received
  45. :raise: ValidationError if the data match no transaction
  46. """
  47. tx = super()._get_tx_from_notification_data(provider_code, notification_data)
  48. if provider_code != 'payumoney' or len(tx) == 1:
  49. return tx
  50. reference = notification_data.get('txnid')
  51. if not reference:
  52. raise ValidationError(
  53. "PayUmoney: " + _("Received data with missing reference (%s)", reference)
  54. )
  55. tx = self.search([('reference', '=', reference), ('provider_code', '=', 'payumoney')])
  56. if not tx:
  57. raise ValidationError(
  58. "PayUmoney: " + _("No transaction found matching reference %s.", reference)
  59. )
  60. return tx
  61. def _process_notification_data(self, notification_data):
  62. """ Override of payment to process the transaction based on Payumoney data.
  63. Note: self.ensure_one()
  64. :param dict notification_data: The notification data sent by the provider
  65. :return: None
  66. """
  67. super()._process_notification_data(notification_data)
  68. if self.provider_code != 'payumoney':
  69. return
  70. status = notification_data.get('status')
  71. self.provider_reference = notification_data.get('payuMoneyId')
  72. if status == 'success':
  73. self._set_done()
  74. else: # 'failure'
  75. # See https://www.payumoney.com/pdf/PayUMoney-Technical-Integration-Document.pdf
  76. error_code = notification_data.get('Error')
  77. self._set_error(
  78. "PayUmoney: " + _("The payment encountered an error with code %s", error_code)
  79. )