diff --git a/plone/app/discussion/conversation.py b/plone/app/discussion/conversation.py
index 6bc4437..19705a9 100644
--- a/plone/app/discussion/conversation.py
+++ b/plone/app/discussion/conversation.py
@@ -115,7 +115,9 @@ class Conversation(Persistent, Explicit):
if not reply_to in self._children:
self._children[reply_to] = LLSet()
self._children[reply_to].insert(id)
- notify(ObjectAddedEvent(comment, self, id))
+ # Notify that the object is added. The object must here be
+ # acquisition wrapped or the indexing will fail.
+ notify(ObjectAddedEvent(comment.__of__(self), self, id))
notify(ContainerModifiedEvent(self))
# Dict API
@@ -137,6 +139,9 @@ class Conversation(Persistent, Explicit):
def keys(self):
return self._comments.keys()
+ def getPhysicalPath(self):
+ return self.aq_parent.getPhysicalPath() + (self.id,)
+
# TODO: Update internal data structures when items added or removed
@implementer(IConversation)
diff --git a/plone/app/discussion/profiles/default/componentregistry.xml b/plone/app/discussion/profiles/default/componentregistry.xml
index 9764a7f..35f1a08 100644
--- a/plone/app/discussion/profiles/default/componentregistry.xml
+++ b/plone/app/discussion/profiles/default/componentregistry.xml
@@ -3,7 +3,7 @@
diff --git a/plone/app/discussion/profiles/default/toolset.xml b/plone/app/discussion/profiles/default/toolset.xml
new file mode 100644
index 0000000..0823a74
--- /dev/null
+++ b/plone/app/discussion/profiles/default/toolset.xml
@@ -0,0 +1,5 @@
+
+
+
+
\ No newline at end of file
diff --git a/plone/app/discussion/tests/test_api.py b/plone/app/discussion/tests/test_api.py
index 96d552b..dc2642c 100644
--- a/plone/app/discussion/tests/test_api.py
+++ b/plone/app/discussion/tests/test_api.py
@@ -29,7 +29,10 @@ class ConversationTest(TestCase):
# Create a conversation. In this case we doesn't assign it to an
# object, as we just want to check the Conversation object API.
conversation = IConversation(self.portal.doc1)
-
+ # Pretend that we have traversed to the comment by aq wrapping it.
+ # XXX implement traversal to commenting and change this:
+ conversation = conversation.__of__(self.portal.doc1)
+
# Add a comment. reply_to=0 means it's not a reply
comment = Comment(conversation=conversation, reply_to=0)
comment.title = 'Comment 1'
diff --git a/plone/app/discussion/tests/test_tool.py b/plone/app/discussion/tests/test_tool.py
index 730e143..7c7126f 100644
--- a/plone/app/discussion/tests/test_tool.py
+++ b/plone/app/discussion/tests/test_tool.py
@@ -29,6 +29,9 @@ class ToolTest(TestCase):
# Create a conversation. In this case we doesn't assign it to an
# object, as we just want to check the Conversation object API.
conversation = IConversation(self.portal.doc1)
+ # Pretend that we have traversed to the comment by aq wrapping it.
+ # XXX implement traversal to commenting and change this:
+ conversation = conversation.__of__(self.portal.doc1)
# Add a comment. reply_to=0 means it's not a reply
comment = Comment(conversation=conversation, reply_to=0)
@@ -39,8 +42,10 @@ class ToolTest(TestCase):
# Check that the comment got indexed in the tool:
tool = getUtility(ICommentingTool)
- comment = list(tool.search())[0]
- self.assertEquals(comment['text'], 'Comment text')
+ comment = list(tool.searchResults())
+ self.assert_(len(comment) == 1, "There is only one comment, but we got"
+ " %s results in the search" % len(comment))
+ self.assertEquals(comment[0].Title, 'Comment 1')
def test_suite():
diff --git a/plone/app/discussion/tool.py b/plone/app/discussion/tool.py
index 1c90d1b..c37a011 100644
--- a/plone/app/discussion/tool.py
+++ b/plone/app/discussion/tool.py
@@ -2,58 +2,65 @@ import time
from zope import interface
from zope.component import getUtility
-from BTrees.OOBTree import OOBTree, OOSet, intersection
-
-from interfaces import ICommentingTool
+from interfaces import ICommentingTool, IComment
# The commenting tool, which is a local utility
-class CommentingTool(object):
+from Products.CMFCore.utils import UniqueObject, getToolByName
+from OFS.SimpleItem import SimpleItem
+
+class CommentingTool(UniqueObject, SimpleItem):
+
interface.implements(ICommentingTool)
- def __init__(self):
- self._id2uid = OOBTree() # The comment ID to object UID
- self._id2text = OOBTree() # The text for a comment
- self._wfstate2id = OOBTree() # To search on wf states
- self._creator2id = OOBTree() # To search/order on creator ids
-
- def index(self, comment):
- # Store the object in the store:
- id = comment.comment_id
- self._id2uid[id] = comment.__parent__._parent_uid
- self._id2text[id] = comment.text
+ meta_type = 'plone.app.discussion tool'
+ id = 'portal_discussion'
+
+ def reindexObject(self, object):
+ """Remove from catalog.
+ """
+ catalog = getToolByName(self, 'portal_catalog')
+ return catalog.reindexObject(object)
+
+ indexObject = reindexObject
- # TODO
- ## Index on workflow state
- #wfstate = comment.getWorkflowState()
- #if not wfstate in self._wfstate2id:
- #self._wfstate2id[wfstate] = OOSet()
- #self._wfstate2id[wfstate].insert(id)
+ def unindexObject(self, object):
+ """Remove from catalog.
+ """
+ catalog = getToolByName(self, 'portal_catalog')
+ return catalog.unindexObject(object)
+
+ def uniqueValuesFor(self, name):
+ """ return unique values for FieldIndex name """
+ catalog = getToolByName(self, 'portal_catalog')
+ return catalog.uniqueValuesFor(name)
- # Index on creator
- creator = comment.creator
- if not creator in self._creator2id:
- self._creator2id[creator] = OOSet()
- self._creator2id[creator].insert(id)
-
- def search(self, creator=None):
- if creator is not None:
- # Get all replies for a certain object
- ids = self._creator2ids.get(creator, None)
- if ids is None:
- raise StopIteration
- else:
- ids = self._id2uid.keys()
-
- for id in ids:
- yield {'id': id,
- 'text': self._id2text[id]
- # TODO: More data + maybe brains or something?
- }
+ def searchResults(self, REQUEST=None, **kw):
+ """
+ Calls ZCatalog.searchResults with extra arguments that
+ limit the results to what the user is allowed to see.
+ """
+ catalog = getToolByName(self, 'portal_catalog')
+ object_provides = [IComment.__identifier__]
+ if 'object_provides' in kw:
+ kw_provides = kw['object_provides']
+ if isinstance(str, kw_provides):
+ object_provides.append(kw_provides)
+ else:
+ object_provides.extend(kw_provides)
+ if REQUEST is not None and 'object_provides' in REQUEST.form:
+ rq_provides = REQUEST.form['object_provides']
+ del REQUEST.form['object_provides']
+ if isinstance(str, rq_provides):
+ object_provides.append(rq_provides)
+ else:
+ object_provides.extend(rq_provides)
+ kw['object_provides'] = object_provides
+ return catalog.searchResults(REQUEST, **kw)
def object_added_handler(obj, event):
tool = getUtility(ICommentingTool)
- tool.index(obj)
+ tool.indexObject(obj)
def object_removed_handler(obj, event):
tool = getUtility(ICommentingTool)
- tool.unindex(obj)
+ tool.unindexObject(obj)