changeset 26357bb18e09 in modules/party:default
details: https://hg.tryton.org/modules/party?cmd=changeset&node=26357bb18e09
description:
Move distance definition into party module
issue10104
review343621004
diffstat:
CHANGELOG | 1 +
contact_mechanism.py | 3 +-
party.py | 54 +++++++++++++++++++++++++++++++++++++++++++++++++++-
tests/test_party.py | 21 ++++++++++++++++++++
4 files changed, 77 insertions(+), 2 deletions(-)
diffs (137 lines):
diff -r 508fd56d0ae5 -r 26357bb18e09 CHANGELOG
--- a/CHANGELOG Sun Mar 21 16:09:13 2021 +0100
+++ b/CHANGELOG Wed Mar 24 21:37:48 2021 +0100
@@ -1,3 +1,4 @@
+* Add simple distance between parties
* Configure available identifiers
* Add ar, at, by, cn, cr, gr, id, il, kr, lt, no, ro and se identifiers
diff -r 508fd56d0ae5 -r 26357bb18e09 contact_mechanism.py
--- a/contact_mechanism.py Sun Mar 21 16:09:13 2021 +0100
+++ b/contact_mechanism.py Wed Mar 24 21:37:48 2021 +0100
@@ -86,7 +86,8 @@
@classmethod
def __setup__(cls):
super(ContactMechanism, cls).__setup__()
- cls._order.insert(0, ('party', 'ASC'))
+ cls._order.insert(0, ('party.distance', 'ASC NULLS LAST'))
+ cls._order.insert(1, ('party', 'ASC'))
@staticmethod
def default_type():
diff -r 508fd56d0ae5 -r 26357bb18e09 party.py
--- a/party.py Sun Mar 21 16:09:13 2021 +0100
+++ b/party.py Wed Mar 24 21:37:48 2021 +0100
@@ -3,6 +3,7 @@
from stdnum import get_cc_module
import stdnum.exceptions
from sql import Null, Column, Literal
+from sql.aggregate import Min
from sql.functions import CharLength, Substring, Position
from trytond.i18n import gettext
@@ -63,6 +64,7 @@
fax = fields.Function(fields.Char('Fax'), 'get_mechanism')
email = fields.Function(fields.Char('E-Mail'), 'get_mechanism')
website = fields.Function(fields.Char('Website'), 'get_mechanism')
+ distance = fields.Function(fields.Integer('Distance'), 'get_distance')
@classmethod
def __setup__(cls):
@@ -71,7 +73,8 @@
cls._sql_constraints = [
('code_uniq', Unique(t, t.code), 'party.msg_party_code_unique')
]
- cls._order.insert(0, ('name', 'ASC'))
+ cls._order.insert(0, ('distance', 'ASC NULLS LAST'))
+ cls._order.insert(1, ('name', 'ASC'))
cls.active.states.update({
'readonly': Bool(Eval('replaced_by')),
})
@@ -170,6 +173,55 @@
return ''
@classmethod
+ def _distance_query(cls, usages=None, party=None, depth=None):
+ context = Transaction().context
+ if party is None:
+ party = context.get('related_party')
+
+ if not party:
+ return
+
+ table = cls.__table__()
+ return table.select(
+ table.id.as_('to'),
+ Literal(0).as_('distance'),
+ where=(table.id == party))
+
+ @classmethod
+ def get_distance(cls, parties, name):
+ distances = {p.id: None for p in parties}
+ query = cls._distance_query()
+ if query:
+ cursor = Transaction().connection.cursor()
+ cursor.execute(*query.select(
+ query.to.as_('to'),
+ Min(query.distance).as_('distance'),
+ group_by=[query.to]))
+ distances.update(cursor)
+ return distances
+
+ @classmethod
+ def order_distance(cls, tables):
+ party, _ = tables[None]
+ key = 'distance'
+ if key not in tables:
+ query = cls._distance_query()
+ if not query:
+ return []
+ query = query.select(
+ query.to.as_('to'),
+ Min(query.distance).as_('distance'),
+ group_by=[query.to])
+ join = party.join(query, type_='LEFT',
+ condition=query.to == party.id)
+ tables[key] = {
+ None: (join.right, join.condition),
+ }
+ else:
+ query, _ = tables[key][None]
+ return [query.distance]
+
+ @classmethod
def _new_code(cls, **pattern):
pool = Pool()
Configuration = pool.get('party.configuration')
diff -r 508fd56d0ae5 -r 26357bb18e09 tests/test_party.py
--- a/tests/test_party.py Sun Mar 21 16:09:13 2021 +0100
+++ b/tests/test_party.py Wed Mar 24 21:37:48 2021 +0100
@@ -449,6 +449,27 @@
set(Party.tax_identifier_types())
- set(dict(IDENTIFIER_TYPES).keys()))
+ @with_transaction()
+ def test_party_distance(self):
+ "Test party distance"
+ pool = Pool()
+ Party = pool.get('party.party')
+
+ A, B, = Party.create([{
+ 'name': 'A',
+ }, {
+ 'name': 'B',
+ }])
+
+ parties = Party.search([])
+ self.assertEqual([p.distance for p in parties], [None] * 2)
+
+ with Transaction().set_context(related_party=A.id):
+ parties = Party.search([])
+ self.assertEqual(
+ [(p.name, p.distance) for p in parties],
+ [('A', 0), ('B', None)])
+
def suite():
suite = trytond.tests.test_tryton.suite()