feat(configurator): totals = one tax on (subtotal + charge)
This commit is contained in:
@@ -28,3 +28,19 @@ class TestChargeTaxLot(TransactionCase):
|
||||
self.assertEqual(ct.default_amount, 75.0)
|
||||
cid, cname = self.env['fp.additional.charge.type'].name_create('Setup')
|
||||
self.assertTrue(cid)
|
||||
|
||||
# ----- Task 3: totals -----
|
||||
def _make_wizard(self, **kw):
|
||||
vals = {'partner_id': self.partner.id}
|
||||
vals.update(kw)
|
||||
return self.env['fp.direct.order.wizard'].create(vals)
|
||||
|
||||
def test_tax_applies_on_subtotal_plus_charge(self):
|
||||
wiz = self._make_wizard(charge_amount=100.0, tax_id=self.tax13.id)
|
||||
self.env['fp.direct.order.line'].create({
|
||||
'wizard_id': wiz.id, 'quantity': 1, 'unit_price': 50.0,
|
||||
})
|
||||
wiz.invalidate_recordset()
|
||||
self.assertEqual(wiz.total_subtotal, 50.0)
|
||||
self.assertAlmostEqual(wiz.total_tax, 19.5, places=2)
|
||||
self.assertAlmostEqual(wiz.total_amount, 169.5, places=2)
|
||||
|
||||
@@ -401,65 +401,41 @@ class FpDirectOrderWizard(models.Model):
|
||||
|
||||
# ---- Computes ----
|
||||
@api.depends(
|
||||
'line_ids.line_subtotal',
|
||||
'line_ids.quantity',
|
||||
'line_ids.unit_price',
|
||||
'line_ids.tax_ids',
|
||||
'charge_amount',
|
||||
'tooling_charge',
|
||||
'tax_id',
|
||||
'partner_id',
|
||||
'currency_id',
|
||||
)
|
||||
def _compute_totals(self):
|
||||
"""Roll up subtotal / tax / grand total across lines + tooling.
|
||||
"""Roll up subtotal / tax / grand total across lines + charge.
|
||||
|
||||
Each line's taxes are computed via account.tax.compute_all so the
|
||||
Express form's totals card mirrors what the eventual SO will show
|
||||
once the operator hits Confirm. The tooling charge is added at the
|
||||
wizard level here AND pushed as an actual sale.order.line at
|
||||
action_create_order time (so it carries into the invoice).
|
||||
The order-level ``tax_id`` is applied once to (subtotal + charge),
|
||||
where charge = ``charge_amount`` (legacy ``tooling_charge`` as
|
||||
fallback). The charge is also pushed as an actual sale.order.line
|
||||
at action_create_order time (so it carries into the invoice).
|
||||
"""
|
||||
for rec in self:
|
||||
subtotal = 0.0
|
||||
subtotal = sum(
|
||||
(l.quantity or 0) * (l.unit_price or 0.0)
|
||||
for l in rec.line_ids
|
||||
)
|
||||
charge = rec.charge_amount or rec.tooling_charge or 0.0
|
||||
tax_total = 0.0
|
||||
for line in rec.line_ids:
|
||||
line_pre_tax = (line.quantity or 0) * (line.unit_price or 0.0)
|
||||
subtotal += line_pre_tax
|
||||
if line.tax_ids and line_pre_tax:
|
||||
taxes_res = line.tax_ids.compute_all(
|
||||
line.unit_price or 0.0,
|
||||
currency=rec.currency_id,
|
||||
quantity=line.quantity or 0,
|
||||
product=None,
|
||||
partner=rec.partner_id or None,
|
||||
)
|
||||
tax_total += (
|
||||
taxes_res['total_included']
|
||||
- taxes_res['total_excluded']
|
||||
)
|
||||
# Tooling charge: pick the tax set from the FIRST line that
|
||||
# has one (best proxy for the customer's standard rate). If
|
||||
# no line has taxes set yet, tooling is shown untaxed in the
|
||||
# preview; the eventual SO line will apply product defaults.
|
||||
tooling = rec.tooling_charge or 0.0
|
||||
if tooling:
|
||||
first_taxed_line = next(
|
||||
(l for l in rec.line_ids if l.tax_ids), False,
|
||||
if rec.tax_id and (subtotal + charge):
|
||||
res = rec.tax_id.compute_all(
|
||||
subtotal + charge,
|
||||
currency=rec.currency_id,
|
||||
quantity=1,
|
||||
product=None,
|
||||
partner=rec.partner_id or None,
|
||||
)
|
||||
if first_taxed_line:
|
||||
tooling_res = first_taxed_line.tax_ids.compute_all(
|
||||
tooling,
|
||||
currency=rec.currency_id,
|
||||
quantity=1,
|
||||
product=None,
|
||||
partner=rec.partner_id or None,
|
||||
)
|
||||
tax_total += (
|
||||
tooling_res['total_included']
|
||||
- tooling_res['total_excluded']
|
||||
)
|
||||
tax_total = res['total_included'] - res['total_excluded']
|
||||
rec.total_subtotal = subtotal
|
||||
rec.total_tax = tax_total
|
||||
rec.total_amount = subtotal + tax_total + tooling
|
||||
rec.total_amount = subtotal + charge + tax_total
|
||||
rec.total_qty = sum(rec.line_ids.mapped('quantity'))
|
||||
rec.total_line_count = len(rec.line_ids)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user