Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[FIX] sale_loyalty: prevent error while remove all product quantities from cart #163055

Conversation

mega-odoo
Copy link
Contributor

@mega-odoo mega-odoo commented Apr 23, 2024

Currently, an error is generated when removing all product quantities from the cart after a claiming a reward(discount).

Step to produce:

  • Install a 'website_sale_loyalty' module.
  • Navigate to the website / eCommerce / Loyalty / Discount & Loyalty to create a record.
  • Set the Loyalty Program name and Program Type as 'Loyalty Cards'.(Ensure it's available on sale and the website.)
  • And add 'Rewards' and set a Reward Type as 'Discount' which is applied to on Cheapest Product.
  • Go to the website shop add any product on a card, Open a cart increase the quantity of the product, and claim the discount reward.
  • Again go to Loyalty Program and open Loyalty Card, Open a record and add a Balance(greater than 200 as default reward points are 200) and copy 'Code'.
  • Again go to the website shop and apply this code to claim a discount after a claim discount.
  • Now remove all product quantity from a cart.

See Traceback:

AttributeError: 'bool' object has no attribute 'price_unit'
  File "odoo/http.py", line 2252, in __call__
    response = request._serve_db()
  File "odoo/http.py", line 1828, in _serve_db
    return self._transactioning(_serve_ir_http, readonly=ro)
  File "odoo/http.py", line 1848, in _transactioning
    return service_model.retrying(func, env=self.env)
  File "odoo/service/model.py", line 134, in retrying
    result = func()
  File "odoo/http.py", line 1826, in _serve_ir_http
    return self._serve_ir_http(rule, args)
  File "odoo/http.py", line 1833, in _serve_ir_http
    response = self.dispatcher.dispatch(rule.endpoint, args)
  File "odoo/http.py", line 2058, in dispatch
    result = self.request.registry['ir.http']._dispatch(endpoint)
  File "odoo/addons/base/models/ir_http.py", line 222, in _dispatch
    result = endpoint(**request.params)
  File "odoo/http.py", line 740, in route_wrapper
    result = endpoint(self, *args, **params_ok)
  File "addons/website_sale_loyalty/controllers/main.py", line 126, in cart_update_json
    return super().cart_update_json(*args, set_qty=set_qty, **kwargs)
  File "odoo/http.py", line 740, in route_wrapper
    result = endpoint(self, *args, **params_ok)
  File "addons/website_sale/controllers/main.py", line 817, in cart_update_json
    values = order._cart_update(
  File "addons/website_sale_loyalty/models/sale_order.py", line 174, in _cart_update
    self._update_programs_and_rewards()
  File "addons/website_sale_loyalty/models/sale_order.py", line 60, in _update_programs_and_rewards
    return super()._update_programs_and_rewards()
  File "addons/sale_loyalty/models/sale_order.py", line 802, in _update_programs_and_rewards
    values_list = self._get_reward_line_values(reward, coupon, product=reward_key[3])
  File "addons/sale_loyalty_delivery/models/sale_order.py", line 64, in _get_reward_line_values
    return super()._get_reward_line_values(reward, coupon, **kwargs)
  File "addons/sale_loyalty/models/sale_order.py", line 573, in _get_reward_line_values
    return self._get_reward_values_discount(reward, coupon, **kwargs)
  File "addons/sale_loyalty/models/sale_order.py", line 321, in _get_reward_values_discount
    discountable, discountable_per_tax = self._discountable_cheapest(reward)
  File "addons/sale_loyalty/models/sale_order.py", line 211, in _discountable_cheapest
    discountable = cheapest_line.price_unit * (1 - (cheapest_line.discount or 0) / 100)

The issue occurs when attempting to remove all product quantities from a cart. At this point [1], a bool value 'False' is returned, and the system attempts to get a value of 'price_unit' from it [2].

link [1]:

def _cheapest_line(self):
self.ensure_one()
cheapest_line = False
for line in (self.order_line - self._get_no_effect_on_threshold_lines()):
if line.reward_id or not line.product_uom_qty or not line.price_unit:
continue
if not cheapest_line or cheapest_line.price_unit > line.price_unit:
cheapest_line = line
return cheapest_line

link [2]:

discountable = cheapest_line.price_total

This commit resolves the issue, If the _cheapest_line() method returns False then also returns False from _discountable_cheapest(), To raise an error at [3].

link [3]:

discountable, discountable_per_tax = self._discountable_cheapest(reward)
if not discountable:
if not reward.program_id.is_payment_program and any(line.reward_id.program_id.is_payment_program for line in self.order_line):
return [{
'name': _("TEMPORARY DISCOUNT LINE"),
'product_id': reward.discount_line_product_id.id,
'price_unit': 0,
'product_uom_qty': 0,
'product_uom': reward.discount_line_product_id.uom_id.id,
'reward_id': reward.id,
'coupon_id': coupon.id,
'points_cost': 0,
'reward_identifier_code': _generate_random_reward_code(),
'sequence': sequence,
'tax_id': [(Command.CLEAR, 0, 0)]
}]
raise UserError(_('There is nothing to discount'))

sentry-5119007021


I confirm I have signed the CLA and read the PR guidelines at www.odoo.com/submit-pr

@robodoo
Copy link
Contributor

robodoo commented Apr 23, 2024

@C3POdoo C3POdoo added the RD research & development, internal work label Apr 23, 2024
… from cart

Currently, an error is generated when removing all product quantities from the
cart after a claiming a reward(discount).

Step to produce:

- Install a 'website_sale_loyalty' module.
- Navigate to the website / eCommerce / Loyalty / Discount & Loyalty to create
a record.
- Set the Loyalty Program name and Program Type as 'Loyalty Cards'.(Ensure it's
available on sale and the website.)
-  And add 'Rewards' and set a Reward Type as 'Discount' which is applied to
on Cheapest Product.
 - Go to the website shop add any product on a card, Open a cart increase the
 quantity of the product, and claim the discount reward.
- Again go to Loyalty Program and open Loyalty Card, Open a record and add a
Balance(greater than 200 as default reward points are 200) and copy 'Code'.
- Again go to the website shop and apply this code to claim a discount after a
claim discount.
- Now remove all product quantity from a cart.

AttributeError: 'bool' object has no attribute 'price_unit'

The issue occurs when attempting to remove all product quantities from a cart.
At this point [1], a bool value  'False' is returned, and the system attempts to
get a value of 'price_unit' from it [2].

link [1]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L187-L195

link [2]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L205

This commit resolve issue, If the _cheapest_line() method returns False then
also returns False from _discountable_cheapest(), To raise an error at [3].

link [3]:  https://github.com/odoo/odoo/blob/cbc40eccf576c499709f7825edad9a3b3ce7a22d/addons/sale_loyalty/models/sale_order.py#L317-L333

sentry-5119007021
@mega-odoo mega-odoo force-pushed the 16.0-sentry-5119007021-website-sale-loyalty-attribute-error-mega branch from 0083817 to 988bf4f Compare April 24, 2024 08:52
@mega-odoo
Copy link
Contributor Author

Hello @odoo/sentry_reviewers

please review this PR.

Thank You 🙂

@mega-odoo mega-odoo marked this pull request as ready for review April 24, 2024 13:32
@C3POdoo C3POdoo requested a review from a team April 24, 2024 13:38
Copy link
Contributor

@anko-odoo anko-odoo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM :)

Copy link
Contributor

@Feyensv Feyensv left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@robodoo delegate+

@mega-odoo
Copy link
Contributor Author

@robodoo r+

robodoo pushed a commit that referenced this pull request Apr 25, 2024
… from cart

Currently, an error is generated when removing all product quantities from the
cart after a claiming a reward(discount).

Step to produce:

- Install a 'website_sale_loyalty' module.
- Navigate to the website / eCommerce / Loyalty / Discount & Loyalty to create
a record.
- Set the Loyalty Program name and Program Type as 'Loyalty Cards'.(Ensure it's
available on sale and the website.)
-  And add 'Rewards' and set a Reward Type as 'Discount' which is applied to
on Cheapest Product.
 - Go to the website shop add any product on a card, Open a cart increase the
 quantity of the product, and claim the discount reward.
- Again go to Loyalty Program and open Loyalty Card, Open a record and add a
Balance(greater than 200 as default reward points are 200) and copy 'Code'.
- Again go to the website shop and apply this code to claim a discount after a
claim discount.
- Now remove all product quantity from a cart.

AttributeError: 'bool' object has no attribute 'price_unit'

The issue occurs when attempting to remove all product quantities from a cart.
At this point [1], a bool value  'False' is returned, and the system attempts to
get a value of 'price_unit' from it [2].

link [1]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L187-L195

link [2]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L205

This commit resolve issue, If the _cheapest_line() method returns False then
also returns False from _discountable_cheapest(), To raise an error at [3].

link [3]:  https://github.com/odoo/odoo/blob/cbc40eccf576c499709f7825edad9a3b3ce7a22d/addons/sale_loyalty/models/sale_order.py#L317-L333

sentry-5119007021

closes #163055

Signed-off-by: Meet Gandhi (mega) <mega@odoo.com>
@robodoo robodoo closed this Apr 25, 2024
MohammedBasioni pushed a commit to odoo-dev/odoo that referenced this pull request Apr 29, 2024
… from cart

Currently, an error is generated when removing all product quantities from the
cart after a claiming a reward(discount).

Step to produce:

- Install a 'website_sale_loyalty' module.
- Navigate to the website / eCommerce / Loyalty / Discount & Loyalty to create
a record.
- Set the Loyalty Program name and Program Type as 'Loyalty Cards'.(Ensure it's
available on sale and the website.)
-  And add 'Rewards' and set a Reward Type as 'Discount' which is applied to
on Cheapest Product.
 - Go to the website shop add any product on a card, Open a cart increase the
 quantity of the product, and claim the discount reward.
- Again go to Loyalty Program and open Loyalty Card, Open a record and add a
Balance(greater than 200 as default reward points are 200) and copy 'Code'.
- Again go to the website shop and apply this code to claim a discount after a
claim discount.
- Now remove all product quantity from a cart.

AttributeError: 'bool' object has no attribute 'price_unit'

The issue occurs when attempting to remove all product quantities from a cart.
At this point [1], a bool value  'False' is returned, and the system attempts to
get a value of 'price_unit' from it [2].

link [1]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L187-L195

link [2]: https://github.com/odoo/odoo/blob/499056a82db26f7d9caa86314e666e2bd49cc79c/addons/sale_loyalty/models/sale_order.py#L205

This commit resolve issue, If the _cheapest_line() method returns False then
also returns False from _discountable_cheapest(), To raise an error at [3].

link [3]:  https://github.com/odoo/odoo/blob/cbc40eccf576c499709f7825edad9a3b3ce7a22d/addons/sale_loyalty/models/sale_order.py#L317-L333

sentry-5119007021

closes odoo#163055

Signed-off-by: Meet Gandhi (mega) <mega@odoo.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
RD research & development, internal work
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

6 participants