Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
106 changes: 106 additions & 0 deletions sale_order_compute_commitment_date/README.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
==================================
Sale Order Compute Commitment Date
==================================

..
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! This file is generated by oca-gen-addon-readme !!
!! changes will be overwritten. !!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! source digest: sha256:f77cbe11285d1aff1796eee9fac951f13819b1741c0660524121c96d6fb1f610
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

.. |badge1| image:: https://img.shields.io/badge/maturity-Beta-yellow.png
:target: https://odoo-community.org/page/development-status
:alt: Beta
.. |badge2| image:: https://img.shields.io/badge/licence-LGPL--3-blue.png
:target: http://www.gnu.org/licenses/lgpl-3.0-standalone.html
:alt: License: LGPL-3
.. |badge3| image:: https://img.shields.io/badge/github-OCA%2Fsale--workflow-lightgray.png?logo=github
:target: https://github.com/OCA/sale-workflow/tree/18.0/sale_order_compute_commitment_date
:alt: OCA/sale-workflow
.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png
:target: https://translation.odoo-community.org/projects/sale-workflow-18-0/sale-workflow-18-0-sale_order_compute_commitment_date
:alt: Translate me on Weblate
.. |badge5| image:: https://img.shields.io/badge/runboat-Try%20me-875A7B.png
:target: https://runboat.odoo-community.org/builds?repo=OCA/sale-workflow&target_branch=18.0
:alt: Try me on Runboat

|badge1| |badge2| |badge3| |badge4| |badge5|

This module automatically computes sale orders commitment date based on
the product template sale_delay and product attribute variant lead time
fields.

**Table of contents**

.. contents::
:local:

Configuration
=============

To configure this module, you need to:

- Create a product.
- Set its delay time on the "Inventory" tab.
- If you want product variants to increase the commitment date, check
the Extend Lead Time boolean.
- Now configure a variant for the product and set its lead time.
- Create a sales order and add the product.
- On the "Other Information" tab you will see the commitment date its
automatically computed.
- This module relies on the resource calendar to calculate dates,
including both working days and any configured leave days.
- Once the sale order is confirmed, it computes again the commitment
date.

Bug Tracker
===========

Bugs are tracked on `GitHub Issues <https://github.com/OCA/sale-workflow/issues>`_.
In case of trouble, please check there if your issue has already been reported.
If you spotted it first, help us to smash it by providing a detailed and welcomed
`feedback <https://github.com/OCA/sale-workflow/issues/new?body=module:%20sale_order_compute_commitment_date%0Aversion:%2018.0%0A%0A**Steps%20to%20reproduce**%0A-%20...%0A%0A**Current%20behavior**%0A%0A**Expected%20behavior**>`_.

Do not contact contributors directly about support or help with technical issues.

Credits
=======

Authors
-------

* APSL - Nagarro

Contributors
------------

- ``APSL-Nagarro <https://apsl.tech>``\ \_:

- Miquel Pascual [email protected]

Maintainers
-----------

This module is maintained by the OCA.

.. image:: https://odoo-community.org/logo.png
:alt: Odoo Community Association
:target: https://odoo-community.org

OCA, or the Odoo Community Association, is a nonprofit organization whose
mission is to support the collaborative development of Odoo features and
promote its widespread use.

.. |maintainer-mpascuall| image:: https://github.com/mpascuall.png?size=40px
:target: https://github.com/mpascuall
:alt: mpascuall

Current `maintainer <https://odoo-community.org/page/maintainer-role>`__:

|maintainer-mpascuall|

This module is part of the `OCA/sale-workflow <https://github.com/OCA/sale-workflow/tree/18.0/sale_order_compute_commitment_date>`_ project on GitHub.

You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute.
4 changes: 4 additions & 0 deletions sale_order_compute_commitment_date/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from . import models
21 changes: 21 additions & 0 deletions sale_order_compute_commitment_date/__manifest__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

