def queryCatalog(self, batch=True, b_start=0, b_size=30, sort_on=None): from plone.app.contenttypes.behaviors.collection import \ ICollection as ICollection_behavior return ICollection_behavior(self).results(batch, b_start, b_size, sort_on=sort_on)
def test_collection_templates(self): self.portal.acl_users.userFolderAddUser(SITE_OWNER_NAME, SITE_OWNER_PASSWORD, ['Manager'], []) browser = self.browser portal = self.portal login(portal, SITE_OWNER_NAME) # add an image that will be listed by the collection portal.invokeFactory('Image', 'image', title='Image example') image = self.portal['image'] image.image = dummy_image() # add a collection, so we can add a query to it portal.invokeFactory('Collection', 'collection', title='New Collection') collection = portal['collection'] # Search for images query = [{ 'i': 'Type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'Image', }] collection.text = RichTextValue(u'Lorem collection ipsum', 'text/plain', 'text/html') wrapped = ICollection_behavior(collection) # set the query and publish the collection wrapped.query = query workflow = portal.portal_workflow workflow.doActionFor(collection, 'publish') commit() logout() # open a browser to see if our image is in the results browser.handleErrors = False url = collection.absolute_url() browser.open(url) self.assertIn('Lorem collection ipsum', browser.contents) self.assertIn('Image example', browser.contents) # open summary_view template browser.open('{0}/@@summary_view'.format(url)) self.assertIn('Lorem collection ipsum', browser.contents) self.assertIn('Image example', browser.contents) # open full_view template browser.open('{0}/@@full_view'.format(url)) self.assertIn('Lorem collection ipsum', browser.contents) self.assertIn('Image example', browser.contents) # open tabular_view template browser.open('{0}/@@tabular_view'.format(url)) self.assertIn('Lorem collection ipsum', browser.contents) self.assertIn('Image example', browser.contents) # open thumbnail_view template browser.open('{0}/@@album_view'.format(url)) self.assertIn('Lorem collection ipsum', browser.contents) self.assertIn('Image example', browser.contents)
def selectedViewFields(self): """Returns a list of all metadata fields from the catalog that were selected. """ from plone.app.contenttypes.behaviors.collection import \ ICollection as ICollection_behavior return ICollection_behavior(self).selectedViewFields()
def __call__(self, context, **query): ctool = getToolByName(context, 'portal_faceted', None) if ctool: search = ctool.search else: logger.debug('portal_faceted not present, using portal_catalog') ctool = getToolByName(context, 'portal_catalog') search = ctool.searchResults # Also get query from Topic buildQuery = getattr(context, 'buildQuery', None) newquery = buildQuery and buildQuery() or {} formquery = None # Get query from Collection if HAS_PAT: if PACI.ICollection.providedBy(context): infos = ICollection_behavior(context) sort_order = ('descending' if infos.sort_reversed else 'ascending') sort_on = infos.sort_on formquery = infos.query if ICollection.providedBy(context): getRawQuery = getattr(context, 'getRawQuery', lambda: []) formquery = getRawQuery() getSortOn = getattr(context, 'getSort_on', lambda: None) sort_on = getSortOn() if sort_on: getSortReversed = getattr( context, 'getSort_reversed', lambda: None) sort_order = getSortReversed() if sort_order: sort_order = 'descending' else: sort_order = 'ascending' else: sort_order = None if formquery is not None: newquery = parseFormquery(context, formquery, sort_on, sort_order) if not isinstance(newquery, dict): newquery = {} # Avoid mixing sorting params from faceted and collection if 'sort_on' not in query: query.pop('sort_order', None) if 'sort_on' in query and 'sort_order' not in query: newquery.pop('sort_order', None) newquery.update(query) notify(QueryWillBeExecutedEvent(context, newquery)) return search(**newquery)
def test_collection_templates(self): browser = self.browser portal = self.layer['portal'] login(portal, 'admin') # add an image that will be listed by the collection portal.invokeFactory("Image", "image", title="Image example") image = self.portal['image'] image.image = dummy_image() # add a collection, so we can add a query to it portal.invokeFactory("Collection", "collection", title="New Collection") collection = portal['collection'] # Search for images query = [{ 'i': 'Type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'Image', }] collection.text = RichTextValue(u"Lorem collection ipsum", 'text/plain', 'text/html') wrapped = ICollection_behavior(collection) # set the query and publish the collection wrapped.query = query workflow = portal.portal_workflow workflow.doActionFor(collection, "publish") commit() logout() # open a browser to see if our image is in the results browser.handleErrors = False url = collection.absolute_url() browser.open(url) self.assertTrue("Lorem collection ipsum" in browser.contents) self.assertTrue("Image example" in browser.contents) # open summary_view template browser.open('%s/@@summary_view' % url) self.assertTrue("Lorem collection ipsum" in browser.contents) self.assertTrue("Image example" in browser.contents) # open full_view template browser.open('%s/@@full_view' % url) self.assertTrue("Lorem collection ipsum" in browser.contents) self.assertTrue("Image example" in browser.contents) # open tabular_view template browser.open('%s/@@tabular_view' % url) self.assertTrue("Lorem collection ipsum" in browser.contents) self.assertTrue("Image example" in browser.contents) # open thumbnail_view template browser.open('%s/@@album_view' % url) self.assertTrue("Lorem collection ipsum" in browser.contents) self.assertTrue("Image example" in browser.contents)
def test_respect_navigation_root(self): self.portal.acl_users.userFolderAddUser(SITE_OWNER_NAME, SITE_OWNER_PASSWORD, ['Manager'], []) portal = self.portal login(portal, SITE_OWNER_NAME) # Create two subsites i.e create two folders and mark them with # INavigationRoot for i in range(1, 3): folder_id = 'folder{0}'.format(i) portal.invokeFactory('Folder', folder_id, title='Folder{0}'.format(i)) folder = portal[folder_id] alsoProvides(folder, INavigationRoot) folders = (portal['folder1'], portal['folder2']) # Add a content item to each folder for f in folders: f_id = f.getId() f.invokeFactory('Document', 'item_in_{0}'.format(f_id), title='Item In {0}'.format(f_id)) # Add a collection to folder1 folder1 = folders[0] folder1.invokeFactory('Collection', 'collection1', title='Collection 1') collection1 = folder1['collection1'] wrapped = ICollection_behavior(collection1) wrapped.query = [ { 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'Document', }, # use a "/" path and navroot works fine! { 'i': 'path', 'o': 'plone.app.querystring.operation.string.path', 'v': '/', }, ] # Check if only the item inside folder1 is returned, since it's a # navigation root. items = wrapped.results(batch=False) ids = [i.getId() for i in items] self.assertListEqual(ids, ['item_in_folder1'])
def test_custom_query(self): self.portal.acl_users.userFolderAddUser(SITE_OWNER_NAME, SITE_OWNER_PASSWORD, ['Manager'], []) portal = self.portal login(portal, SITE_OWNER_NAME) query = [{ 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': ['News Item', 'Document'], }] portal.invokeFactory( 'Collection', 'collection', title='New Collection', query=query, ) # item 1 portal.invokeFactory(id='testnews', type_name='News Item') item1 = portal.testnews item1.reindexObject() # item 2 portal.invokeFactory(id='testdoc', type_name='Document') item2 = portal.testdoc item2.reindexObject() collection = portal['collection'] wrapped = ICollection_behavior(collection) # Test unmodified query results = wrapped.results(batch=False) self.assertEqual(len(results), 2) # Test with custom query results = wrapped.results(batch=False, custom_query={'portal_type': 'Document'}) self.assertEqual(len(results), 1) self.assertEqual(results[0].id, 'testdoc') # Test with custom query, which should not find anything results = wrapped.results(batch=False, custom_query={ 'portal_type': 'Document', 'id': 'bla' }) self.assertEqual(len(results), 0)
def test_sorting_1(self): self.portal.acl_users.userFolderAddUser( SITE_OWNER_NAME, SITE_OWNER_PASSWORD, ['Manager'], []) portal = self.portal login(portal, SITE_OWNER_NAME) query = [{ 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'News Item', }] portal.invokeFactory('Collection', 'collection', title='New Collection', query=query, sort_on='created', sort_reversed=True, ) now = DateTime() # News Item 1 portal.invokeFactory(id='newsitem1', type_name='News Item') item1 = portal.newsitem1 item1.creation_date = now - 2 item1.reindexObject() # News Item 2 portal.invokeFactory(id='newsitem2', type_name='News Item') item2 = portal.newsitem2 item2.creation_date = now - 1 item2.reindexObject() # News Item 3 portal.invokeFactory(id='newsitem3', type_name='News Item') item3 = portal.newsitem3 item3.creation_date = now item3.reindexObject() collection = portal['collection'] wrapped = ICollection_behavior(collection) results = wrapped.results(batch=False) ritem0 = results[0] ritem1 = results[1] ritem2 = results[2] self.assertTrue(ritem0.CreationDate() > ritem1.CreationDate()) self.assertTrue(ritem1.CreationDate() > ritem2.CreationDate())
def test_sorting_1(self): portal = self.layer['portal'] login(portal, 'admin') query = [{ 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'News Item', }] portal.invokeFactory("Collection", "collection", title="New Collection", query=query, sort_on='created', sort_reversed=True, ) now = DateTime() # News Item 1 portal.invokeFactory(id='newsitem1', type_name='News Item') item1 = portal.newsitem1 item1.creation_date = now - 2 item1.reindexObject() # News Item 2 portal.invokeFactory(id='newsitem2', type_name='News Item') item2 = portal.newsitem2 item2.creation_date = now - 1 item2.reindexObject() # News Item 3 portal.invokeFactory(id='newsitem3', type_name='News Item') item3 = portal.newsitem3 item3.creation_date = now item3.reindexObject() collection = portal['collection'] wrapped = ICollection_behavior(collection) results = wrapped.results(batch=False) ritem0 = results[0] ritem1 = results[1] ritem2 = results[2] self.assertTrue(ritem0.CreationDate() > ritem1.CreationDate()) self.assertTrue(ritem1.CreationDate() > ritem2.CreationDate())
def test_custom_query(self): portal = self.layer['portal'] login(portal, 'admin') query = [{ 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': ['News Item', 'Document'], }] portal.invokeFactory( "Collection", "collection", title="New Collection", query=query, ) # item 1 portal.invokeFactory(id='testnews', type_name='News Item') item1 = portal.testnews item1.reindexObject() # item 2 portal.invokeFactory(id="testdoc", type_name='Document') item2 = portal.testdoc item2.reindexObject() collection = portal['collection'] wrapped = ICollection_behavior(collection) # Test unmodified query results = wrapped.results(batch=False) self.assertEqual(len(results), 2) # Test with custom query results = wrapped.results(batch=False, custom_query={'portal_type': 'Document'}) self.assertEqual(len(results), 1) self.assertEqual(results[0].id, 'testdoc') # Test with custom query, which should not find anything results = wrapped.results(batch=False, custom_query={ 'portal_type': 'Document', 'id': 'bla' }) self.assertEqual(len(results), 0)
def test_respect_navigation_root(self): portal = self.layer['portal'] login(portal, 'admin') # Create two subsites i.e create two folders and mark them with # INavigationRoot for i in xrange(1, 3): folder_id = 'folder{}'.format(i) portal.invokeFactory('Folder', folder_id, title='Folder{}'.format(i)) folder = portal[folder_id] alsoProvides(folder, INavigationRoot) folders = (portal['folder1'], portal['folder2']) # Add a content item to each folder for f in folders: f_id = f.getId() f.invokeFactory('Document', 'item_in_{}'.format(f_id), title='Item In {}'.format(f_id)) # Add a collection to folder1 folder1 = folders[0] folder1.invokeFactory('Collection', 'collection1', title='Collection 1') collection1 = folder1['collection1'] wrapped = ICollection_behavior(collection1) wrapped.query = [{ 'i': 'portal_type', 'o': 'plone.app.querystring.operation.string.is', 'v': 'Document', }] # Check if only the item inside folder1 is returned, since it's a # navigation root. items = wrapped.results(batch=False) ids = [i.getId() for i in items] self.assertListEqual(ids, ['item_in_folder1'])
def results(self, **kwargs): from plone.app.contenttypes.behaviors.collection import \ ICollection as ICollection_behavior return ICollection_behavior(self).results(**kwargs)
def __call__(self, context, **query): # return super(FacetedCatalog, self).__call__(context, **query) ctool = getToolByName(context, 'portal_faceted', None) if ctool: search = ctool.search else: logger.debug('portal_faceted not present, using portal_catalog') ctool = getToolByName(context, 'portal_catalog') search = ctool.searchResults # Also get query from Topic buildQuery = getattr(context, 'buildQuery', None) newquery = buildQuery and buildQuery() or {} formquery = None # Get query from Collection if HAS_PAT: if PACI.ICollection.providedBy(context): infos = ICollection_behavior(context) sort_order = ('descending' if infos.sort_reversed else 'ascending') sort_on = infos.sort_on formquery = infos.query if ICollection.providedBy(context): getRawQuery = getattr(context, 'getRawQuery', lambda: []) formquery = getRawQuery() getSortOn = getattr(context, 'getSort_on', lambda: None) sort_on = getSortOn() if sort_on: getSortReversed = getattr(context, 'getSort_reversed', lambda: None) sort_order = getSortReversed() if sort_order: sort_order = 'descending' else: sort_order = 'ascending' else: sort_order = None if formquery is not None: newquery = parseFormquery(context, formquery, sort_on, sort_order) if not isinstance(newquery, dict): newquery = {} # Avoid mixing sorting params from faceted and collection if 'sort_on' not in query: query.pop('sort_order', None) if 'sort_on' in query and 'sort_order' not in query: newquery.pop('sort_order', None) newquery.update(query) notify(QueryWillBeExecutedEvent(context, newquery)) # code above is unchanged from original code # example of query: #{'sort_order': 'descending', # 'Language': ['fr', ''], # 'portal_type': {'query': ['operationalobjective']}, # 'sort_on': 'created', # ':has_child': {'query': { # 'portal_type': {'query': ['pstaction']}, # 'planned_end_date': {'query': DateTime('2016/08/12 12:49:6.218718 GMT+2'), 'range': 'max'}}}} has_child_filters = [ k for k in newquery.keys() if k.startswith(':has_child') ] if len(has_child_filters) > 1: raise Exception('We only support one :has_child filter') if has_child_filters: sort_on = newquery.pop('sort_on', None) sort_order = newquery.pop('sort_order', None) limit = newquery.pop('limit', None) b_start = int(newquery.pop('b_start', 0)) b_size = newquery.pop('b_size', None) if b_size is not None: b_size = int(b_size) if b_size is not None: limit = b_start + b_size elif limit and b_size is None: b_size = limit has_child_filter = deepcopy( newquery[has_child_filters[0]]['query']) # be sure we don't do a useless sort and we have all results has_child_filter.pop('sort_on', None) has_child_filter.pop('sort_order', None) has_child_filter.pop('limit', None) has_child_filter.pop('b_size', None) children_results = search(**has_child_filter) parentRIDs = IISet() for b in children_results: # TODO: possible optimization is to add parentRID as brain metadata parentRID = ctool._catalog.uids.get('/'.join( b.getPath().split('/')[:-1])) parentRIDs.add(parentRID) brains = search(**newquery) # brains should be a LazyMap, access direct to brains._seq which is a list of rids # instead of doing IISet(brain.getRID() for brain in brains) rs = weightedIntersection(IISet(brains._seq), parentRIDs)[1] rlen = len(rs) if sort_on is not None: # We only support single sort order sort_index = ctool._catalog.indexes[sort_on] reverse = 1 if sort_order == 'descending' else 0 brains = ctool._catalog.sortResults(rs, sort_index, reverse, limit, merge=1, actual_result_count=rlen, b_start=b_start, b_size=b_size) else: brains = brains.__class__(brains._func, rs, rlen, rlen) else: brains = search(**newquery) return brains