Odoo18-Base/addons/website_sale_loyalty/wizard/coupon_share.py
2025-01-06 10:57:38 +07:00

97 lines
4.1 KiB
Python

# Part of Odoo. See LICENSE file for full copyright and licensing details.
from werkzeug.urls import url_encode
from odoo import fields, models, api, _
from odoo.exceptions import UserError, ValidationError
class CouponShare(models.TransientModel):
_name = 'coupon.share'
_description = 'Create links that apply a coupon and redirect to a specific page'
def _get_default_website_id(self):
program_website_id = self.env['loyalty.program'].browse(self.env.context.get('default_program_id')).website_id
if program_website_id:
return program_website_id
else:
Website = self.env['website']
websites = Website.search([])
return len(websites) == 1 and websites or Website
website_id = fields.Many2one('website', required=True, default=_get_default_website_id)
coupon_id = fields.Many2one('loyalty.card', domain="[('program_id', '=', program_id)]")
program_id = fields.Many2one('loyalty.program', required=True, domain=[
'|', ('program_type', '=', 'coupons'), # All coupons programs
'|', ('trigger', '=', 'with_code'), # All programs that require a code
('rule_ids.code', '!=', False), # All programs that can not trigger without a code
])
program_website_id = fields.Many2one('website', string='Program Website', related='program_id.website_id')
promo_code = fields.Char(compute='_compute_promo_code')
share_link = fields.Char(compute='_compute_share_link')
redirect = fields.Char(required=True, default='/shop')
@api.constrains('coupon_id', 'program_id')
def _check_program(self):
if self.filtered(lambda record: not record.coupon_id and record.program_id.program_type == 'coupons'):
raise ValidationError(_("A coupon is needed for coupon programs."))
@api.constrains('website_id', 'program_id')
def _check_website(self):
if self.filtered(lambda record: record.program_website_id and record.program_website_id != record.website_id):
raise ValidationError(_("The shared website should correspond to the website of the program."))
@api.depends('coupon_id.code', 'program_id.rule_ids.code')
def _compute_promo_code(self):
for record in self:
record.promo_code = record.coupon_id.code or record.program_id.rule_ids.filtered('code')[:1].code
@api.depends('website_id', 'redirect')
@api.depends_context('use_short_link')
def _compute_share_link(self):
for record in self:
target_url = '{base}/coupon/{code}?{query}'.format(
base=record.website_id.get_base_url(),
code=record.promo_code,
query=url_encode({'r': record.redirect}),
)
if record.env.context.get('use_short_link'):
tracker = self.env['link.tracker'].search([('url', '=', target_url)], limit=1)
if not tracker:
tracker = self.env['link.tracker'].create({'url': target_url})
record.share_link = tracker.short_url
else:
record.share_link = target_url
def action_generate_short_link(self):
return {
'name': _('Share'),
'type': 'ir.actions.act_window',
'view_mode': 'form',
'res_model': 'coupon.share',
'target': 'new',
'res_id': self.id,
'context': {
'use_short_link': True,
}
}
@api.model
def create_share_action(self, coupon=None, program=None):
if bool(program) == bool(coupon):
raise UserError(_("Provide either a coupon or a program."))
return {
'name': _('Share %s', self.env["loyalty.program"]._program_items_name().get((program or coupon).program_type, "")),
'type': 'ir.actions.act_window',
'view_mode': 'form',
'res_model': 'coupon.share',
'target': 'new',
'context': {
'default_program_id': program and program.id or coupon.program_id.id,
'default_coupon_id': coupon and coupon.id or None,
}
}