{
"name": "Sale Order Compute Commitment Date",
"version": "18.0.1.0.0",
"category": "Sales Management",
"summary": "Automatically computes the commitment date based on product"
"lead times and attributes",
"author": "APSL - Nagarro, Odoo Community Association (OCA)",
"maintainers": ["mpascuall"],
"website": "https://github.com/OCA/sale-workflow",
"license": "LGPL-3",
"depends": ["base", "sale_management", "stock"],
"data": [
"views/product_attribute_value.xml",
"views/product_template.xml",
],
"installable": True,
"application": False,
}
71 changes: 71 additions & 0 deletions sale_order_compute_commitment_date/l10n/es.po
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
# Translation of Odoo Server.
# This file contains the translation of the following modules:
# * sale_order_compute_commitment_date
#
msgid ""
msgstr ""
"Project-Id-Version: Odoo Server 18.0+e\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2025-06-26 07:21+0000\n"
"PO-Revision-Date: 2025-06-26 07:21+0000\n"
"Last-Translator: \n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: \n"
"Plural-Forms: \n"

#. module: sale_order_compute_commitment_date
#: model:ir.model,name:sale_order_compute_commitment_date.model_product_attribute_value
msgid "Attribute Value"
msgstr "Valor del Atributo"

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,field_description:sale_order_compute_commitment_date.field_sale_order__commitment_date
msgid "Delivery Date"
msgstr "Fecha de entrega"

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,field_description:sale_order_compute_commitment_date.field_product_product__extend_lead_time
#: model:ir.model.fields,field_description:sale_order_compute_commitment_date.field_product_template__extend_lead_time
msgid "Extend Lead Time"
msgstr "Tiempo de Entrega Extendido"

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,help:sale_order_compute_commitment_date.field_product_product__extend_lead_time
#: model:ir.model.fields,help:sale_order_compute_commitment_date.field_product_template__extend_lead_time
msgid ""
"If checked, the attribute lead time will be taken into account to calculate "
"the final lead time."
msgstr "Si está marcado, el tiempo de entrega del atributo se tendrá "
"en cuenta para calcular el tiempo de entrega final."

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,field_description:sale_order_compute_commitment_date.field_product_attribute_value__lead_time
msgid "Lead Time"
msgstr "Tiempo de Entrega"

#. module: sale_order_compute_commitment_date
#: model:ir.model,name:sale_order_compute_commitment_date.model_product_template
msgid "Product"
msgstr "Producto"

#. module: sale_order_compute_commitment_date
#: model:ir.model,name:sale_order_compute_commitment_date.model_sale_order
msgid "Sales Order"
msgstr "Pedido de venta"

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,help:sale_order_compute_commitment_date.field_product_attribute_value__lead_time
msgid "The number of days this attribute adds to the product's lead time."
msgstr "El número de días que este atributo añade al tiempo de entrega del producto."

#. module: sale_order_compute_commitment_date
#: model:ir.model.fields,help:sale_order_compute_commitment_date.field_sale_order__commitment_date
msgid ""
"This is the delivery date promised to the customer. If set, the delivery "
"order will be scheduled based on this date rather than product lead times."
msgstr ""
"Ésta es la fecha de entrega prometida al cliente. Si se establece, la orden "
"de entrega se programará en función de esta fecha en lugar de los plazos de "
"entrega del producto."
6 changes: 6 additions & 0 deletions sale_order_compute_commitment_date/models/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from . import product_template
from . import product_attribute_value
from . import sale_order
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from odoo import fields, models


class ProductAttributeValue(models.Model):
_inherit = "product.attribute.value"

lead_time = fields.Integer(
help="The number of days this attribute adds to the product's lead time.",
)
13 changes: 13 additions & 0 deletions sale_order_compute_commitment_date/models/product_template.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from odoo import fields, models


class ProductTemplate(models.Model):
_inherit = "product.template"

extend_lead_time = fields.Boolean(
Copy link
Contributor

Choose a reason for hiding this comment

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

IMHO, this field name should reflect the attribute term as the name is too generic.

Something like attribute_extend_lead_time.

help="If checked, the attribute lead time will be "
"taken into account to calculate the final lead time.",
)
91 changes: 91 additions & 0 deletions sale_order_compute_commitment_date/models/sale_order.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
# Copyright 2025 APSL Nagarro
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from datetime import timedelta

