-
-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #8 from plone/move_gopipindex
move gopipindex from plone.app.folder to plone.folder
- Loading branch information
Showing
3 changed files
with
170 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
<dtml-var manage_page_header> | ||
<dtml-var "manage_form_title(this(), _, form_title='Add GopipIndex')"> | ||
|
||
<p class="form-help"> | ||
A <em>GopipIndex</em> fakes the formerly used "getObjPositionInParent" index | ||
by retrieving the necessary information directly from the search results' | ||
containers. It works as a drop-in replacement and makes expensive indexing | ||
of each item's position unnecessary. | ||
</p> | ||
|
||
<form action="manage_addGopipIndex" method="post" enctype="multipart/form-data"> | ||
<table cellspacing="0" cellpadding="2" border="0"> | ||
<tr> | ||
<td align="left" valign="top"> | ||
<div class="form-label"> | ||
Id | ||
</div> | ||
</td> | ||
<td align="left" valign="top"> | ||
<input type="text" name="identifier" size="40"> | ||
</td> | ||
</tr> | ||
<tr> | ||
<td align="left" valign="top"> | ||
<div class="form-optional"> | ||
Type | ||
</div> | ||
</td> | ||
<td align="left" valign="top"> | ||
GopipIndex | ||
</td> | ||
</tr> | ||
<tr> | ||
<td align="left" valign="top"></td> | ||
<td align="left" valign="top"> | ||
<div class="form-element"> | ||
<input class="form-element" type="submit" name="submit" value=" Add "> | ||
</div> | ||
</td> | ||
</tr> | ||
</table> | ||
</form> | ||
|
||
<dtml-var manage_page_footer> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,123 @@ | ||
# -*- coding: utf-8 -*- | ||
from Acquisition import aq_base | ||
from App.special_dtml import DTMLFile | ||
from OFS.SimpleItem import SimpleItem | ||
from Products.CMFCore.interfaces import ISiteRoot | ||
from Products.PluginIndexes.interfaces import IPluggableIndex, ISortIndex | ||
from inspect import currentframe | ||
from logging import getLogger | ||
from zope.component import getUtility | ||
from zope.interface import implementer | ||
|
||
logger = getLogger(__name__) | ||
|
||
|
||
@implementer(IPluggableIndex) | ||
class StubIndex(SimpleItem): | ||
""" stub catalog index doing nothing """ | ||
|
||
def __init__(self, id, *args, **kw): | ||
self.id = id | ||
|
||
def getId(self): | ||
return self.id | ||
|
||
def getEntryForObject(self, *args, **kw): | ||
return [] | ||
|
||
def getIndexSourceNames(self): | ||
return [self.id] | ||
|
||
def index_object(self, *args, **kw): | ||
return 0 | ||
|
||
def unindex_object(self, *args, **kw): | ||
pass | ||
|
||
def _apply_index(self, *args, **kw): | ||
return None | ||
|
||
def numObjects(self): | ||
return 0 | ||
|
||
def clear(self): | ||
pass | ||
|
||
|
||
@implementer(ISortIndex) | ||
class GopipIndex(StubIndex): | ||
""" fake index for sorting against `getObjPositionInParent` """ | ||
|
||
meta_type = 'GopipIndex' | ||
manage_options = dict(label='Settings', action='manage_main'), | ||
|
||
keyForDocument = 42 | ||
|
||
def __init__(self, id, extra=None, caller=None): | ||
super(GopipIndex, self).__init__(id) | ||
self.catalog = aq_base(caller._catalog) | ||
|
||
def __len__(self): | ||
# with python 2.4 returning `sys.maxint` gives: | ||
# OverflowError: __len__() should return 0 <= outcome < 2**31 | ||
# so... | ||
return 2**31 - 1 | ||
|
||
def documentToKeyMap(self): | ||
# we need to get the containers in order to get the respective | ||
# positions of the search results, but before that we need those | ||
# results themselves. luckily this is only ever called from | ||
# `sortResults`, so we can get it form there. oh, and lurker | ||
# says this won't work in jython, though! :) | ||
rs = currentframe().f_back.f_locals['rs'] | ||
rids = {} | ||
items = [] | ||
containers = {} | ||
getpath = self.catalog.paths.get | ||
traverse = getUtility(ISiteRoot).unrestrictedTraverse | ||
for rid in rs: | ||
path = getpath(rid) | ||
parent, id = path.rsplit('/', 1) | ||
container = containers.get(parent) | ||
if container is None: | ||
containers[parent] = container = traverse(parent) | ||
rids[id] = rid # remember in case of single folder | ||
items.append((rid, container, id)) # or else for deferred lookup | ||
pos = {} | ||
if len(containers) == 1: | ||
# the usual "all from one folder" case can be optimized | ||
folder = list(containers.values())[0] | ||
if getattr(aq_base(folder), 'getOrdering', None): | ||
ids = folder.getOrdering().idsInOrder() | ||
else: | ||
# site root or old folders | ||
ids = folder.objectIds() | ||
for idx, id in enumerate(ids): | ||
rid = rids.get(id) | ||
if rid: | ||
pos[rid] = idx | ||
return pos | ||
else: | ||
# otherwise the entire map needs to be constructed... | ||
for rid, container, id in items: | ||
if getattr(aq_base(container), 'getObjectPosition', None): | ||
pos[rid] = container.getObjectPosition(id) | ||
else: | ||
# fallback for unordered folders | ||
pos[rid] = 0 | ||
return pos | ||
|
||
|
||
manage_addGopipForm = DTMLFile('dtml/addGopipIndex', globals()) | ||
|
||
|
||
def manage_addGopipIndex(self, identifier, REQUEST=None, RESPONSE=None, | ||
URL3=None): | ||
""" add a fake gopip index """ | ||
return self.manage_addIndex( | ||
identifier, | ||
'GopipIndex', | ||
REQUEST=REQUEST, | ||
RESPONSE=RESPONSE, | ||
URL1=URL3 | ||
) |