changeset 7ed95c461601 in modules/product:default
details: https://hg.tryton.org/modules/product?cmd=changeset;node=7ed95c461601
description:
Make product code unique
This allows to use the product code as SKU.
issue9004
review270831002
diffstat:
CHANGELOG | 1 +
doc/index.rst | 10 ++++++----
message.xml | 3 +++
product.py | 16 +++++++++++++---
4 files changed, 23 insertions(+), 7 deletions(-)
diffs (91 lines):
diff -r 88f15ac40dbe -r 7ed95c461601 CHANGELOG
--- a/CHANGELOG Thu Mar 19 00:28:43 2020 +0100
+++ b/CHANGELOG Thu Mar 19 00:33:37 2020 +0100
@@ -1,3 +1,4 @@
+* Make product code unique
* Add code to template as variant prefix code
* Hide product fields inherited from template when empty
* Skip default products when template is created from product
diff -r 88f15ac40dbe -r 7ed95c461601 doc/index.rst
--- a/doc/index.rst Thu Mar 19 00:28:43 2020 +0100
+++ b/doc/index.rst Thu Mar 19 00:33:37 2020 +0100
@@ -61,10 +61,10 @@
- Active, allow to disable a product.
-The Product model extend the Product Template with two fields: Code
-and Description. If a sequence is set on product configuration the code will
-be readonly and will be filled in using the sequence. It's also possible to
-define a list of identifiers on product. An identifier is composed by a type
+The Product model extends the Product Template with two fields: Code (aka SKU_)
+and Description. If a sequence is set on product configuration the code will be
+read-only and will be filled in using the sequence. It's also possible to
+define a list of identifiers on product. An identifier is composed by a type
and a code. The following types are available:
* International Article Number (EAN)
@@ -74,6 +74,8 @@
* International Securities Identification Number (ISIN)
* International Standard Music Number (ISMN)
+.. _SKU: https://en.wikipedia.org/wiki/Stock_keeping_unit
+
Configuration
*************
diff -r 88f15ac40dbe -r 7ed95c461601 message.xml
--- a/message.xml Thu Mar 19 00:28:43 2020 +0100
+++ b/message.xml Thu Mar 19 00:33:37 2020 +0100
@@ -24,5 +24,8 @@
<record model="ir.message" id="msg_invalid_code">
<field name="text">The %(type)s "%(code)s" for product
"%(product)s" is not valid.</field>
</record>
+ <record model="ir.message" id="msg_product_code_unique">
+ <field name="text">Code of active product must be unique.</field>
+ </record>
</data>
</tryton>
diff -r 88f15ac40dbe -r 7ed95c461601 product.py
--- a/product.py Thu Mar 19 00:28:43 2020 +0100
+++ b/product.py Thu Mar 19 00:33:37 2020 +0100
@@ -7,12 +7,13 @@
import stdnum
import stdnum.exceptions
-from sql import Null, Column
+from sql import Null, Column, Literal
+from sql.operators import Equal
from trytond.i18n import gettext
from trytond.model import (
ModelView, ModelSQL, Model, UnionMixin, DeactivableMixin, sequence_ordered,
- fields)
+ Exclude, fields)
from trytond.pyson import Eval
from trytond.transaction import Transaction
from trytond.pool import Pool
@@ -235,7 +236,8 @@
states={
'readonly': Eval('code_readonly', False),
},
- depends=['code_readonly'])
+ depends=['code_readonly'],
+ help="The unique identifier for the product (aka SKU).")
code = fields.Char("Code", readonly=True, select=True)
identifiers = fields.One2Many(
'product.identifier', 'product', "Identifiers",
@@ -261,6 +263,14 @@
super(Product, cls).__setup__()
+ t = cls.__table__()
+ cls._sql_constraints = [
+ ('code_exclude', Exclude(t, (t.code, Equal),
+ where=(t.active == Literal(True))
+ & (t.code != '')),
+ 'product.msg_product_code_unique'),
+ ]
+
for attr in dir(Template):
tfield = getattr(Template, attr)
if not isinstance(tfield, fields.Field):