from pytz import timezone, utc

from odoo import api, fields, models


class SaleOrder(models.Model):
_inherit = "sale.order"

commitment_date = fields.Datetime(
"Delivery Date",
compute="_compute_commitment_date",
store=True,
readonly=False,
help="This is the delivery date promised to the customer. "
"If set, the delivery order will be "
"scheduled based on this date rather than product lead times.",
)

@api.depends(
"order_line.product_id",
Copy link
Contributor

Choose a reason for hiding this comment

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

IMHO, only order_line.product_id should be taken into account here.

You should manage the fact changing the delay, the product variant lead time or the extend configuration will trigger a compute on every existing sale order line that uses that product. And that is unwanted behavior

"order_line.product_id.sale_delay",
"order_line.product_id.product_tmpl_id.extend_lead_time",
"order_line.product_id.product_template_attribute_value_ids.product_attribute_value_id.lead_time",
"date_order",
"state",
"company_id.resource_calendar_id.attendance_ids.dayofweek",
"company_id.resource_calendar_id.leave_ids",
)
def _compute_commitment_date(self):
for order in self:
max_total_lead_time = 0

for line in order.order_line:
product_template = line.product_id.product_tmpl_id

current_line_lead_time = (
product_template.sale_delay
if product_template.sale_delay is not None
else 0
)

if product_template.extend_lead_time:
for ptav in line.product_id.product_template_attribute_value_ids:
if ptav.product_attribute_value_id.lead_time:
current_line_lead_time += (
ptav.product_attribute_value_id.lead_time
)

if current_line_lead_time > max_total_lead_time:
max_total_lead_time = current_line_lead_time

base_date_for_calculation = order.date_order

if base_date_for_calculation:
order.commitment_date = order._get_date_with_lead_time_from_calendar(
base_date_for_calculation, max_total_lead_time
)
else:
order.commitment_date = False

def _get_date_with_lead_time_from_calendar(self, base_datetime, lead_time_days):
self.ensure_one()

calendar = self.company_id.resource_calendar_id

if not calendar:
return base_datetime + timedelta(days=lead_time_days)

hours_per_day = calendar.hours_per_day if calendar.hours_per_day else 8.0
hours_to_add = lead_time_days * hours_per_day

calendar_tz = timezone(calendar.tz) if calendar.tz else timezone("UTC")

if not base_datetime.tzinfo:
base_datetime_aware = utc.localize(base_datetime)
else:
base_datetime_aware = base_datetime

base_dt_in_calendar_tz = base_datetime_aware.astimezone(calendar_tz)
naive_base_dt = base_dt_in_calendar_tz.replace(tzinfo=None)

final_datetime_aware = calendar.plan_hours(
hours_to_add, naive_base_dt, compute_leaves=True
)

return final_datetime_aware.astimezone(timezone("UTC")).replace(tzinfo=None)
3 changes: 3 additions & 0 deletions sale_order_compute_commitment_date/pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[build-system]
requires = ["whool"]
build-backend = "whool.buildapi"
10 changes: 10 additions & 0 deletions sale_order_compute_commitment_date/readme/CONFIGURE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
To configure this module, you need to:

- Create a product.
- Set its delay time on the "Inventory" tab.
- If you want product variants to increase the commitment date, check the Extend Lead Time boolean.
- Now configure a variant for the product and set its lead time.
- Create a sales order and add the product.
- On the "Other Information" tab you will see the commitment date its automatically computed.
- This module relies on the resource calendar to calculate dates, including both working days and any configured leave days.
- Once the sale order is confirmed, it computes again the commitment date.
2 changes: 2 additions & 0 deletions sale_order_compute_commitment_date/readme/CONTRIBUTORS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
* `APSL-Nagarro <https://apsl.tech>`_:
* Miquel Pascual <[email protected]>
2 changes: 2 additions & 0 deletions sale_order_compute_commitment_date/readme/DESCRIPTION.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
This module automatically computes sale orders commitment date based on the product template sale_delay
and product attribute variant lead time fields.
Loading
Loading