Commit 840066ac authored by Klaus Wölfel's avatar Klaus Wölfel Committed by Jérome Perrin

Fix a broken case of Worklist calculation when using security_uid columns

With some combinations of worklists using two additional security_uid
columns coming from local role groups, some documents might be excluded
from worklists, without the fix, when running with a random
PYTHONHASHSEED, the test can fail with:

    FAIL: test_worklist_exclusionlist_collision (erp5.component.test.erp5_version.testERP5CatalogSecurityUidOptimization.TestSecurityUidOptimizationWorklist)
    ----------------------------------------------------------------------
    Traceback (most recent call last):
      File "<portal_components/test.erp5.testERP5CatalogSecurityUidOptimization>", line 370, in test_worklist_exclusionlist_collision
        'security_uid_or_alternate_security_uid_draft': 1,
      File "<portal_components/test.erp5.testERP5CatalogSecurityUidOptimization>", line 213, in assertWorklistCount
        expected_count_by_worklist_id,
    AssertionError: {'security_uid_or_alternate_security_uid_draft': 1} != {'collision_worklist': 1, 'security_uid_or_alternate_security_uid_draft': 1}
    - {'security_uid_or_alternate_security_uid_draft': 1}
    + {'collision_worklist': 1, 'security_uid_or_alternate_security_uid_draft': 1}
    ?  +++++++++++++++++++++++++

What happens in sumCatalogResultByWorklist is something like this:

    (Pdb) pp criterion_dict
    {'alternate_security_uid': <ExclusionList [11, 14]>,
     'other_security_uid': frozenset([13L]),
     'portal_type': frozenset(['Person']),
     'validation_state': frozenset(['draft'])}

    (Pdb) pp catalog_result.dictionaries()
    [{'alternate_security_uid': 12,
      'count': Decimal('1'),
      'other_security_uid': 13,
      'portal_type': 'Person',
      'validation_state': 'draft'}]

Depending on the worklists grouped together in grouped_worklist_dict and
the order this dict is iterated, we may reach a situation where
criterion_id_list contains 'alternate_security_uid', because for another
worklist it was not an ExclusionList but a list to be applied, in this
case, this if condition is false:

        for criterion_id in criterion_id_list:
          criterion_value_set = criterion_dict[criterion_id]
          if result_line[criterion_id] not in criterion_value_set:
            is_candidate = False

and the row is not counted in collision_worklist worklist.
Co-authored-by: Jérome Perrin's avatarJérome Perrin <jerome@nexedi.com>
parent 590c1b3e
Pipeline #33525 failed with stage
in 0 seconds