From 920392d1244f91919ce5e4a838fbb6d57ad91d31 Mon Sep 17 00:00:00 2001 From: Andrea Cecchi Date: Mon, 3 Mar 2014 15:12:16 +0100 Subject: [PATCH] added Delete comments permission to manage comments deletion --- CHANGES.rst | 6 +- plone/app/discussion/browser/comments.py | 11 +-- plone/app/discussion/browser/configure.zcml | 2 +- plone/app/discussion/browser/controlpanel.py | 2 - plone/app/discussion/browser/moderation.py | 11 +-- plone/app/discussion/interfaces.py | 11 --- plone/app/discussion/permissions.zcml | 4 + .../discussion/profiles/default/rolemap.xml | 9 ++- plone/app/discussion/testing.py | 10 +++ .../tests/functional_test_comments.txt | 76 ++++--------------- 10 files changed, 43 insertions(+), 99 deletions(-) diff --git a/CHANGES.rst b/CHANGES.rst index 9cdfec9..9cfe383 100644 --- a/CHANGES.rst +++ b/CHANGES.rst @@ -25,12 +25,12 @@ Changelog - Fix ownership of comments. [toutpt] -- Provide 'delete own comments' as a configurable option - [gyst] - - Make comments editable. [pjstevns, gyst] +- Provide 'Delete comments' permission to handle comments deletion + [cekk] + 2.2.10 (2013-09-24) ------------------- diff --git a/plone/app/discussion/browser/comments.py b/plone/app/discussion/browser/comments.py index d58dfb7..0661654 100644 --- a/plone/app/discussion/browser/comments.py +++ b/plone/app/discussion/browser/comments.py @@ -312,18 +312,9 @@ class CommentsViewlet(ViewletBase): """By default requires 'Review comments'. If 'delete own comments' is enabled, requires 'Edit comments'. """ - if self.is_delete_own_comment_allowed(): - permission = 'Edit comments' - else: - permission = 'Review comments' - return getSecurityManager().checkPermission(permission, + return getSecurityManager().checkPermission('Delete comments', aq_inner(reply)) - def is_delete_own_comment_allowed(self): - registry = queryUtility(IRegistry) - settings = registry.forInterface(IDiscussionSettings, check=False) - return settings.delete_own_comment_enabled - def is_discussion_allowed(self): context = aq_inner(self.context) return context.restrictedTraverse('@@conversation_view').enabled() diff --git a/plone/app/discussion/browser/configure.zcml b/plone/app/discussion/browser/configure.zcml index facb643..427395d 100644 --- a/plone/app/discussion/browser/configure.zcml +++ b/plone/app/discussion/browser/configure.zcml @@ -88,7 +88,7 @@ name="moderate-delete-comment" layer="..interfaces.IDiscussionLayer" class=".moderation.DeleteComment" - permission="zope2.DeleteObjects" + permission="plone.app.discussion.DeleteComments" /> diff --git a/plone/app/discussion/browser/controlpanel.py b/plone/app/discussion/browser/controlpanel.py index 84ded37..822ca2b 100644 --- a/plone/app/discussion/browser/controlpanel.py +++ b/plone/app/discussion/browser/controlpanel.py @@ -54,8 +54,6 @@ class DiscussionSettingsEditForm(controlpanel.RegistryEditForm): SingleCheckBoxFieldWidget self.fields['edit_comment_enabled'].widgetFactory = \ SingleCheckBoxFieldWidget - self.fields['delete_own_comment_enabled'].widgetFactory = \ - SingleCheckBoxFieldWidget self.fields['anonymous_comments'].widgetFactory = \ SingleCheckBoxFieldWidget self.fields['show_commenter_image'].widgetFactory = \ diff --git a/plone/app/discussion/browser/moderation.py b/plone/app/discussion/browser/moderation.py index 0324a43..66f235b 100644 --- a/plone/app/discussion/browser/moderation.py +++ b/plone/app/discussion/browser/moderation.py @@ -117,18 +117,9 @@ class DeleteComment(BrowserView): """By default requires 'Review comments'. If 'delete own comments' is enabled, requires 'Edit comments'. """ - if self.is_delete_own_comment_allowed(): - permission = 'Edit comments' - else: - permission = 'Review comments' - return getSecurityManager().checkPermission(permission, + return getSecurityManager().checkPermission('Delete comments', aq_inner(reply)) - def is_delete_own_comment_allowed(self): - registry = queryUtility(IRegistry) - settings = registry.forInterface(IDiscussionSettings, check=False) - return settings.delete_own_comment_enabled - class PublishComment(BrowserView): """Publish a comment. diff --git a/plone/app/discussion/interfaces.py b/plone/app/discussion/interfaces.py index 70b9f4b..e8ff537 100644 --- a/plone/app/discussion/interfaces.py +++ b/plone/app/discussion/interfaces.py @@ -253,17 +253,6 @@ class IDiscussionSettings(Interface): default=False, ) - delete_own_comment_enabled = schema.Bool( - title=_(u"label_delete_own_comment_enabled", - default="Allow users to delete their own comment threads"), - description=_(u"help_edit_comment_enabled", - default=u"If selected, users may delete their own " - "comments -> AND the whole reply thread below that " - "comment!"), - required=False, - default=False, - ) - text_transform = schema.Choice( title=_(u"label_text_transform", default="Comment text transform"), diff --git a/plone/app/discussion/permissions.zcml b/plone/app/discussion/permissions.zcml index dd71e63..97c6782 100644 --- a/plone/app/discussion/permissions.zcml +++ b/plone/app/discussion/permissions.zcml @@ -14,5 +14,9 @@ title="Edit comments" /> + diff --git a/plone/app/discussion/profiles/default/rolemap.xml b/plone/app/discussion/profiles/default/rolemap.xml index 8e8b019..83a67fc 100644 --- a/plone/app/discussion/profiles/default/rolemap.xml +++ b/plone/app/discussion/profiles/default/rolemap.xml @@ -3,15 +3,20 @@ - + - + + + + + + diff --git a/plone/app/discussion/testing.py b/plone/app/discussion/testing.py index cf1066c..6a52a9b 100644 --- a/plone/app/discussion/testing.py +++ b/plone/app/discussion/testing.py @@ -28,6 +28,8 @@ class PloneAppDiscussion(PloneSandboxLayer): USER_WITH_FULLNAME_PASSWORD = 'secret' MANAGER_USER_NAME = 'manager' MANAGER_USER_PASSWORD = 'secret' + REVIEWER_NAME = 'reviewer' + REVIEWER_PASSWORD = 'secret' def setUpZope(self, app, configurationContext): # Load ZCML @@ -60,7 +62,15 @@ class PloneAppDiscussion(PloneSandboxLayer): ['Member'], [], ) + acl_users.userFolderAddUser( + self.REVIEWER_NAME, + self.REVIEWER_PASSWORD, + ['Member'], + [], + ) mtool = getToolByName(portal, 'portal_membership', None) + gtool = getToolByName(portal, 'portal_groups', None) + gtool.addPrincipalToGroup(self.REVIEWER_NAME, 'Reviewers') mtool.addMember('jim', 'Jim', ['Member'], []) mtool.getMemberById('jim').setMemberProperties( {"fullname": 'Jim Fult\xc3\xb8rn'}) diff --git a/plone/app/discussion/tests/functional_test_comments.txt b/plone/app/discussion/tests/functional_test_comments.txt index a31ed48..180b2b5 100644 --- a/plone/app/discussion/tests/functional_test_comments.txt +++ b/plone/app/discussion/tests/functional_test_comments.txt @@ -32,6 +32,7 @@ you're not logged in:: >>> unprivileged_browser = Browser(app) >>> browser_member = Browser(app) >>> browser_user = Browser(app) + >>> browser_reviewer = Browser(app) Make sure we have a test user from the layer and it uses fancy characters: @@ -143,7 +144,6 @@ Post a comment as member ------------------------ Login as user 'jim'. - >>> browser_member.open(portal_url + '/login_form') >>> browser_member.getControl(name='__ac_name').value = 'jim' >>> browser_member.getControl(name='__ac_password').value = 'secret' @@ -320,8 +320,8 @@ But Anon can see the edited comment. True -Deleting existing comments | 'delete own comments' disabled ------------------------------------------------------------ +Deleting existing comments | 'Delete comments' permission +---------------------------------------------------------- Anonymous cannot delete comments @@ -329,7 +329,7 @@ Anonymous cannot delete comments >>> 'form.button.Delete' in unprivileged_browser.contents False -A member cannot delete his own comments, unless this is explicitly enabled (see later) +A member cannot delete his own comments if he can't review or he isn't a Site Administrator >>> browser_member.open(urldoc1) >>> 'form.button.Delete' in browser_member.contents @@ -360,7 +360,6 @@ The comment is still there >>> comment_id in unprivileged_browser.contents True - A Member cannot delete even his own comment by hitting the delete url directly. Extract the member comment id from the admin browser @@ -387,10 +386,17 @@ The comment is still there >>> 'Comment from Jim' in browser_member.contents True -Admin, who hase 'review comments' permission, can delete comments +Now login as user 'reviewer' - >>> browser.open(urldoc1) - >>> form = browser.getForm(name='delete', index=0) + >>> browser_reviewer.open(portal_url + '/login_form') + >>> browser_reviewer.getControl(name='__ac_name').value = 'reviewer' + >>> browser_reviewer.getControl(name='__ac_password').value = 'secret' + >>> browser_reviewer.getControl(name='submit').click() + +Admin and who have 'Delete comments' permission (reviewers for example), can delete comments + + >>> browser_reviewer.open(urldoc1) + >>> form = browser_reviewer.getForm(name='delete', index=0) >>> '@@moderate-delete-comment' in form.action True @@ -406,58 +412,8 @@ We'll just catch that and check the result later. Returning to the document we find the deleted comment is indeed gone - >>> browser.open(urldoc1) - >>> comment_id in browser.contents - False - - -Deleting existing comments | 'delete own comments' ENABLED ----------------------------------------------------------- - -Enable deletion of own comments - - >>> from zope.component import queryUtility - >>> from plone.registry.interfaces import IRegistry - >>> from plone.app.discussion.interfaces import IDiscussionSettings - >>> registry = queryUtility(IRegistry) - >>> settings = registry.forInterface(IDiscussionSettings) - >>> settings.delete_own_comment_enabled = True - - >>> import transaction - >>> transaction.commit() - -Anonymous still cannot delete comments - - >>> unprivileged_browser.open(urldoc1) - >>> 'form.button.Delete' in unprivileged_browser.contents - False - -A member can now delete his own comments - - >>> browser_member.open(urldoc1) - >>> 'form.button.Delete' in browser_member.contents - True - - >>> form = browser_member.getForm(name='delete', index=0) - >>> '@@moderate-delete-comment' in form.action - True - - >>> comment_id = form.action.split('/')[-2] - -Submitting the form runs into a testbrowser notFoundException. -We'll just catch that and check the result later. - - >>> try: - ... form.submit() - ... except: - ... pass - -Returning to the document we find the deleted comment is indeed gone - - >>> browser_member.open(urldoc1) - >>> comment_id in browser_member.contents - False - >>> 'Comment from Jim' in browser_member.contents + >>> browser_reviewer.open(urldoc1) + >>> comment_id in browser_reviewer.contents False