From ad2bdf6d9411e8d53bf72cb4da484e60e88d6c49 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thibault=20Delavall=C3=A9e?= Date: Thu, 28 Nov 2013 17:17:07 +0100 Subject: [PATCH] [IMP] payment_acquirer_paypal: added fees computation on paypal acquirer. paypal acquirer model: added paypal_fee_active and paypal_fee_* fields: fix and variable fees, for domestic and international transactions. updated views accordingly + cleaned paypal form view. updated tests updated form, adding handling input in the paypal button that is the input controlling the fees in the tx process. When creating a paypal tx, it dynamically computes fees. bzr revid: tde@openerp.com-20131128161707-ignhrlphts47wk72 --- .../views/payment_acquirer.xml | 58 +++++++++++-------- .../payment_acquirer_paypal/models/paypal.py | 50 +++++++++++++++- .../tests/test_paypal.py | 34 +++++++++++ .../views/payment_acquirer.xml | 32 +++++++--- .../payment_acquirer_paypal/views/paypal.xml | 4 ++ 5 files changed, 143 insertions(+), 35 deletions(-) diff --git a/addons/payment_acquirer/views/payment_acquirer.xml b/addons/payment_acquirer/views/payment_acquirer.xml index 916f4915e66..09c209f7dee 100644 --- a/addons/payment_acquirer/views/payment_acquirer.xml +++ b/addons/payment_acquirer/views/payment_acquirer.xml @@ -12,32 +12,41 @@ payment.acquirer
- - - - - - + +
@@ -84,6 +93,7 @@ + diff --git a/addons/payment_acquirer_paypal/models/paypal.py b/addons/payment_acquirer_paypal/models/paypal.py index 50b16d0e818..40c14ccbe36 100644 --- a/addons/payment_acquirer_paypal/models/paypal.py +++ b/addons/payment_acquirer_paypal/models/paypal.py @@ -27,6 +27,13 @@ class AcquirerPaypal(osv.Model): 'paypal_username': fields.char('Username', required_if_provider='paypal'), 'paypal_tx_url': fields.char('Transaction URL', required_if_provider='paypal'), 'paypal_use_ipn': fields.boolean('Use IPN'), + # Fees + 'paypal_fee_active': fields.boolean('Compute fees'), + 'paypal_fee_dom_fixed': fields.float('Fixed domestic fees'), + 'paypal_fee_dom_var': fields.float('Variable domestic fees (in percents)'), + 'paypal_fee_int_fixed': fields.float('Fixed international fees'), + 'paypal_fee_int_var': fields.float('Variable international fees (in percents)'), + # Server 2 server 'paypal_api_enabled': fields.boolean('Use Rest API'), 'paypal_api_username': fields.char('Rest API Username'), 'paypal_api_password': fields.char('Rest API Password'), @@ -35,11 +42,33 @@ class AcquirerPaypal(osv.Model): } _defaults = { - 'paypal_use_ipn': True, - 'paypal_api_enabled': False, 'paypal_tx_url': 'https://www.sandbox.paypal.com/cgi-bin/webscr', + 'paypal_use_ipn': True, + 'paypal_fee_active': False, + 'paypal_fee_dom_fixed': 0.35, + 'paypal_fee_dom_var': 3.4, + 'paypal_fee_int_fixed': 0.35, + 'paypal_fee_int_var': 3.9, + 'paypal_api_enabled': False, } + def paypal_compute_fees(self, cr, uid, id, amount, country_id, context=None): + """ Compute paypal fees. + + :param float amount: the amount to pay + :param integer country_id: an ID of a res.country, or None. This is + the customer's country, to be compared to + the acquirer company country. + :return float fees: computed fees + """ + acquirer = self.browse(cr, uid, id, context=context) + country = self.pool['res.country'].browse(cr, uid, country_id, context=context) + if country and acquirer.company_id.country_id.id == country.id: + fees = amount * (1 + acquirer.paypal_fee_dom_var / 100.0) + acquirer.paypal_fee_dom_fixed - amount + else: + fees = amount * (1 + acquirer.paypal_fee_int_var / 100.0) + acquirer.paypal_fee_int_fixed - amount + return fees + def paypal_form_generate_values(self, cr, uid, id, reference, amount, currency, partner_id=False, partner_values=None, tx_custom_values=None, context=None): if partner_values is None: partner_values = {} @@ -48,6 +77,11 @@ class AcquirerPaypal(osv.Model): partner = None if partner_id: partner = self.pool['res.partner'].browse(cr, uid, partner_id, context=context) + if partner: + country_id = partner.country_id.id + else: + country_ids = self.pool['res.country'].search(cr, uid, [('name', '=', partner_values.get('country_name'))], context=context) + country_id = country_ids and country_ids[0] or None tx_values = { 'cmd': '_xclick', 'business': acquirer.paypal_email_id, @@ -66,6 +100,8 @@ class AcquirerPaypal(osv.Model): 'notify_url': '%s' % urlparse.urljoin(base_url, PaypalController._notify_url), 'cancel_return': '%s' % urlparse.urljoin(base_url, PaypalController._cancel_url), } + if acquirer.paypal_fee_active: + tx_values['handling'] = '%.2f' % self.paypal_compute_fees(cr, uid, acquirer.id, amount, country_id, context=context) if tx_custom_values and tx_custom_values.get('return_url'): tx_values['custom'] = json.dumps({'return_url': '%s' % tx_custom_values.pop('return_url')}) if tx_custom_values: @@ -112,6 +148,16 @@ class TxPaypal(osv.Model): 'paypal_txn_type': fields.char('Transaction type'), } + # -------------------------------------------------- + # CRUD + # -------------------------------------------------- + + def paypal_create(self, cr, uid, values, context=None): + paypal = self.pool['payment.acquirer'].browse(cr, uid, values['acquirer_id'], context=context) + if paypal.paypal_fee_active: + values['fees'] = self.pool['payment.acquirer'].paypal_compute_fees(cr, uid, paypal.id, values.get('amount', 0.0), values.get('country_id'), context=context) + return values + # -------------------------------------------------- # FORM RELATED METHODS # -------------------------------------------------- diff --git a/addons/payment_acquirer_paypal/tests/test_paypal.py b/addons/payment_acquirer_paypal/tests/test_paypal.py index d3d9bfb7087..9b2c65272e6 100644 --- a/addons/payment_acquirer_paypal/tests/test_paypal.py +++ b/addons/payment_acquirer_paypal/tests/test_paypal.py @@ -95,6 +95,9 @@ class PaypalForm(PaypalCommon): def test_10_paypal_form_render(self): cr, uid, context = self.cr, self.uid, {} + # be sure not to do stupid things + paypal = self.payment_acquirer.browse(cr, uid, self.paypal_id, context) + self.assertEqual(paypal.env, 'test', 'test without test env') # ---------------------------------------- # Test: button direct rendering @@ -139,9 +142,40 @@ class PaypalForm(PaypalCommon): 'paypal: wrong value for form: received %s instead of %s' % (form_input.get('value'), form_values[form_input.get('name')]) ) + def test_11_paypal_form_with_fees(self): + cr, uid, context = self.cr, self.uid, {} + self.payment_acquirer.write(cr, uid, self.paypal_id, { + 'paypal_fee_active': True, + }, context) + + # be sure not to do stupid things + paypal = self.payment_acquirer.browse(self.cr, self.uid, self.paypal_id, None) + self.assertEqual(paypal.env, 'test', 'test without test env') + + # render the button + res = self.payment_acquirer.render( + cr, uid, self.paypal_id, + 'test_ref0', 12.50, self.currency_euro, + partner_id=None, + partner_values=self.buyer_values, + context=context) + + # check form result + handling_found = False + tree = objectify.fromstring(res) + self.assertEqual(tree.get('action'), 'https://www.sandbox.paypal.com/cgi-bin/webscr', 'paypal: wrong form POST url') + for form_input in tree.input: + if form_input.get('name') in ['handling']: + handling_found = True + self.assertEqual(form_input.get('value'), '0.84', 'paypal: wrong computed fees') + self.assertTrue(handling_found, 'paypal: paypal_fee_active did not add handling input in rendered form') + @mute_logger('openerp.addons.payment_acquirer_paypal.models.paypal', 'ValidationError') def test_20_paypal_form_management(self): cr, uid, context = self.cr, self.uid, {} + # be sure not to do stupid things + paypal = self.payment_acquirer.browse(cr, uid, self.paypal_id, context) + self.assertEqual(paypal.env, 'test', 'test without test env') # typical data posted by paypal after client has successfully paid paypal_post_data = { diff --git a/addons/payment_acquirer_paypal/views/payment_acquirer.xml b/addons/payment_acquirer_paypal/views/payment_acquirer.xml index d0d97cdfa12..8a6c36ac7b2 100644 --- a/addons/payment_acquirer_paypal/views/payment_acquirer.xml +++ b/addons/payment_acquirer_paypal/views/payment_acquirer.xml @@ -7,15 +7,29 @@ payment.acquirer - - - - - - - - + + + + + + + + + + + + + + + + + diff --git a/addons/payment_acquirer_paypal/views/paypal.xml b/addons/payment_acquirer_paypal/views/paypal.xml index 329714fb0a5..a6f401f6c3c 100644 --- a/addons/payment_acquirer_paypal/views/paypal.xml +++ b/addons/payment_acquirer_paypal/views/paypal.xml @@ -9,6 +9,10 @@ + + + +