diff --git a/addons/l10n_be_intrastat/wizard/xml_decl.py b/addons/l10n_be_intrastat/wizard/xml_decl.py index 8cadb3d094d..33810226616 100644 --- a/addons/l10n_be_intrastat/wizard/xml_decl.py +++ b/addons/l10n_be_intrastat/wizard/xml_decl.py @@ -114,6 +114,11 @@ class XmlDeclaration(models.TransientModel): round_digits = self._get_rounding_digits() _round = partial(float_round, precision_digits=round_digits) + value, weight, supply_units = amounts + # Assuming weight cannot be negative + if weight >= 0 and weight < 0.01: + weight = 0.01 + self._set_Dim(item, 'EXSEQCODE', unicode(numlgn)) self._set_Dim(item, 'EXTRF', unicode(linekey.EXTRF)) self._set_Dim(item, 'EXCNT', unicode(linekey.EXCNT)) @@ -123,9 +128,9 @@ class XmlDeclaration(models.TransientModel): if extendedmode: self._set_Dim(item, 'EXTPC', unicode(linekey.EXTPC)) self._set_Dim(item, 'EXDELTRM', unicode(linekey.EXDELTRM)) - self._set_Dim(item, 'EXTXVAL', unicode(_round(amounts[0])).replace(".", ",")) - self._set_Dim(item, 'EXWEIGHT', unicode(_round(amounts[1])).replace(".", ",")) - self._set_Dim(item, 'EXUNITS', unicode(_round(amounts[2])).replace(".", ",")) + self._set_Dim(item, 'EXTXVAL', unicode(_round(value)).replace(".", ",")) + self._set_Dim(item, 'EXWEIGHT', unicode(_round(weight)).replace(".", ",")) + self._set_Dim(item, 'EXUNITS', unicode(_round(supply_units)).replace(".", ",")) def _get_intrastat_linekey(self, declcode, inv_line, dispatchmode, extendedmode): IntrastatRegion = self.env['l10n_be_intrastat.region'] diff --git a/addons/payment_authorize/models/payment.py b/addons/payment_authorize/models/payment.py index 227b0d49d83..5c368b3ff58 100644 --- a/addons/payment_authorize/models/payment.py +++ b/addons/payment_authorize/models/payment.py @@ -24,6 +24,7 @@ class PaymentAcquirerAuthorize(models.Model): provider = fields.Selection(selection_add=[('authorize', 'Authorize.Net')]) authorize_login = fields.Char(string='API Login Id', required_if_provider='authorize', groups='base.group_user') authorize_transaction_key = fields.Char(string='API Transaction Key', required_if_provider='authorize', groups='base.group_user') + authorize_signature_key = fields.Char(string='API Signature Key', groups='base.group_user', compute="_compute_auth_signature_key", inverse="_inverse_auth_signature_key") def _get_feature_support(self): """Get advanced feature support by provider. @@ -41,6 +42,16 @@ class PaymentAcquirerAuthorize(models.Model): res['tokenize'].append('authorize') return res + def _compute_auth_signature_key(self): + ICP = self.env['ir.config_parameter'].sudo() + for acquirer in self.filtered(lambda a: a.provider == 'authorize'): + acquirer.authorize_signature_key = ICP.get_param('payment_authorize.signature_key_%s' % acquirer.id) + + def _inverse_auth_signature_key(self): + ICP = self.env['ir.config_parameter'].sudo() + for acquirer in self.filtered(lambda a: a.provider == 'authorize'): + ICP.set_param('payment_authorize.signature_key_%s' % acquirer.id, acquirer.authorize_signature_key) + def _get_authorize_urls(self, environment): """ Authorize URLs """ if environment == 'prod': @@ -56,12 +67,24 @@ class PaymentAcquirerAuthorize(models.Model): values['x_amount'], values['x_currency_code']]) - # [BACKWARD COMPATIBILITY] Check that the merchant did update his transaction - # key to signature key (end of MD5 support from Authorize.net) + # [BACKWARD COMPATIBILITY, 2nd edition] # The signature key is now '128-character hexadecimal format', while the # transaction key was only 16-character. - if len(values['x_trans_key']) == 128: + # One of 2 things should have happened: + # 1/ the Transaction Key has been replaced with the Signature Key value (patch from March 2019) + # => Use that to sign, but server-to-server won't work since it uses transaction key + # as its credentials + # 2/ the Signature key is a new field (patch from July 2019) + # => Use that field for the signature + + # FORWARD-PORT NOTE: be careful, hexadecimal decoding in python 3 is done by using bytes.fromhex(str) + # (P2) self.authorize_signature_key.decode("hex") ==> (P3) bytes.fromhex(self.authorize_signature_key) + # FORWARD-PORT NOTE NUMERO DOS: forward part to saas-12.4 but no further + if len(values['x_trans_key']) == 128 and not self.authorize_signature_key: + self.authorize_signature_key = values['x_trans_key'] # store in the correct field return hmac.new(values['x_trans_key'].decode("hex"), data, hashlib.sha512).hexdigest().upper() + elif self.authorize_signature_key: + return hmac.new(self.authorize_signature_key.decode("hex"), data, hashlib.sha512).hexdigest().upper() else: return hmac.new(str(values['x_trans_key']), data, hashlib.md5).hexdigest() diff --git a/addons/payment_authorize/views/payment_views.xml b/addons/payment_authorize/views/payment_views.xml index 7a957e41442..b3f3ed8e535 100644 --- a/addons/payment_authorize/views/payment_views.xml +++ b/addons/payment_authorize/views/payment_views.xml @@ -9,6 +9,7 @@ + How to get paid with Authorize.Net diff --git a/addons/website_sale/controllers/main.py b/addons/website_sale/controllers/main.py index 1ecfb31162a..d42c69c4440 100644 --- a/addons/website_sale/controllers/main.py +++ b/addons/website_sale/controllers/main.py @@ -338,9 +338,11 @@ class WebsiteSale(http.Controller): @http.route(['/shop/pricelist'], type='http', auth="public", website=True) def pricelist(self, promo, **post): redirect = post.get('r', '/shop/cart') - pricelist = request.env['product.pricelist'].sudo().search([('code', '=', promo)], limit=1) - if not pricelist or (pricelist and not request.website.is_pricelist_available(pricelist.id)): - return request.redirect("%s?code_not_available=1" % redirect) + # empty promo code is used to reset/remove pricelist (see `sale_get_order()`) + if promo: + pricelist = request.env['product.pricelist'].sudo().search([('code', '=', promo)], limit=1) + if (not pricelist or (pricelist and not request.website.is_pricelist_available(pricelist.id))): + return request.redirect("%s?code_not_available=1" % redirect) request.website.sale_get_order(code=promo) return request.redirect(redirect)