Files
tradon/modules/account_tax_rule_country/account.py
2026-03-14 09:42:12 +00:00

177 lines
6.9 KiB
Python

# This file is part of Tryton. The COPYRIGHT file at the top level of
# this repository contains the full copyright notices and license terms.
from trytond.model import fields
from trytond.pool import Pool, PoolMeta
from trytond.pyson import Eval
class TaxRule(metaclass=PoolMeta):
__name__ = 'account.tax.rule'
def apply(self, tax, pattern):
pool = Pool()
Subdivision = pool.get('country.subdivision')
def parents(subdivision):
while subdivision:
yield subdivision.id
subdivision = subdivision.parent
pattern = pattern.copy()
pattern.setdefault('from_country')
pattern.setdefault('to_country')
for name in ['from_subdivision', 'to_subdivision']:
subdivision = pattern.pop(name, None)
if not subdivision:
continue
subdivision = Subdivision(subdivision)
pattern[name] = list(parents(subdivision))
return super().apply(tax, pattern)
class _TaxRuleLineMixin:
__slots__ = ()
from_country = fields.Many2One(
'country.country', 'From Country', ondelete='RESTRICT',
help="Apply only to addresses of this country.")
from_subdivision = fields.Many2One(
'country.subdivision', "From Subdivision", ondelete='RESTRICT',
domain=[
('country', '=', Eval('from_country', -1)),
],
states={
'invisible': ~Eval('from_country'),
},
help="Apply only to addresses in this subdivision.")
to_country = fields.Many2One(
'country.country', 'To Country', ondelete='RESTRICT',
help="Apply only to addresses of this country.")
to_subdivision = fields.Many2One(
'country.subdivision', "To Subdivision", ondelete='RESTRICT',
domain=[
('country', '=', Eval('to_country', -1)),
],
states={
'invisible': ~Eval('to_country'),
},
help="Apply only to addresses in this subdivision.")
class TaxRuleLineTemplate(_TaxRuleLineMixin, metaclass=PoolMeta):
__name__ = 'account.tax.rule.line.template'
def _get_tax_rule_line_value(self, rule_line=None):
value = super()._get_tax_rule_line_value(
rule_line=rule_line)
if not rule_line or rule_line.from_country != self.from_country:
value['from_country'] = (
self.from_country.id if self.from_country else None)
if (not rule_line
or rule_line.from_subdivision != self.from_subdivision):
value['from_subdivision'] = (
self.from_subdivision.id if self.from_subdivision else None)
if not rule_line or rule_line.to_country != self.to_country:
value['to_country'] = (
self.to_country.id if self.to_country else None)
if (not rule_line
or rule_line.to_subdivision != self.to_subdivision):
value['to_subdivision'] = (
self.to_subdivision.id if self.to_subdivision else None)
return value
class TaxRuleLine(_TaxRuleLineMixin, metaclass=PoolMeta):
__name__ = 'account.tax.rule.line'
def match(self, pattern):
for name in ['from_subdivision', 'to_subdivision']:
subdivision = getattr(self, name)
if name not in pattern:
if subdivision:
return False
else:
continue
pattern = pattern.copy()
subdivisions = pattern.pop(name)
if (subdivision is not None
and subdivision.id not in subdivisions):
return False
return super().match(pattern)
class InvoiceLine(metaclass=PoolMeta):
__name__ = 'account.invoice.line'
@fields.depends('origin')
def _get_tax_rule_pattern(self):
pool = Pool()
try:
SaleLine = pool.get('sale.line')
except KeyError:
SaleLine = None
try:
PurchaseLine = pool.get('purchase.line')
except KeyError:
PurchaseLine = None
try:
Move = pool.get('stock.move')
ShipmentOut = pool.get('stock.shipment.out')
ShipmentOutReturn = pool.get('stock.shipment.out.return')
except KeyError:
Move = ShipmentOut = ShipmentOutReturn = None
pattern = super()._get_tax_rule_pattern()
from_country = from_subdivision = to_country = to_subdivision = None
if (SaleLine
and isinstance(self.origin, SaleLine)
and self.origin.id >= 0):
warehouse = self.origin.warehouse
if warehouse and warehouse.address:
from_country = warehouse.address.country
from_subdivision = warehouse.address.subdivision
shipment_address = self.origin.sale.shipment_address
to_country = shipment_address.country
to_subdivision = shipment_address.subdivision
elif (PurchaseLine
and isinstance(self.origin, PurchaseLine)
and self.origin.id >= 0):
invoice_address = self.origin.purchase.invoice_address
from_country = invoice_address.country
from_subdivision = invoice_address.subdivision
warehouse = self.origin.warehouse
if warehouse and warehouse.address:
to_country = warehouse.address.country
to_subdivision = warehouse.address.subdivision
elif (Move
and isinstance(self.origin, Move)
and self.origin.id >= 0):
move = self.origin
if move.from_location.warehouse:
warehouse_address = move.from_location.warehouse.address
if warehouse_address:
from_country = warehouse_address.country
from_subdivision = warehouse_address.subdivision
elif isinstance(move.origin, ShipmentOutReturn):
delivery_address = move.origin.delivery_address
from_country = delivery_address.country
from_subdivision = delivery_address.subdivision
if move.to_location.warehouse:
warehouse_address = move.to_location.warehouse.address
if warehouse_address:
to_country = warehouse_address.country
to_subdivision = warehouse_address.subdivision
elif isinstance(move.origin, ShipmentOut):
delivery_address = move.origin.delivery_address
to_country = delivery_address.country
to_subdivision = delivery_address.subdivision
pattern['from_country'] = from_country.id if from_country else None
pattern['from_subdivision'] = (
from_subdivision.id if from_subdivision else None)
pattern['to_country'] = to_country.id if to_country else None
pattern['to_subdivision'] = (
to_subdivision.id if to_subdivision else None)
return pattern