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
99 changes: 99 additions & 0 deletions sale_order_finish_service/README.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
=========================
Sale Order Finish Service
=========================

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

.. |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-AGPL--3-blue.png
:target: http://www.gnu.org/licenses/agpl-3.0-standalone.html
:alt: License: AGPL-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_finish_service
: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_finish_service
: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|

Adds a new flag on sale order to mark that the service sale order has
been finished or delivered.

**Table of contents**

.. contents::
:local:

Use Cases / Context
===================

Odoo way of handling sale orders has only 4 states (draft, sent, sale,
cancel).

Also, on all services sale orders (linked to timesheets), it only checks
if the sale order is in state sale. In projects, it works fine, but it
can lead to errors on users, because they are not allowed to "close" an
existing sale order.

The concept of this module is to add a new flag that will detected
"finished sale orders" and will not allow to select them anymore.

Usage
=====

Access a sale order. When it is in state sale order, a Finish/Unfinish
button will appear in top.

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_finish_service%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
-------

* Dixmit

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

- `Dixmit <https://www.dixmit.com>`__

- Enric Tobella

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.

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

You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute.
1 change: 1 addition & 0 deletions sale_order_finish_service/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from . import models
15 changes: 15 additions & 0 deletions sale_order_finish_service/__manifest__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Copyright 2026 Dixmit
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

{
"name": "Sale Order Finish Service",
"summary": """Adds a finish service flag on sale orders""",
"version": "18.0.1.0.0",
"license": "AGPL-3",
"author": "Dixmit,Odoo Community Association (OCA)",
"website": "https://github.com/OCA/sale-workflow",
"depends": ["sale_service"],
"data": [
"views/sale_order.xml",
],
}
2 changes: 2 additions & 0 deletions sale_order_finish_service/models/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
from . import sale_order
from . import sale_order_line
22 changes: 22 additions & 0 deletions sale_order_finish_service/models/sale_order.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
# Copyright 2026 Dixmit
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from odoo import fields, models


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

finished_sale_order = fields.Boolean(copy=False)

def action_finish_sale_order(self):
for order in self.filtered(
lambda o: o.state == "sale" and not o.finished_sale_order
):
order.finished_sale_order = True

def action_unfinish_sale_order(self):
for order in self.filtered(
lambda o: o.state == "sale" and o.finished_sale_order
):
order.finished_sale_order = False
27 changes: 27 additions & 0 deletions sale_order_finish_service/models/sale_order_line.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# Copyright 2026 Dixmit
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).

from odoo import fields, models
from odoo.tools.sql import column_exists, create_column


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

finished_sale_order = fields.Boolean(
related="order_id.finished_sale_order", store=True, copy=False
)

def _domain_sale_line_service(self, **kwargs):
domain = super()._domain_sale_line_service(**kwargs)
if kwargs.get("check_finished_sale_order", True):
domain.append(("finished_sale_order", "=", False))
return domain

def _auto_init(self):
"""
Create column to avoid computation by the ORM
"""
if not column_exists(self.env.cr, "sale_order_line", "finished_sale_order"):
create_column(self.env.cr, "sale_order_line", "finished_sale_order", "bool")
return super()._auto_init()
3 changes: 3 additions & 0 deletions sale_order_finish_service/pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[build-system]
requires = ["whool"]
build-backend = "whool.buildapi"
6 changes: 6 additions & 0 deletions sale_order_finish_service/readme/CONTEXT.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
Odoo way of handling sale orders has only 4 states (draft, sent, sale, cancel).

Also, on all services sale orders (linked to timesheets), it only checks if the sale order is in state sale.
In projects, it works fine, but it can lead to errors on users, because they are not allowed to "close" an existing sale order.

The concept of this module is to add a new flag that will detected "finished sale orders" and will not allow to select them anymore.
2 changes: 2 additions & 0 deletions sale_order_finish_service/readme/CONTRIBUTORS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
- [Dixmit](https://www.dixmit.com)
- Enric Tobella
1 change: 1 addition & 0 deletions sale_order_finish_service/readme/DESCRIPTION.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Adds a new flag on sale order to mark that the service sale order has been finished or delivered.
2 changes: 2 additions & 0 deletions sale_order_finish_service/readme/USAGE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Access a sale order.
When it is in state sale order, a Finish/Unfinish button will appear in top.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Loading