server/test/unittest_msplanner.py
changeset 7543 570522300e22
parent 7306 a21bafe9fe35
child 7651 7c0af7ef3325
equal deleted inserted replaced
7542:86e9632a4e9c 7543:570522300e22
   294                    {self.cards: {'X': s[2], 'S': s[0, 1, 2]},
   294                    {self.cards: {'X': s[2], 'S': s[0, 1, 2]},
   295                     self.system: {'X': s[0, 1, 2], 'S': s[0, 1, 2]}},
   295                     self.system: {'X': s[0, 1, 2], 'S': s[0, 1, 2]}},
   296                    True)
   296                    True)
   297 
   297 
   298     def test_not_relation_no_split_external(self):
   298     def test_not_relation_no_split_external(self):
   299         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
   299         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
   300         # similar to the above test but with an eid coming from the external source.
   300         # similar to the above test but with an eid coming from the external source.
   301         # the same plan may be used, since we won't find any record in the system source
   301         # the same plan may be used, since we won't find any record in the system source
   302         # linking 9999999 to a state
   302         # linking 9999999 to a state
   303         self._test('Any SN WHERE NOT X in_state S, X eid %(x)s, S name SN',
   303         self._test('Any SN WHERE NOT X in_state S, X eid %(x)s, S name SN',
   304                    {'x': 999999},
   304                    {'x': 999999},
   311                    {self.system: {'X': s[0, 1, 2], 'S': s[0, 1, 2], 'T': s[0, 1, 2], 'tags': s[0, 1, 2]},
   311                    {self.system: {'X': s[0, 1, 2], 'S': s[0, 1, 2], 'T': s[0, 1, 2], 'tags': s[0, 1, 2]},
   312                     self.cards: {'X': s[2], 'S': s[2]}},
   312                     self.cards: {'X': s[2], 'S': s[2]}},
   313                    True)
   313                    True)
   314 
   314 
   315     def test_simplified_var(self):
   315     def test_simplified_var(self):
   316         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
   316         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
   317         self._test('Any U WHERE U in_group G, (G name IN ("managers", "logilab") OR (X require_permission P?, P name "bla", P require_group G)), X eid %(x)s, U eid %(u)s',
   317         self._test('Any U WHERE U in_group G, (G name IN ("managers", "logilab") OR (X require_permission P?, P name "bla", P require_group G)), X eid %(x)s, U eid %(u)s',
   318                    {'x': 999999, 'u': self.session.user.eid},
   318                    {'x': 999999, 'u': self.session.user.eid},
   319                    {self.system: {'P': s[0], 'G': s[0], 'X': s[0],
   319                    {self.system: {'P': s[0], 'G': s[0], 'X': s[0],
   320                                   'require_permission': s[0], 'in_group': s[0], 'P': s[0], 'require_group': s[0],
   320                                   'require_permission': s[0], 'in_group': s[0], 'P': s[0], 'require_group': s[0],
   321                                   'u': s[0]}},
   321                                   'u': s[0]}},
   327                    {'x': ueid, 'y': ueid},
   327                    {'x': ueid, 'y': ueid},
   328                    {self.system: {'Y': s[0], 'created_by': s[0], 'x': s[0]}},
   328                    {self.system: {'Y': s[0], 'created_by': s[0], 'x': s[0]}},
   329                    False)
   329                    False)
   330 
   330 
   331     def test_crossed_relation_eid_1_needattr(self):
   331     def test_crossed_relation_eid_1_needattr(self):
   332         repo._type_source_cache[999999] = ('Note', 'system', 999999)
   332         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
   333         ueid = self.session.user.eid
   333         ueid = self.session.user.eid
   334         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
   334         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
   335                    {'x': 999999,},
   335                    {'x': 999999,},
   336                    {self.cards: {'Y': s[0]}, self.system: {'Y': s[0], 'x': s[0]}},
   336                    {self.cards: {'Y': s[0]}, self.system: {'Y': s[0], 'x': s[0]}},
   337                    True)
   337                    True)
   338 
   338 
   339     def test_crossed_relation_eid_1_invariant(self):
   339     def test_crossed_relation_eid_1_invariant(self):
   340         repo._type_source_cache[999999] = ('Note', 'system', 999999)
   340         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
   341         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
   341         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
   342                    {'x': 999999},
   342                    {'x': 999999},
   343                    {self.system: {'Y': s[0], 'x': s[0]}},
   343                    {self.system: {'Y': s[0], 'x': s[0]}},
   344                    False)
   344                    False)
   345 
   345 
   346     def test_crossed_relation_eid_2_invariant(self):
   346     def test_crossed_relation_eid_2_invariant(self):
   347         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
   347         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
   348         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
   348         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
   349                    {'x': 999999,},
   349                    {'x': 999999,},
   350                    {self.cards: {'Y': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]},
   350                    {self.cards: {'Y': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]},
   351                     self.system: {'Y': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]}},
   351                     self.system: {'Y': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]}},
   352                    False)
   352                    False)
   353 
   353 
   354     def test_version_crossed_depends_on_1(self):
   354     def test_version_crossed_depends_on_1(self):
   355         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
   355         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
   356         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
   356         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
   357                    {'x': 999999},
   357                    {'x': 999999},
   358                    {self.cards: {'X': s[0], 'AD': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]},
   358                    {self.cards: {'X': s[0], 'AD': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]},
   359                     self.system: {'X': s[0], 'AD': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]}},
   359                     self.system: {'X': s[0], 'AD': s[0], 'multisource_crossed_rel': s[0], 'x': s[0]}},
   360                    True)
   360                    True)
   361 
   361 
   362     def test_version_crossed_depends_on_2(self):
   362     def test_version_crossed_depends_on_2(self):
   363         repo._type_source_cache[999999] = ('Note', 'system', 999999)
   363         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
   364         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
   364         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
   365                    {'x': 999999},
   365                    {'x': 999999},
   366                    {self.cards: {'X': s[0], 'AD': s[0]},
   366                    {self.cards: {'X': s[0], 'AD': s[0]},
   367                     self.system: {'X': s[0], 'AD': s[0], 'x': s[0]}},
   367                     self.system: {'X': s[0], 'AD': s[0], 'x': s[0]}},
   368                     True)
   368                     True)
   369 
   369 
   370     def test_simplified_var_3(self):
   370     def test_simplified_var_3(self):
   371         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
   371         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
   372         repo._type_source_cache[999998] = ('State', 'cards', 999998)
   372         repo._type_source_cache[999998] = ('State', 'cards', 999998, 'cards')
   373         self._test('Any S,T WHERE S eid %(s)s, N eid %(n)s, N type T, N is Note, S is State',
   373         self._test('Any S,T WHERE S eid %(s)s, N eid %(n)s, N type T, N is Note, S is State',
   374                    {'n': 999999, 's': 999998},
   374                    {'n': 999999, 's': 999998},
   375                    {self.cards: {'s': s[0], 'N': s[0]}}, False)
   375                    {self.cards: {'s': s[0], 'N': s[0]}}, False)
   376 
   376 
   377 
   377 
  1264                                        [{'S': 'State', 'SN': 'String'}])],
  1264                                        [{'S': 'State', 'SN': 'String'}])],
  1265                      None, None, [self.cards, self.system], {}, [])],
  1265                      None, None, [self.cards, self.system], {}, [])],
  1266                    {'x': ueid})
  1266                    {'x': ueid})
  1267 
  1267 
  1268     def test_not_relation_no_split_external(self):
  1268     def test_not_relation_no_split_external(self):
  1269         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1269         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1270         # similar to the above test but with an eid coming from the external source.
  1270         # similar to the above test but with an eid coming from the external source.
  1271         # the same plan may be used, since we won't find any record in the system source
  1271         # the same plan may be used, since we won't find any record in the system source
  1272         # linking 9999999 to a state
  1272         # linking 9999999 to a state
  1273         self._test('Any SN WHERE NOT X in_state S, X eid %(x)s, S name SN',
  1273         self._test('Any SN WHERE NOT X in_state S, X eid %(x)s, S name SN',
  1274                    [('OneFetchStep', [('Any SN WHERE NOT EXISTS(999999 in_state S), S name SN, S is State',
  1274                    [('OneFetchStep', [('Any SN WHERE NOT EXISTS(999999 in_state S), S name SN, S is State',
  1295                        None, None, [self.system], {'S': 'table0.C1', 'S.name': 'table0.C0', 'SN': 'table0.C0'},
  1295                        None, None, [self.system], {'S': 'table0.C1', 'S.name': 'table0.C0', 'SN': 'table0.C0'},
  1296                        []),]
  1296                        []),]
  1297                      )])
  1297                      )])
  1298 
  1298 
  1299     def test_external_attributes_and_relation(self):
  1299     def test_external_attributes_and_relation(self):
  1300         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1300         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1301         self._test('Any A,B,C,D WHERE A eid %(x)s,A creation_date B,A modification_date C, A todo_by D?',
  1301         self._test('Any A,B,C,D WHERE A eid %(x)s,A creation_date B,A modification_date C, A todo_by D?',
  1302                    [('FetchStep', [('Any A,B,C WHERE A eid 999999, A creation_date B, A modification_date C, A is Note',
  1302                    [('FetchStep', [('Any A,B,C WHERE A eid 999999, A creation_date B, A modification_date C, A is Note',
  1303                                     [{'A': 'Note', 'C': 'Datetime', 'B': 'Datetime'}])],
  1303                                     [{'A': 'Note', 'C': 'Datetime', 'B': 'Datetime'}])],
  1304                      [self.cards], None,
  1304                      [self.cards], None,
  1305                      {'A': 'table0.C0', 'A.creation_date': 'table0.C1', 'A.modification_date': 'table0.C2', 'C': 'table0.C2', 'B': 'table0.C1'}, []),
  1305                      {'A': 'table0.C0', 'A.creation_date': 'table0.C1', 'A.modification_date': 'table0.C2', 'C': 'table0.C2', 'B': 'table0.C1'}, []),
  1312                    {'x': 999999})
  1312                    {'x': 999999})
  1313 
  1313 
  1314 
  1314 
  1315     def test_simplified_var(self):
  1315     def test_simplified_var(self):
  1316         ueid = self.session.user.eid
  1316         ueid = self.session.user.eid
  1317         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1317         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1318         self._test('Any U WHERE U in_group G, (G name IN ("managers", "logilab") OR (X require_permission P?, P name "bla", P require_group G)), X eid %(x)s, U eid %(u)s',
  1318         self._test('Any U WHERE U in_group G, (G name IN ("managers", "logilab") OR (X require_permission P?, P name "bla", P require_group G)), X eid %(x)s, U eid %(u)s',
  1319                    [('OneFetchStep', [('Any %s WHERE %s in_group G, (G name IN("managers", "logilab")) OR (X require_permission P?, P name "bla", P require_group G), X eid 999999' % (ueid, ueid),
  1319                    [('OneFetchStep', [('Any %s WHERE %s in_group G, (G name IN("managers", "logilab")) OR (X require_permission P?, P name "bla", P require_group G), X eid 999999' % (ueid, ueid),
  1320                                        [{'X': 'Note', 'G': 'CWGroup', 'P': 'CWPermission'}])],
  1320                                        [{'X': 'Note', 'G': 'CWGroup', 'P': 'CWPermission'}])],
  1321                      None, None, [self.system], {}, [])],
  1321                      None, None, [self.system], {}, [])],
  1322                    {'x': 999999, 'u': ueid})
  1322                    {'x': 999999, 'u': ueid})
  1527                       'N': 'table0.C1'},
  1527                       'N': 'table0.C1'},
  1528                      [])],
  1528                      [])],
  1529                    {'E': ueid})
  1529                    {'E': ueid})
  1530 
  1530 
  1531     def test_eid_dont_cross_relation_1(self):
  1531     def test_eid_dont_cross_relation_1(self):
  1532         repo._type_source_cache[999999] = ('Personne', 'system', 999999)
  1532         repo._type_source_cache[999999] = ('Personne', 'system', 999999, 'system')
  1533         self._test('Any Y,YT WHERE X eid %(x)s, X fiche Y, Y title YT',
  1533         self._test('Any Y,YT WHERE X eid %(x)s, X fiche Y, Y title YT',
  1534                    [('OneFetchStep', [('Any Y,YT WHERE X eid 999999, X fiche Y, Y title YT',
  1534                    [('OneFetchStep', [('Any Y,YT WHERE X eid 999999, X fiche Y, Y title YT',
  1535                                        [{'X': 'Personne', 'Y': 'Card', 'YT': 'String'}])],
  1535                                        [{'X': 'Personne', 'Y': 'Card', 'YT': 'String'}])],
  1536                      None, None, [self.system], {}, [])],
  1536                      None, None, [self.system], {}, [])],
  1537                    {'x': 999999})
  1537                    {'x': 999999})
  1538 
  1538 
  1539     def test_eid_dont_cross_relation_2(self):
  1539     def test_eid_dont_cross_relation_2(self):
  1540         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1540         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1541         self.cards.dont_cross_relations.add('concerne')
  1541         self.cards.dont_cross_relations.add('concerne')
  1542         try:
  1542         try:
  1543             self._test('Any Y,S,YT,X WHERE Y concerne X, Y in_state S, X eid 999999, Y ref YT',
  1543             self._test('Any Y,S,YT,X WHERE Y concerne X, Y in_state S, X eid 999999, Y ref YT',
  1544                    [('OneFetchStep', [('Any Y,S,YT,999999 WHERE Y concerne 999999, Y in_state S, Y ref YT',
  1544                    [('OneFetchStep', [('Any Y,S,YT,999999 WHERE Y concerne 999999, Y in_state S, Y ref YT',
  1545                                        [{'Y': 'Affaire', 'YT': 'String', 'S': 'State'}])],
  1545                                        [{'Y': 'Affaire', 'YT': 'String', 'S': 'State'}])],
  1550 
  1550 
  1551 
  1551 
  1552     # external source w/ .cross_relations == ['multisource_crossed_rel'] ######
  1552     # external source w/ .cross_relations == ['multisource_crossed_rel'] ######
  1553 
  1553 
  1554     def test_crossed_relation_eid_1_invariant(self):
  1554     def test_crossed_relation_eid_1_invariant(self):
  1555         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1555         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1556         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
  1556         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
  1557                    [('OneFetchStep', [('Any Y WHERE 999999 multisource_crossed_rel Y', [{u'Y': 'Note'}])],
  1557                    [('OneFetchStep', [('Any Y WHERE 999999 multisource_crossed_rel Y', [{u'Y': 'Note'}])],
  1558                       None, None, [self.system], {}, [])
  1558                       None, None, [self.system], {}, [])
  1559                     ],
  1559                     ],
  1560                    {'x': 999999,})
  1560                    {'x': 999999,})
  1561 
  1561 
  1562     def test_crossed_relation_eid_1_needattr(self):
  1562     def test_crossed_relation_eid_1_needattr(self):
  1563         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1563         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1564         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
  1564         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
  1565                    [('FetchStep', [('Any Y,T WHERE Y type T, Y is Note', [{'T': 'String', 'Y': 'Note'}])],
  1565                    [('FetchStep', [('Any Y,T WHERE Y type T, Y is Note', [{'T': 'String', 'Y': 'Note'}])],
  1566                      [self.cards, self.system], None,
  1566                      [self.cards, self.system], None,
  1567                      {'T': 'table0.C1', 'Y': 'table0.C0', 'Y.type': 'table0.C1'}, []),
  1567                      {'T': 'table0.C1', 'Y': 'table0.C0', 'Y.type': 'table0.C1'}, []),
  1568                     ('OneFetchStep', [('Any Y,T WHERE 999999 multisource_crossed_rel Y, Y type T, Y is Note',
  1568                     ('OneFetchStep', [('Any Y,T WHERE 999999 multisource_crossed_rel Y, Y type T, Y is Note',
  1571                      {'T': 'table0.C1', 'Y': 'table0.C0', 'Y.type': 'table0.C1'}, []),
  1571                      {'T': 'table0.C1', 'Y': 'table0.C0', 'Y.type': 'table0.C1'}, []),
  1572                     ],
  1572                     ],
  1573                    {'x': 999999,})
  1573                    {'x': 999999,})
  1574 
  1574 
  1575     def test_crossed_relation_eid_2_invariant(self):
  1575     def test_crossed_relation_eid_2_invariant(self):
  1576         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1576         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1577         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
  1577         self._test('Any Y WHERE X eid %(x)s, X multisource_crossed_rel Y',
  1578                    [('OneFetchStep', [('Any Y WHERE 999999 multisource_crossed_rel Y, Y is Note', [{'Y': 'Note'}])],
  1578                    [('OneFetchStep', [('Any Y WHERE 999999 multisource_crossed_rel Y, Y is Note', [{'Y': 'Note'}])],
  1579                       None, None, [self.cards, self.system], {}, [])
  1579                       None, None, [self.cards, self.system], {}, [])
  1580                     ],
  1580                     ],
  1581                    {'x': 999999,})
  1581                    {'x': 999999,})
  1582 
  1582 
  1583     def test_crossed_relation_eid_2_needattr(self):
  1583     def test_crossed_relation_eid_2_needattr(self):
  1584         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1584         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1585         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
  1585         self._test('Any Y,T WHERE X eid %(x)s, X multisource_crossed_rel Y, Y type T',
  1586                    [('OneFetchStep', [('Any Y,T WHERE 999999 multisource_crossed_rel Y, Y type T, Y is Note',
  1586                    [('OneFetchStep', [('Any Y,T WHERE 999999 multisource_crossed_rel Y, Y type T, Y is Note',
  1587                                        [{'T': 'String', 'Y': 'Note'}])],
  1587                                        [{'T': 'String', 'Y': 'Note'}])],
  1588                      None, None, [self.cards, self.system], {},
  1588                      None, None, [self.cards, self.system], {},
  1589                      []),
  1589                      []),
  1590                     ],
  1590                     ],
  1591                    {'x': 999999,})
  1591                    {'x': 999999,})
  1592 
  1592 
  1593     def test_crossed_relation_eid_not_1(self):
  1593     def test_crossed_relation_eid_not_1(self):
  1594         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1594         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1595         self._test('Any Y WHERE X eid %(x)s, NOT X multisource_crossed_rel Y',
  1595         self._test('Any Y WHERE X eid %(x)s, NOT X multisource_crossed_rel Y',
  1596                    [('FetchStep', [('Any Y WHERE Y is Note', [{'Y': 'Note'}])],
  1596                    [('FetchStep', [('Any Y WHERE Y is Note', [{'Y': 'Note'}])],
  1597                      [self.cards, self.system], None, {'Y': 'table0.C0'}, []),
  1597                      [self.cards, self.system], None, {'Y': 'table0.C0'}, []),
  1598                     ('OneFetchStep', [('Any Y WHERE NOT EXISTS(999999 multisource_crossed_rel Y), Y is Note',
  1598                     ('OneFetchStep', [('Any Y WHERE NOT EXISTS(999999 multisource_crossed_rel Y), Y is Note',
  1599                                        [{'Y': 'Note'}])],
  1599                                        [{'Y': 'Note'}])],
  1606 #         self._test('Any Y WHERE X eid %(x)s, NOT X multisource_crossed_rel Y',
  1606 #         self._test('Any Y WHERE X eid %(x)s, NOT X multisource_crossed_rel Y',
  1607 #                    [],
  1607 #                    [],
  1608 #                    {'x': 999999,})
  1608 #                    {'x': 999999,})
  1609 
  1609 
  1610     def test_crossed_relation_base_XXXFIXME(self):
  1610     def test_crossed_relation_base_XXXFIXME(self):
  1611         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1611         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1612         self._test('Any X,Y,T WHERE X multisource_crossed_rel Y, Y type T, X type T',
  1612         self._test('Any X,Y,T WHERE X multisource_crossed_rel Y, Y type T, X type T',
  1613                    [('FetchStep', [('Any X,T WHERE X type T, X is Note', [{'T': 'String', 'X': 'Note'}])],
  1613                    [('FetchStep', [('Any X,T WHERE X type T, X is Note', [{'T': 'String', 'X': 'Note'}])],
  1614                      [self.cards, self.system], None,
  1614                      [self.cards, self.system], None,
  1615                      {'T': 'table0.C1', 'X': 'table0.C0', 'X.type': 'table0.C1'}, []),
  1615                      {'T': 'table0.C1', 'X': 'table0.C0', 'X.type': 'table0.C1'}, []),
  1616                     ('FetchStep',  [('Any Y,T WHERE Y type T, Y is Note', [{'T': 'String', 'Y': 'Note'}])],
  1616                     ('FetchStep',  [('Any Y,T WHERE Y type T, Y is Note', [{'T': 'String', 'Y': 'Note'}])],
  1695             self.repo.set_schema(self.schema)
  1695             self.repo.set_schema(self.schema)
  1696 
  1696 
  1697     # edition queries tests ###################################################
  1697     # edition queries tests ###################################################
  1698 
  1698 
  1699     def test_insert_simplified_var_1(self):
  1699     def test_insert_simplified_var_1(self):
  1700         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1700         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1701         repo._type_source_cache[999998] = ('State', 'system', None)
  1701         repo._type_source_cache[999998] = ('State', 'system', None, 'system')
  1702         self._test('INSERT Note X: X in_state S, X type T WHERE S eid %(s)s, N eid %(n)s, N type T',
  1702         self._test('INSERT Note X: X in_state S, X type T WHERE S eid %(s)s, N eid %(n)s, N type T',
  1703                    [('InsertStep',
  1703                    [('InsertStep',
  1704                      [('InsertRelationsStep',
  1704                      [('InsertRelationsStep',
  1705                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1705                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1706                                            [{'N': 'Note', 'T': 'String'}])],
  1706                                            [{'N': 'Note', 'T': 'String'}])],
  1708                       ])
  1708                       ])
  1709                     ],
  1709                     ],
  1710                    {'n': 999999, 's': 999998})
  1710                    {'n': 999999, 's': 999998})
  1711 
  1711 
  1712     def test_insert_simplified_var_2(self):
  1712     def test_insert_simplified_var_2(self):
  1713         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1713         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1714         repo._type_source_cache[999998] = ('State', 'system', None)
  1714         repo._type_source_cache[999998] = ('State', 'system', None, 'system')
  1715         self._test('INSERT Note X: X in_state S, X type T, X migrated_from N WHERE S eid %(s)s, N eid %(n)s, N type T',
  1715         self._test('INSERT Note X: X in_state S, X type T, X migrated_from N WHERE S eid %(s)s, N eid %(n)s, N type T',
  1716                    [('InsertStep',
  1716                    [('InsertStep',
  1717                      [('InsertRelationsStep',
  1717                      [('InsertRelationsStep',
  1718                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1718                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1719                                            [{'N': 'Note', 'T': 'String'}])],
  1719                                            [{'N': 'Note', 'T': 'String'}])],
  1722                       ])
  1722                       ])
  1723                     ],
  1723                     ],
  1724                    {'n': 999999, 's': 999998})
  1724                    {'n': 999999, 's': 999998})
  1725 
  1725 
  1726     def test_insert_simplified_var_3(self):
  1726     def test_insert_simplified_var_3(self):
  1727         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1727         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1728         repo._type_source_cache[999998] = ('State', 'cards', 999998)
  1728         repo._type_source_cache[999998] = ('State', 'cards', 999998, 'cards')
  1729         self._test('INSERT Note X: X in_state S, X type T WHERE S eid %(s)s, N eid %(n)s, N type T',
  1729         self._test('INSERT Note X: X in_state S, X type T WHERE S eid %(s)s, N eid %(n)s, N type T',
  1730                    [('InsertStep',
  1730                    [('InsertStep',
  1731                      [('InsertRelationsStep',
  1731                      [('InsertRelationsStep',
  1732                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1732                        [('OneFetchStep', [('Any T WHERE N eid 999999, N type T, N is Note',
  1733                                            [{'N': 'Note', 'T': 'String'}])],
  1733                                            [{'N': 'Note', 'T': 'String'}])],
  1735                        )]
  1735                        )]
  1736                      )],
  1736                      )],
  1737                    {'n': 999999, 's': 999998})
  1737                    {'n': 999999, 's': 999998})
  1738 
  1738 
  1739     def test_insert_simplified_var_4(self):
  1739     def test_insert_simplified_var_4(self):
  1740         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1740         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1741         repo._type_source_cache[999998] = ('State', 'system', None)
  1741         repo._type_source_cache[999998] = ('State', 'system', None, 'system')
  1742         self._test('INSERT Note X: X in_state S, X type "bla", X migrated_from N WHERE S eid %(s)s, N eid %(n)s',
  1742         self._test('INSERT Note X: X in_state S, X type "bla", X migrated_from N WHERE S eid %(s)s, N eid %(n)s',
  1743                    [('InsertStep',
  1743                    [('InsertStep',
  1744                       [('InsertRelationsStep', [])]
  1744                       [('InsertRelationsStep', [])]
  1745                      )],
  1745                      )],
  1746                    {'n': 999999, 's': 999998})
  1746                    {'n': 999999, 's': 999998})
  1747 
  1747 
  1748     def test_insert_simplified_var_5(self):
  1748     def test_insert_simplified_var_5(self):
  1749         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1749         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1750         repo._type_source_cache[999998] = ('State', 'system', None)
  1750         repo._type_source_cache[999998] = ('State', 'system', None, 'system')
  1751         self._test('INSERT Note X: X in_state S, X type "bla", X migrated_from N WHERE S eid %(s)s, N eid %(n)s, A concerne N',
  1751         self._test('INSERT Note X: X in_state S, X type "bla", X migrated_from N WHERE S eid %(s)s, N eid %(n)s, A concerne N',
  1752                    [('InsertStep',
  1752                    [('InsertStep',
  1753                      [('InsertRelationsStep',
  1753                      [('InsertRelationsStep',
  1754                        [('OneFetchStep',
  1754                        [('OneFetchStep',
  1755                          [('Any A WHERE A concerne 999999, A is Affaire',
  1755                          [('Any A WHERE A concerne 999999, A is Affaire',
  1782                         ]),
  1782                         ]),
  1783                     ],
  1783                     ],
  1784                    {'x': ueid, 'y': ueid})
  1784                    {'x': ueid, 'y': ueid})
  1785 
  1785 
  1786     def test_delete_relation3(self):
  1786     def test_delete_relation3(self):
  1787         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1787         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1788         self._test('DELETE Y multisource_inlined_rel X WHERE X eid %(x)s, NOT (Y cw_source S, S name %(source)s)',
  1788         self._test('DELETE Y multisource_inlined_rel X WHERE X eid %(x)s, NOT (Y cw_source S, S name %(source)s)',
  1789                    [('DeleteRelationsStep',
  1789                    [('DeleteRelationsStep',
  1790                      [('OneFetchStep',
  1790                      [('OneFetchStep',
  1791                        [('Any Y,999999 WHERE Y multisource_inlined_rel 999999, NOT EXISTS(Y cw_source S, S name "cards"), S is CWSource, Y is IN(Card, Note)',
  1791                        [('Any Y,999999 WHERE Y multisource_inlined_rel 999999, NOT EXISTS(Y cw_source S, S name "cards"), S is CWSource, Y is IN(Card, Note)',
  1792                          [{'S': 'CWSource', 'Y': 'Card'}, {'S': 'CWSource', 'Y': 'Note'}])],
  1792                          [{'S': 'CWSource', 'Y': 'Card'}, {'S': 'CWSource', 'Y': 'Note'}])],
  1794                        [])]
  1794                        [])]
  1795                      )],
  1795                      )],
  1796                    {'x': 999999, 'source': 'cards'})
  1796                    {'x': 999999, 'source': 'cards'})
  1797 
  1797 
  1798     def test_delete_entity1(self):
  1798     def test_delete_entity1(self):
  1799         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1799         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1800         self._test('DELETE Note X WHERE X eid %(x)s, NOT Y multisource_rel X',
  1800         self._test('DELETE Note X WHERE X eid %(x)s, NOT Y multisource_rel X',
  1801                    [('DeleteEntitiesStep',
  1801                    [('DeleteEntitiesStep',
  1802                      [('OneFetchStep', [('Any 999999 WHERE NOT EXISTS(Y multisource_rel 999999), Y is IN(Card, Note)',
  1802                      [('OneFetchStep', [('Any 999999 WHERE NOT EXISTS(Y multisource_rel 999999), Y is IN(Card, Note)',
  1803                                          [{'Y': 'Card'}, {'Y': 'Note'}])],
  1803                                          [{'Y': 'Card'}, {'Y': 'Note'}])],
  1804                        None, None, [self.system], {}, [])
  1804                        None, None, [self.system], {}, [])
  1805                       ])
  1805                       ])
  1806                     ],
  1806                     ],
  1807                    {'x': 999999})
  1807                    {'x': 999999})
  1808 
  1808 
  1809     def test_delete_entity2(self):
  1809     def test_delete_entity2(self):
  1810         repo._type_source_cache[999999] = ('Note', 'system', 999999)
  1810         repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  1811         self._test('DELETE Note X WHERE X eid %(x)s, NOT X multisource_inlined_rel Y',
  1811         self._test('DELETE Note X WHERE X eid %(x)s, NOT X multisource_inlined_rel Y',
  1812                    [('DeleteEntitiesStep',
  1812                    [('DeleteEntitiesStep',
  1813                      [('OneFetchStep', [('Any X WHERE X eid 999999, NOT X multisource_inlined_rel Y, X is Note, Y is IN(Affaire, Note)',
  1813                      [('OneFetchStep', [('Any X WHERE X eid 999999, NOT X multisource_inlined_rel Y, X is Note, Y is IN(Affaire, Note)',
  1814                                          [{'X': 'Note', 'Y': 'Affaire'}, {'X': 'Note', 'Y': 'Note'}])],
  1814                                          [{'X': 'Note', 'Y': 'Affaire'}, {'X': 'Note', 'Y': 'Note'}])],
  1815                        None, None, [self.system], {}, [])
  1815                        None, None, [self.system], {}, [])
  1870 #                         None, None, [self.system], {}, []),
  1870 #                         None, None, [self.system], {}, []),
  1871 #                        ]),
  1871 #                        ]),
  1872 #                     ])
  1872 #                     ])
  1873 
  1873 
  1874     def test_ldap_user_related_to_invariant_and_dont_cross_rel(self):
  1874     def test_ldap_user_related_to_invariant_and_dont_cross_rel(self):
  1875         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1875         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1876         self.cards.dont_cross_relations.add('created_by')
  1876         self.cards.dont_cross_relations.add('created_by')
  1877         try:
  1877         try:
  1878             self._test('Any X,XL WHERE E eid %(x)s, E created_by X, X login XL',
  1878             self._test('Any X,XL WHERE E eid %(x)s, E created_by X, X login XL',
  1879                    [('FetchStep', [('Any X,XL WHERE X login XL, X is CWUser',
  1879                    [('FetchStep', [('Any X,XL WHERE X login XL, X is CWUser',
  1880                                     [{'X': 'CWUser', 'XL': 'String'}])],
  1880                                     [{'X': 'CWUser', 'XL': 'String'}])],
  1891                        {'x': 999999})
  1891                        {'x': 999999})
  1892         finally:
  1892         finally:
  1893             self.cards.dont_cross_relations.remove('created_by')
  1893             self.cards.dont_cross_relations.remove('created_by')
  1894 
  1894 
  1895     def test_ambigous_cross_relation(self):
  1895     def test_ambigous_cross_relation(self):
  1896         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  1896         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  1897         self.cards.support_relations['see_also'] = True
  1897         self.cards.support_relations['see_also'] = True
  1898         self.cards.cross_relations.add('see_also')
  1898         self.cards.cross_relations.add('see_also')
  1899         try:
  1899         try:
  1900             self._test('Any X,AA ORDERBY AA WHERE E eid %(x)s, E see_also X, X modification_date AA',
  1900             self._test('Any X,AA ORDERBY AA WHERE E eid %(x)s, E see_also X, X modification_date AA',
  1901                        [('AggrStep',
  1901                        [('AggrStep',
  2042                        [{'X': 'Card', 'XT': 'String'}])],
  2042                        [{'X': 'Card', 'XT': 'String'}])],
  2043                      None, None, [self.cards], {}, [])
  2043                      None, None, [self.cards], {}, [])
  2044                     ])
  2044                     ])
  2045 
  2045 
  2046     def test_source_conflict_1(self):
  2046     def test_source_conflict_1(self):
  2047         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2047         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2048         with self.assertRaises(BadRQLQuery) as cm:
  2048         with self.assertRaises(BadRQLQuery) as cm:
  2049             self._test('Any X WHERE X cw_source S, S name "system", X eid %(x)s',
  2049             self._test('Any X WHERE X cw_source S, S name "system", X eid %(x)s',
  2050                        [], {'x': 999999})
  2050                        [], {'x': 999999})
  2051         self.assertEqual(str(cm.exception), 'source conflict for term %(x)s')
  2051         self.assertEqual(str(cm.exception), 'source conflict for term %(x)s')
  2052 
  2052 
  2065                      [self.system],
  2065                      [self.system],
  2066                      {}, [])])
  2066                      {}, [])])
  2067 
  2067 
  2068 
  2068 
  2069     def test_ambigous_cross_relation_source_specified(self):
  2069     def test_ambigous_cross_relation_source_specified(self):
  2070         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2070         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2071         self.cards.support_relations['see_also'] = True
  2071         self.cards.support_relations['see_also'] = True
  2072         self.cards.cross_relations.add('see_also')
  2072         self.cards.cross_relations.add('see_also')
  2073         try:
  2073         try:
  2074             self._test('Any X,AA ORDERBY AA WHERE E eid %(x)s, E see_also X, X modification_date AA',
  2074             self._test('Any X,AA ORDERBY AA WHERE E eid %(x)s, E see_also X, X modification_date AA',
  2075                        [('AggrStep',
  2075                        [('AggrStep',
  2196                                        [{'X': 'Affaire', 'Y': 'Note'}])],
  2196                                        [{'X': 'Affaire', 'Y': 'Note'}])],
  2197                      None, None, [self.system], {'Y': 'table0.C0'}, [])
  2197                      None, None, [self.system], {'Y': 'table0.C0'}, [])
  2198                     ])
  2198                     ])
  2199 
  2199 
  2200     def test_nonregr7(self):
  2200     def test_nonregr7(self):
  2201         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2201         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2202         self._test('Any S,SUM(DUR),SUM(I),(SUM(I) - SUM(DUR)),MIN(DI),MAX(DI) GROUPBY S ORDERBY S WHERE A is Affaire, A duration DUR, A invoiced I, A modification_date DI, A in_state S, S name SN, (EXISTS(A concerne WP, W multisource_rel WP)) OR (EXISTS(A concerne W)), W eid %(n)s',
  2202         self._test('Any S,SUM(DUR),SUM(I),(SUM(I) - SUM(DUR)),MIN(DI),MAX(DI) GROUPBY S ORDERBY S WHERE A is Affaire, A duration DUR, A invoiced I, A modification_date DI, A in_state S, S name SN, (EXISTS(A concerne WP, W multisource_rel WP)) OR (EXISTS(A concerne W)), W eid %(n)s',
  2203                    [('FetchStep', [('Any WP WHERE 999999 multisource_rel WP, WP is Note', [{'WP': 'Note'}])],
  2203                    [('FetchStep', [('Any WP WHERE 999999 multisource_rel WP, WP is Note', [{'WP': 'Note'}])],
  2204                      [self.cards], None, {'WP': u'table0.C0'}, []),
  2204                      [self.cards], None, {'WP': u'table0.C0'}, []),
  2205                     ('OneFetchStep', [('Any S,SUM(DUR),SUM(I),(SUM(I) - SUM(DUR)),MIN(DI),MAX(DI) GROUPBY S ORDERBY S WHERE A duration DUR, A invoiced I, A modification_date DI, A in_state S, S name SN, (EXISTS(A concerne WP, WP is Note)) OR (EXISTS(A concerne 999999)), A is Affaire, S is State',
  2205                     ('OneFetchStep', [('Any S,SUM(DUR),SUM(I),(SUM(I) - SUM(DUR)),MIN(DI),MAX(DI) GROUPBY S ORDERBY S WHERE A duration DUR, A invoiced I, A modification_date DI, A in_state S, S name SN, (EXISTS(A concerne WP, WP is Note)) OR (EXISTS(A concerne 999999)), A is Affaire, S is State',
  2206                                        [{'A': 'Affaire', 'DI': 'Datetime', 'DUR': 'Int', 'I': 'Float', 'S': 'State', 'SN': 'String', 'WP': 'Note'}])],
  2206                                        [{'A': 'Affaire', 'DI': 'Datetime', 'DUR': 'Int', 'I': 'Float', 'S': 'State', 'SN': 'String', 'WP': 'Note'}])],
  2207                      None, None, [self.system], {'WP': u'table0.C0'}, [])],
  2207                      None, None, [self.system], {'WP': u'table0.C0'}, [])],
  2208                    {'n': 999999})
  2208                    {'n': 999999})
  2209 
  2209 
  2210     def test_nonregr8(self):
  2210     def test_nonregr8(self):
  2211         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2211         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2212         self._test('Any X,Z WHERE X eid %(x)s, X multisource_rel Y, Z concerne X',
  2212         self._test('Any X,Z WHERE X eid %(x)s, X multisource_rel Y, Z concerne X',
  2213                    [('FetchStep', [('Any 999999 WHERE 999999 multisource_rel Y, Y is Note',
  2213                    [('FetchStep', [('Any 999999 WHERE 999999 multisource_rel Y, Y is Note',
  2214                                     [{'Y': 'Note'}])],
  2214                                     [{'Y': 'Note'}])],
  2215                      [self.cards],
  2215                      [self.cards],
  2216                      None, {u'%(x)s': 'table0.C0'},
  2216                      None, {u'%(x)s': 'table0.C0'},
  2221                      {u'%(x)s': 'table0.C0'}, []),
  2221                      {u'%(x)s': 'table0.C0'}, []),
  2222                     ],
  2222                     ],
  2223                    {'x': 999999})
  2223                    {'x': 999999})
  2224 
  2224 
  2225     def test_nonregr9(self):
  2225     def test_nonregr9(self):
  2226         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2226         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2227         repo._type_source_cache[999998] = ('Note', 'cards', 999998)
  2227         repo._type_source_cache[999998] = ('Note', 'cards', 999998, 'cards')
  2228         self._test('SET X migrated_from Y WHERE X eid %(x)s, Y multisource_rel Z, Z eid %(z)s, Y migrated_from Z',
  2228         self._test('SET X migrated_from Y WHERE X eid %(x)s, Y multisource_rel Z, Z eid %(z)s, Y migrated_from Z',
  2229                    [('FetchStep', [('Any Y WHERE Y multisource_rel 999998, Y is Note', [{'Y': 'Note'}])],
  2229                    [('FetchStep', [('Any Y WHERE Y multisource_rel 999998, Y is Note', [{'Y': 'Note'}])],
  2230                      [self.cards], None, {'Y': u'table0.C0'}, []),
  2230                      [self.cards], None, {'Y': u'table0.C0'}, []),
  2231                     ('UpdateStep',
  2231                     ('UpdateStep',
  2232                      [('OneFetchStep', [('DISTINCT Any Y WHERE Y migrated_from 999998, Y is Note',
  2232                      [('OneFetchStep', [('DISTINCT Any Y WHERE Y migrated_from 999998, Y is Note',
  2234                        None, None, [self.system],
  2234                        None, None, [self.system],
  2235                        {'Y': u'table0.C0'}, [])])],
  2235                        {'Y': u'table0.C0'}, [])])],
  2236                    {'x': 999999, 'z': 999998})
  2236                    {'x': 999999, 'z': 999998})
  2237 
  2237 
  2238     def test_nonregr10(self):
  2238     def test_nonregr10(self):
  2239         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999)
  2239         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999, 'ldap')
  2240         self._test('Any X,AA,AB ORDERBY AA WHERE E eid %(x)s, E owned_by X, X login AA, X modification_date AB',
  2240         self._test('Any X,AA,AB ORDERBY AA WHERE E eid %(x)s, E owned_by X, X login AA, X modification_date AB',
  2241                    [('FetchStep',
  2241                    [('FetchStep',
  2242                      [('Any X,AA,AB WHERE X login AA, X modification_date AB, X is CWUser',
  2242                      [('Any X,AA,AB WHERE X login AA, X modification_date AB, X is CWUser',
  2243                        [{'AA': 'String', 'AB': 'Datetime', 'X': 'CWUser'}])],
  2243                        [{'AA': 'String', 'AB': 'Datetime', 'X': 'CWUser'}])],
  2244                      [self.ldap, self.system], None, {'AA': 'table0.C1', 'AB': 'table0.C2',
  2244                      [self.ldap, self.system], None, {'AA': 'table0.C1', 'AB': 'table0.C2',
  2252                      [])
  2252                      [])
  2253                     ],
  2253                     ],
  2254                    {'x': 999999})
  2254                    {'x': 999999})
  2255 
  2255 
  2256     def test_nonregr11(self):
  2256     def test_nonregr11(self):
  2257         repo._type_source_cache[999999] = ('Bookmark', 'system', 999999)
  2257         repo._type_source_cache[999999] = ('Bookmark', 'system', 999999, 'system')
  2258         self._test('SET X bookmarked_by Y WHERE X eid %(x)s, Y login "hop"',
  2258         self._test('SET X bookmarked_by Y WHERE X eid %(x)s, Y login "hop"',
  2259                    [('UpdateStep',
  2259                    [('UpdateStep',
  2260                      [('OneFetchStep', [('DISTINCT Any Y WHERE Y login "hop", Y is CWUser', [{'Y': 'CWUser'}])],
  2260                      [('OneFetchStep', [('DISTINCT Any Y WHERE Y login "hop", Y is CWUser', [{'Y': 'CWUser'}])],
  2261                        None, None, [self.ldap, self.system], {}, [])]
  2261                        None, None, [self.ldap, self.system], {}, [])]
  2262                      )],
  2262                      )],
  2263                    {'x': 999999})
  2263                    {'x': 999999})
  2264 
  2264 
  2265     def test_nonregr12(self):
  2265     def test_nonregr12(self):
  2266         repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2266         repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2267         self._test('Any X ORDERBY Z DESC WHERE X modification_date Z, E eid %(x)s, E see_also X',
  2267         self._test('Any X ORDERBY Z DESC WHERE X modification_date Z, E eid %(x)s, E see_also X',
  2268                    [('FetchStep', [('Any X,Z WHERE X modification_date Z, X is Note',
  2268                    [('FetchStep', [('Any X,Z WHERE X modification_date Z, X is Note',
  2269                                     [{'X': 'Note', 'Z': 'Datetime'}])],
  2269                                     [{'X': 'Note', 'Z': 'Datetime'}])],
  2270                      [self.cards, self.system], None, {'X': 'table0.C0', 'X.modification_date': 'table0.C1', 'Z': 'table0.C1'},
  2270                      [self.cards, self.system], None, {'X': 'table0.C0', 'X.modification_date': 'table0.C1', 'Z': 'table0.C1'},
  2271                      []),
  2271                      []),
  2345                      {'U': 'table1.C0', 'UL': 'table1.C1'},
  2345                      {'U': 'table1.C0', 'UL': 'table1.C1'},
  2346                      [])],
  2346                      [])],
  2347                    {'x': self.session.user.eid})
  2347                    {'x': self.session.user.eid})
  2348 
  2348 
  2349     def test_nonregr14_1(self):
  2349     def test_nonregr14_1(self):
  2350         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999)
  2350         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999, 'ldap')
  2351         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2351         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2352                    [('OneFetchStep', [('Any 999999 WHERE 999999 owned_by 999999', [{}])],
  2352                    [('OneFetchStep', [('Any 999999 WHERE 999999 owned_by 999999', [{}])],
  2353                      None, None, [self.system], {}, [])],
  2353                      None, None, [self.system], {}, [])],
  2354                    {'x': 999999, 'u': 999999})
  2354                    {'x': 999999, 'u': 999999})
  2355 
  2355 
  2356     def test_nonregr14_2(self):
  2356     def test_nonregr14_2(self):
  2357         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999)
  2357         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999999, 'ldap')
  2358         repo._type_source_cache[999998] = ('Note', 'system', 999998)
  2358         repo._type_source_cache[999998] = ('Note', 'system', 999998, 'system')
  2359         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2359         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2360                    [('OneFetchStep', [('Any 999998 WHERE 999998 owned_by 999999', [{}])],
  2360                    [('OneFetchStep', [('Any 999998 WHERE 999998 owned_by 999999', [{}])],
  2361                      None, None, [self.system], {}, [])],
  2361                      None, None, [self.system], {}, [])],
  2362                    {'x': 999998, 'u': 999999})
  2362                    {'x': 999998, 'u': 999999})
  2363 
  2363 
  2364     def test_nonregr14_3(self):
  2364     def test_nonregr14_3(self):
  2365         repo._type_source_cache[999999] = ('CWUser', 'system', 999999)
  2365         repo._type_source_cache[999999] = ('CWUser', 'system', 999999, 'system')
  2366         repo._type_source_cache[999998] = ('CWUser', 'ldap', 999998)
  2366         repo._type_source_cache[999998] = ('CWUser', 'ldap', 999998, 'ldap')
  2367         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2367         self._test('Any X WHERE X eid %(x)s, X owned_by U, U eid %(u)s',
  2368                    [('OneFetchStep', [('Any 999998 WHERE 999998 owned_by 999999', [{}])],
  2368                    [('OneFetchStep', [('Any 999998 WHERE 999998 owned_by 999999', [{}])],
  2369                      None, None, [self.system], {}, [])],
  2369                      None, None, [self.system], {}, [])],
  2370                    {'x': 999998, 'u': 999999})
  2370                    {'x': 999998, 'u': 999999})
  2371 
  2371 
  2372     def test_nonregr_identity_no_source_access_1(self):
  2372     def test_nonregr_identity_no_source_access_1(self):
  2373         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999998)
  2373         repo._type_source_cache[999999] = ('CWUser', 'ldap', 999998, 'ldap')
  2374         self._test('Any S WHERE S identity U, S eid %(s)s, U eid %(u)s',
  2374         self._test('Any S WHERE S identity U, S eid %(s)s, U eid %(u)s',
  2375                    [('OneFetchStep', [('Any 999999 WHERE 999999 identity 999999', [{}])],
  2375                    [('OneFetchStep', [('Any 999999 WHERE 999999 identity 999999', [{}])],
  2376                      None, None, [self.system], {}, [])],
  2376                      None, None, [self.system], {}, [])],
  2377                    {'s': 999999, 'u': 999999})
  2377                    {'s': 999999, 'u': 999999})
  2378 
  2378 
  2379     def test_nonregr_identity_no_source_access_2(self):
  2379     def test_nonregr_identity_no_source_access_2(self):
  2380         repo._type_source_cache[999999] = ('EmailAddress', 'system', 999999)
  2380         repo._type_source_cache[999999] = ('EmailAddress', 'system', 999999, 'system')
  2381         repo._type_source_cache[999998] = ('CWUser', 'ldap', 999998)
  2381         repo._type_source_cache[999998] = ('CWUser', 'ldap', 999998, 'ldap')
  2382         self._test('Any X WHERE O use_email X, ((EXISTS(O identity U)) OR (EXISTS(O in_group G, G name IN("managers", "staff")))) OR (EXISTS(O in_group G2, U in_group G2, NOT G2 name "users")), X eid %(x)s, U eid %(u)s',
  2382         self._test('Any X WHERE O use_email X, ((EXISTS(O identity U)) OR (EXISTS(O in_group G, G name IN("managers", "staff")))) OR (EXISTS(O in_group G2, U in_group G2, NOT G2 name "users")), X eid %(x)s, U eid %(u)s',
  2383                    [('OneFetchStep', [('Any 999999 WHERE O use_email 999999, ((EXISTS(O identity 999998)) OR (EXISTS(O in_group G, G name IN("managers", "staff")))) OR (EXISTS(O in_group G2, 999998 in_group G2, NOT G2 name "users"))',
  2383                    [('OneFetchStep', [('Any 999999 WHERE O use_email 999999, ((EXISTS(O identity 999998)) OR (EXISTS(O in_group G, G name IN("managers", "staff")))) OR (EXISTS(O in_group G2, 999998 in_group G2, NOT G2 name "users"))',
  2384                                        [{'G': 'CWGroup', 'G2': 'CWGroup', 'O': 'CWUser'}])],
  2384                                        [{'G': 'CWGroup', 'G2': 'CWGroup', 'O': 'CWUser'}])],
  2385                      None, None, [self.system], {}, [])],
  2385                      None, None, [self.system], {}, [])],
  2386                    {'x': 999999, 'u': 999998})
  2386                    {'x': 999999, 'u': 999998})
  2387 
  2387 
  2388     def test_nonregr_similar_subquery(self):
  2388     def test_nonregr_similar_subquery(self):
  2389         repo._type_source_cache[999999] = ('Personne', 'system', 999999)
  2389         repo._type_source_cache[999999] = ('Personne', 'system', 999999, 'system')
  2390         self._test('Any T,TD,U,T,UL WITH T,TD,U,UL BEING ('
  2390         self._test('Any T,TD,U,T,UL WITH T,TD,U,UL BEING ('
  2391                    '(Any T,TD,U,UL WHERE X eid %(x)s, T comments X, T content TD, T created_by U?, U login UL)'
  2391                    '(Any T,TD,U,UL WHERE X eid %(x)s, T comments X, T content TD, T created_by U?, U login UL)'
  2392                    ' UNION '
  2392                    ' UNION '
  2393                    '(Any T,TD,U,UL WHERE X eid %(x)s, X connait P, T comments P, T content TD, T created_by U?, U login UL))',
  2393                    '(Any T,TD,U,UL WHERE X eid %(x)s, X connait P, T comments P, T content TD, T created_by U?, U login UL))',
  2394                    # XXX optimization: use a OneFetchStep with a UNION of both queries
  2394                    # XXX optimization: use a OneFetchStep with a UNION of both queries
  2454         assert 'multisource_crossed_rel' in repo.sources_by_uri['cards'].cross_relations
  2454         assert 'multisource_crossed_rel' in repo.sources_by_uri['cards'].cross_relations
  2455     _test = test_plan
  2455     _test = test_plan
  2456 
  2456 
  2457 
  2457 
  2458     def test_linked_external_entities(self):
  2458     def test_linked_external_entities(self):
  2459         repo._type_source_cache[999999] = ('Tag', 'system', 999999)
  2459         repo._type_source_cache[999999] = ('Tag', 'system', 999999, 'system')
  2460         self._test('Any X,XT WHERE X is Card, X title XT, T tags X, T eid %(t)s',
  2460         self._test('Any X,XT WHERE X is Card, X title XT, T tags X, T eid %(t)s',
  2461                    [('FetchStep',
  2461                    [('FetchStep',
  2462                      [('Any X,XT WHERE X title XT, X is Card', [{'X': 'Card', 'XT': 'String'}])],
  2462                      [('Any X,XT WHERE X title XT, X is Card', [{'X': 'Card', 'XT': 'String'}])],
  2463                      [self.cards, self.cards2, self.system],
  2463                      [self.cards, self.cards2, self.system],
  2464                      None, {'X': 'table0.C0', 'X.title': 'table0.C1', 'XT': 'table0.C1'},
  2464                      None, {'X': 'table0.C0', 'X.title': 'table0.C1', 'XT': 'table0.C1'},
  2470                      {'X': 'table0.C0', 'X.title': 'table0.C1', 'XT': 'table0.C1'},
  2470                      {'X': 'table0.C0', 'X.title': 'table0.C1', 'XT': 'table0.C1'},
  2471                      [])],
  2471                      [])],
  2472                    {'t': 999999})
  2472                    {'t': 999999})
  2473 
  2473 
  2474     def test_version_depends_on(self):
  2474     def test_version_depends_on(self):
  2475         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2475         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2476         self._test('Any X,AD,AE WHERE E eid %(x)s, E migrated_from X, X in_state AD, AD name AE',
  2476         self._test('Any X,AD,AE WHERE E eid %(x)s, E migrated_from X, X in_state AD, AD name AE',
  2477                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2477                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2478                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2478                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2479                      [self.cards, self.cards2, self.system],
  2479                      [self.cards, self.cards2, self.system],
  2480                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2480                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2486                      {'AD': 'table0.C1', 'AD.name': 'table0.C2', 'AE': 'table0.C2', 'X': 'table0.C0'},
  2486                      {'AD': 'table0.C1', 'AD.name': 'table0.C2', 'AE': 'table0.C2', 'X': 'table0.C0'},
  2487                      [])],
  2487                      [])],
  2488                    {'x': 999999})
  2488                    {'x': 999999})
  2489 
  2489 
  2490     def test_version_crossed_depends_on_1(self):
  2490     def test_version_crossed_depends_on_1(self):
  2491         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2491         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2492         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
  2492         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
  2493                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2493                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2494                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2494                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2495                      [self.cards, self.cards2, self.system],
  2495                      [self.cards, self.cards2, self.system],
  2496                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2496                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2509                        [])]
  2509                        [])]
  2510                      )],
  2510                      )],
  2511                    {'x': 999999})
  2511                    {'x': 999999})
  2512 
  2512 
  2513     def test_version_crossed_depends_on_2(self):
  2513     def test_version_crossed_depends_on_2(self):
  2514         self.repo._type_source_cache[999999] = ('Note', 'system', 999999)
  2514         self.repo._type_source_cache[999999] = ('Note', 'system', 999999, 'system')
  2515         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
  2515         self._test('Any X,AD,AE WHERE E eid %(x)s, E multisource_crossed_rel X, X in_state AD, AD name AE',
  2516                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2516                    [('FetchStep', [('Any X,AD,AE WHERE X in_state AD, AD name AE, AD is State, X is Note',
  2517                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2517                                     [{'AD': 'State', 'AE': 'String', 'X': 'Note'}])],
  2518                      [self.cards, self.cards2, self.system],
  2518                      [self.cards, self.cards2, self.system],
  2519                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2519                      None, {'AD': 'table0.C1', 'AD.name': 'table0.C2',
  2585                      []
  2585                      []
  2586                      )]
  2586                      )]
  2587                        )
  2587                        )
  2588 
  2588 
  2589     def test_nonregr_dont_cross_rel_source_filtering_1(self):
  2589     def test_nonregr_dont_cross_rel_source_filtering_1(self):
  2590         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2590         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2591         self._test('Any S WHERE E eid %(x)s, E in_state S, NOT S name "moved"',
  2591         self._test('Any S WHERE E eid %(x)s, E in_state S, NOT S name "moved"',
  2592                    [('OneFetchStep', [('Any S WHERE 999999 in_state S, NOT S name "moved", S is State',
  2592                    [('OneFetchStep', [('Any S WHERE 999999 in_state S, NOT S name "moved", S is State',
  2593                                        [{'S': 'State'}])],
  2593                                        [{'S': 'State'}])],
  2594                      None, None, [self.cards], {}, []
  2594                      None, None, [self.cards], {}, []
  2595                      )],
  2595                      )],
  2596                    {'x': 999999})
  2596                    {'x': 999999})
  2597 
  2597 
  2598     def test_nonregr_dont_cross_rel_source_filtering_2(self):
  2598     def test_nonregr_dont_cross_rel_source_filtering_2(self):
  2599         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2599         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2600         self._test('Any X,AA,AB WHERE E eid %(x)s, E in_state X, X name AA, X modification_date AB',
  2600         self._test('Any X,AA,AB WHERE E eid %(x)s, E in_state X, X name AA, X modification_date AB',
  2601                    [('OneFetchStep', [('Any X,AA,AB WHERE 999999 in_state X, X name AA, X modification_date AB, X is State',
  2601                    [('OneFetchStep', [('Any X,AA,AB WHERE 999999 in_state X, X name AA, X modification_date AB, X is State',
  2602                                        [{'AA': 'String', 'AB': 'Datetime', 'X': 'State'}])],
  2602                                        [{'AA': 'String', 'AB': 'Datetime', 'X': 'State'}])],
  2603                      None, None, [self.cards], {}, []
  2603                      None, None, [self.cards], {}, []
  2604                      )],
  2604                      )],
  2605                    {'x': 999999})
  2605                    {'x': 999999})
  2606 
  2606 
  2607     def test_nonregr_eid_query(self):
  2607     def test_nonregr_eid_query(self):
  2608         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999)
  2608         self.repo._type_source_cache[999999] = ('Note', 'cards', 999999, 'cards')
  2609         self._test('Any X WHERE X eid 999999',
  2609         self._test('Any X WHERE X eid 999999',
  2610                    [('OneFetchStep', [('Any 999999', [{}])],
  2610                    [('OneFetchStep', [('Any 999999', [{}])],
  2611                      None, None, [self.system], {}, []
  2611                      None, None, [self.system], {}, []
  2612                      )],
  2612                      )],
  2613                    {'x': 999999})
  2613                    {'x': 999999})
  2705                      {'VC': 'table0.C0'},
  2705                      {'VC': 'table0.C0'},
  2706                      [])
  2706                      [])
  2707                     ])
  2707                     ])
  2708 
  2708 
  2709     def test_fully_simplified_extsource(self):
  2709     def test_fully_simplified_extsource(self):
  2710         self.repo._type_source_cache[999998] = ('Note', 'vcs', 999998)
  2710         self.repo._type_source_cache[999998] = ('Note', 'vcs', 999998, 'vcs')
  2711         self.repo._type_source_cache[999999] = ('Note', 'vcs', 999999)
  2711         self.repo._type_source_cache[999999] = ('Note', 'vcs', 999999, 'vcs')
  2712         self._test('Any X, Y WHERE NOT X multisource_rel Y, X eid 999998, Y eid 999999',
  2712         self._test('Any X, Y WHERE NOT X multisource_rel Y, X eid 999998, Y eid 999999',
  2713                    [('OneFetchStep', [('Any 999998,999999 WHERE NOT EXISTS(999998 multisource_rel 999999)', [{}])],
  2713                    [('OneFetchStep', [('Any 999998,999999 WHERE NOT EXISTS(999998 multisource_rel 999999)', [{}])],
  2714                      None, None, [self.vcs], {}, [])
  2714                      None, None, [self.vcs], {}, [])
  2715                     ])
  2715                     ])
  2716 
  2716 
  2717     def test_nonregr_fully_simplified_extsource(self):
  2717     def test_nonregr_fully_simplified_extsource(self):
  2718         self.repo._type_source_cache[999998] = ('Note', 'vcs', 999998)
  2718         self.repo._type_source_cache[999998] = ('Note', 'vcs', 999998, 'vcs')
  2719         self.repo._type_source_cache[999999] = ('Note', 'vcs', 999999)
  2719         self.repo._type_source_cache[999999] = ('Note', 'vcs', 999999, 'vcs')
  2720         self.repo._type_source_cache[1000000] = ('Note', 'system', 1000000)
  2720         self.repo._type_source_cache[1000000] = ('Note', 'system', 1000000, 'system')
  2721         self._test('DISTINCT Any T,FALSE,L,M WHERE L eid 1000000, M eid 999999, T eid 999998',
  2721         self._test('DISTINCT Any T,FALSE,L,M WHERE L eid 1000000, M eid 999999, T eid 999998',
  2722                    [('OneFetchStep', [('DISTINCT Any 999998,FALSE,1000000,999999', [{}])],
  2722                    [('OneFetchStep', [('DISTINCT Any 999998,FALSE,1000000,999999', [{}])],
  2723                      None, None, [self.system], {}, [])
  2723                      None, None, [self.system], {}, [])
  2724                     ])
  2724                     ])
  2725 
  2725