def test_clear_locks_remove_all_locks_on_the_object(self): lockable = ILockable(self.wrapper) lockable.lock() self.assertTrue(lockable.locked()) lockable.clear_locks() self.assertFalse(lockable.locked())
def test_lockinfo_tile(self): self.other_browser.open( self.pageURL + '/@@plone.app.standardtiles.lockinfo' ) self.assertIn('plone-lock-status', self.other_browser.contents) root = fromstring(self.other_browser.contents) nodes = root.xpath('//body//*[@id="plone-lock-status"]') self.assertEqual(len(nodes), 1) self.assertEqual(0, len(nodes[0].getchildren())) # Then lock the page: lockable = ILockable(self.page) lockable.lock() transaction.commit() # The tile will show them: self.other_browser.open( self.pageURL + '/@@plone.app.standardtiles.lockinfo' ) self.assertIn('plone-lock-status', self.other_browser.contents) root = fromstring(self.other_browser.contents) nodes = root.xpath('//body//*[@id="plone-lock-status"]') self.assertEqual(len(nodes), 1) self.assertGreaterEqual(len(nodes[0].getchildren()), 1)
def test_lockinfo_is_visible_for_lock_owner(self, browser): self.login(self.regular_user, browser=browser) browser.open(self.document) self.assertEquals([], info_messages()) lockable = ILockable(self.document) lockable.lock() browser.open(self.document) self.assertEquals([self.lock_message], info_messages())
def testLockedItem(self): membership_tool = getToolByName(self.folder, 'portal_membership') membership_tool.addMember('anotherMember', 'secret', ['Member'], []) locking = ILockable(self.folder.doc1) locking.lock() self.login('anotherMember') actions = self.menu.getMenuItems(self.folder.doc1, self.request) self.assertEqual(len(actions), 0)
def test_unlock_button_is_visible_for_manager(self, browser): self.login(self.regular_user, browser=browser) browser.open(self.document) self.assertEquals([], info_messages()) lockable = ILockable(self.document) lockable.lock() self.login(self.manager, browser=browser) browser.open(self.document) self.assertEquals([self.lock_message + self.unlock_message], info_messages())
def test_refresh_locks_update_locks_to_current_time(self): lockable = ILockable(self.wrapper) lockable.lock() with freeze(pytz.UTC.localize(datetime(2015, 03, 10, 12, 05))): lockable.refresh_lock() lock = Lock.query.one() self.assertEqual( pytz.UTC.localize(datetime(2015, 03, 10, 12, 05)), lock.time)
def test_unlock_does_not_check_if_lock_is_stealable_when_stealable_only_is_false(self): lockable = ILockable(self.wrapper) lockable.lock() # manually change lock creator lock = Lock.query.first() lock.creator = 'other-user' lockable.unlock() self.assertFalse(lockable.locked())
def begin(self, formname, fieldname, structure='false'): """Begin inline editing - find the widget for the given field name in the given form (looked up as a view on the context), then hide the block with the id '${fieldname}-display' and display an edit form in its place. If 'structure' is 'true' (a string), then the inline editable field will eventually permit HTML input to be rendered unescaped. """ context = aq_inner(self.context) request = aq_inner(self.request) form = getMultiAdapter((context, request), name=formname) form = form.__of__(context) if fieldname.startswith(form.prefix): fieldname = fieldname[len(form.prefix)+1:] formlib_field = form.form_fields[fieldname] widgets = formlib.setUpEditWidgets((formlib_field,), form.prefix, context, request, ignore_request=True) widget = widgets[fieldname] display_id = '%s-display' % fieldname form_id = '%s-form' % fieldname ksscore = self.getCommandSet('core') zopecommands = self.getCommandSet('zope') plonecommands = self.getCommandSet('plone') # lock the context (or issue warning) locking = ILockable(context, None) if locking: if not locking.can_safely_unlock(): selector = ksscore.getHtmlIdSelector('plone-lock-status') zopecommands.refreshViewlet(selector, 'plone.abovecontent', 'plone.lockinfo') plonecommands.refreshContentMenu() return else: # we are locking the content locking.lock() plonecommands.issuePortalMessage('') # hide the existing display field display_selector = ksscore.getHtmlIdSelector(display_id) ksscore.addClass(display_selector, 'hiddenStructure') # show the form form_html = self.form_template(widget=widget, form_id=form_id, fieldname=fieldname, structure=structure) ksscore.insertHTMLAfter(display_selector, form_html)
def test_unlock_does_not_check_if_lock_is_stealable_when_stealable_only_is_false( self): lockable = ILockable(self.wrapper) lockable.lock() # manually change lock creator lock = Lock.query.first() lock.creator = 'other-user' lockable.unlock() self.assertFalse(lockable.locked())
def testLockedItem(self): if self.is_dx: # dexterity has no locking ootb # see https://github.com/plone/plone.app.contenttypes/issues/140 return membership_tool = getToolByName(self.folder, 'portal_membership') membership_tool.addMember('anotherMember', 'secret', ['Member'], []) locking = ILockable(self.folder.doc1) locking.lock() login(self.portal, 'anotherMember') actions = self.menu.getMenuItems(self.folder.doc1, self.request) self.assertEqual(len(actions), 0)
def test_update_locked_object_with_token_succeeds(self): lockable = ILockable(self.doc) lockable.lock() transaction.commit() response = self.api_session.patch( "/", headers={"Lock-Token": lockable.lock_info()[0]["token"]}, json={"title": "New Title"}, ) transaction.commit() self.assertEqual(response.status_code, 204) self.assertEqual(self.doc.Title(), "New Title")
def testLockedItem(self): if self.is_dx: # dexterity has no locking ootb # see https://github.com/plone/plone.app.contenttypes/issues/140 return membership_tool = getToolByName(self.folder, 'portal_membership') membership_tool.addMember('anotherMember', 'secret', ['Member'], []) locking = ILockable(self.folder.doc1) locking.lock() login(self.portal, 'anotherMember') actions = self.menu.getMenuItems(self.folder.doc1, self.request) self.assertEqual(len(actions), 0)
def test_atct_not_lockable(self): portal = self.layer['portal'] setRoles(portal, TEST_USER_ID, ['Contributor']) portal.invokeFactory('Document', 'adoc', title='A title', description='Some description', text='Some text') doc = portal['adoc'] lockable = ILockable(doc) self.assertEqual(False, lockable.locked()) lockable.lock() self.assertEqual(False, lockable.locked())
def test_atct_not_lockable(self): portal = self.layer['portal'] setRoles(portal, TEST_USER_ID, ['Contributor']) portal.invokeFactory('Document', 'adoc', title='A title', description='Some description', text='Some text') doc = portal['adoc'] lockable = ILockable(doc) self.assertEqual(False, lockable.locked()) lockable.lock() self.assertEqual(False, lockable.locked())
def move_all_items_totarget(portal,sourcespace,targetspace,logger): ct = getToolByName(portal,'portal_catalog') logger.info("Moving items from %s to %s" % (sourcespace,targetspace,)) if sourcespace <> None: #impersonate owner of the space #print >> out, "impersonating owner of space: %s" % (sourcespace.Title(),) #impersonateOwner(portal,sourcespace) strPath = sourcespace.getPhysicalPath() strURL = "/".join(strPath) query = {'path': {'query': strURL},'portal_type':spacesdefaultaddablenonfolderishtypes} objects = [b.getObject() for b in ct(query)] logger.info("Moving %s items from space : %s" % (len(objects), sourcespace,)) for o in objects: if callable(o.id): o_id = o.id() else: o_id = o.id try: from plone.locking.interfaces import ILockable lockable = ILockable(o) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parentobject = o.getParentNode() cb = parentobject.manage_cutObjects(ids=[o_id]) targetspace.manage_pasteObjects(cb) if was_locked: lockable.lock() transaction.savepoint() except ComponentLookupError: pass #impersonateAdminUser(portal) query1 = query = {'path': {'query': "/".join(targetspace.getPhysicalPath()),'depth':1},'portal_type':spacesdefaultaddablenonfolderishtypes} movedobjects = ct(query1) logger.info("Moved %s items to space : %s" % (len(movedobjects), targetspace,))
def setId(self, value): """Sets the object id. """ if value != self.getId(): parent = aq_parent(aq_inner(self)) if parent is not None: # See Referenceable, keep refs on what is a move/rename self._v_cp_refs = 1 # We can't rename if the object is locked if HAS_LOCKING: lockable = ILockable(self) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parent.manage_renameObject(self.id, value) if was_locked: lockable.lock() else: parent.manage_renameObject(self.id, value) self._setId(value)
def _set_id(self, value): if not value: return context = aq_inner(self.context) parent = aq_parent(context) if parent is None: # Object hasn't been added to graph yet; just set directly context.id = value return new_id = INameChooser(parent).chooseName(value, context) if getattr(aq_base(context), 'id', None): transaction.savepoint() locked = False lockable = ILockable(context, None) if lockable is not None and lockable.locked(): locked = True lockable.unlock() parent.manage_renameObject(context.getId(), new_id) if locked: lockable.lock() else: context.id = new_id
def test_statictime_lockinfo(self): frozen_time = datetime(1950, 7, 31, 17, 30) statictime = StaticTime(modified=frozen_time) doc1 = self.create_document("doc1") alsoProvides(doc1, ITTWLockable) lockable = ILockable(doc1) lockable.lock() statictime.start() lock_infos = lockable.lock_info() self.assertEqual(1, len(lock_infos)) self.assertEqual(-612858600.0, lock_infos[0]["time"]) fake_datetimes = [lock_infos[0]["time"]] statictime.stop() lock_infos = lockable.lock_info() self.assertEqual(1, len(lock_infos)) self.assert_roughly_now(lock_infos[0]["time"]) real_datetimes = [lock_infos[0]["time"]] self.assert_of_same_type(fake_datetimes, real_datetimes)
def _set_id(self, value): if not value: return context = aq_inner(self.context) parent = aq_parent(context) if parent is None: # Object hasn't been added to graph yet; just set directly context.id = value return new_id = INameChooser(parent).chooseName(value, context) if getattr(aq_base(context), 'id', None): transaction.savepoint() locked = False lockable = ILockable(context, None) if lockable is not None and lockable.locked(): locked = True lockable.unlock() parent.manage_renameObject(context.getId(), new_id) if locked: lockable.lock() else: context.id = new_id
def setId(self, value): # Sets the object id. # avoid CopyError in OFS.CopySupport.manage_renameObject(), # see http://dev.plone.org/ticket/8338 value = value.strip() if value != self.getId(): parent = aq_parent(aq_inner(self)) if parent is not None: # See Referenceable, keep refs on what is a move/rename self._v_cp_refs = 1 # We can't rename if the object is locked if HAS_LOCKING: lockable = ILockable(self) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parent.manage_renameObject(self.id, value) if was_locked: lockable.lock() else: parent.manage_renameObject(self.id, value) self._setId(value)
def setId(self, value): # Sets the object id. # avoid CopyError in OFS.CopySupport.manage_renameObject(), # see http://dev.plone.org/ticket/8338 value = value.strip() if value != self.getId(): parent = aq_parent(aq_inner(self)) if parent is not None: # See Referenceable, keep refs on what is a move/rename self._v_cp_refs = 1 # We can't rename if the object is locked if HAS_LOCKING: lockable = ILockable(self) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parent.manage_renameObject(self.id, value) if was_locked: lockable.lock() else: parent.manage_renameObject(self.id, value) self._setId(value)
def replaceField(self, fieldname, templateId, macro, uid=None, target=None, edit=False): """ kss commands to replace the field value by the edit widget The edit parameter may be used if we are coming from something else than an edit view. """ ksscore = self.getCommandSet('core') zopecommands = self.getCommandSet('zope') plonecommands = self.getCommandSet('plone') instance = self._getFieldContext(uid) if edit: locking = ILockable(instance, None) if locking: if not locking.can_safely_unlock(): selector = ksscore.getHtmlIdSelector('plone-lock-status') zopecommands.refreshViewlet(selector, 'plone.abovecontent', 'plone.lockinfo') plonecommands.refreshContentMenu() return self.render() else: # were are locking the content locking.lock() plonecommands.issuePortalMessage('') html = self.renderEditField(fieldname, templateId, macro, uid) html = html.strip() field_id = target or "parent-fieldname-%s" % fieldname ksscore.replaceHTML(ksscore.getHtmlIdSelector(field_id), html) ksscore.focus("#%s .firstToFocus" % field_id) return self.render()
def lock(self): lockable = ILockable(self.context) if not lockable.locked(): lockable.lock()
def lockContext(context): lockable = ILockable(context) # Be quite forceful - we assume that we won't have gotten here unless # we had rights to do this. lockable.clear_locks() lockable.lock(ITERATE_LOCK, children=True)
def lockContext(context): lockable = ILockable(context) # Be quite forceful - we assume that we won't have gotten here unless # we had rights to do this. lockable.clear_locks() lockable.lock(ITERATE_LOCK, children=True)
def lockOnEditBegins(obj, event): """Lock the object when a user start working on the object """ lockable = ILockable(obj) if not lockable.locked(): lockable.lock()
def migrateFolderToMemberSpace(portal,memberfolder,logger): from ubify.coretypes.content import MemberSpace new_base_folder = { 'MemberSpace' : MemberSpace, } ct = getToolByName(portal,'portal_catalog') strURL = "/".join(memberfolder.getPhysicalPath()) query = {'path':{'query':strURL},'portal_type':('StatuslogItem',)} statusmessages = [b.getObject() for b in ct(query)] logger.info("Count of status messages for %s are : %s" % (memberfolder.Title(),len(statusmessages),)) if memberfolder <> None: from plone.locking.interfaces import ILockable lockable = ILockable(memberfolder) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parent_member = memberfolder.getParentNode() #rename old user folder and create new memberspace object and move status log items to #newly created userfolder and Delete old folder. old_id = memberfolder.getId() new_id = old_id + '_old' try: parent_member.manage_renameObject(old_id,new_id) except ComponentLookupError: pass impersonateOwner(portal,memberfolder) new_memberfolder = getOrCreateType(portal,parent_member,old_id,"MemberSpace") if new_memberfolder <> None and new_memberfolder.title == '': new_memberfolder.title = memberfolder.Title() new_memberfolder.reindexObject() impersonateAdminUser(portal) for message in statusmessages: if callable(message.id): o_id = message.id() else: o_id = message.id try: from plone.locking.interfaces import ILockable lockable = ILockable(message) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parentItem = message.getParentNode() cb = parentItem.manage_cutObjects(ids = [o_id]) new_memberfolder.manage_pasteObjects(cb) if was_locked: lockable.lock() transaction.savepoint() except ComponentLookupError: pass #delete statuslog folder query1 = {'path':{'query':"/".join(memberfolder.getPhysicalPath())},'portal_type':('StatuslogFolder',)} logFolders = [b.getObject() for b in ct(query1)] for lFolder in logFolders: if callable(lFolder.id): o_id = lFolder.id() else: o_id = lFolder.id try: from plone.locking.interfaces import ILockable lockable = ILockable(lFolder) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parentItem = lFolder.getParentNode() parentItem.manage_delObjects(ids=[o_id]) if was_locked: lockable.lock() transaction.savepoint() except ComponentLookupError: pass logger.info("Deleted member status log folder for %s" % (parentItem.Title(),)) try: from plone.locking.interfaces import ILockable lockable = ILockable(memberfolder) was_locked = False if lockable.locked(): was_locked = True lockable.unlock() parentItem = memberfolder.getParentNode() parentItem.manage_delObjects(ids=[memberfolder.getId()]) if was_locked: lockable.lock() transaction.savepoint() except ComponentLookupError: pass new_memberfolder.reindexObject() statusmessages = [b.getObject() for b in ct(query)] logger.info("After Migration Count of status messages for %s are : %s" % (memberfolder.Title(),len(statusmessages),))
def test_lock_use_model_class_name_as_object_type(self): lockable = ILockable(self.wrapper) lockable.lock() lock = Lock.query.first() self.assertEqual(u'Meeting', lock.object_type)
def test_lock_token_contains_object_type_and_is_separated_with_a_colon(self): lockable = ILockable(self.wrapper) lockable.lock() lock = Lock.query.first() self.assertEqual(u'Meeting:1', lock.token)
def test_locked(self): lockable = ILockable(self.wrapper) lockable.lock() self.assertTrue(lockable.locked())
def lock(self): lockable = ILockable(self.context) if not lockable.locked(): lockable.lock()
def test_unlock_delete_lock_if_a_lock_existsts(self): lockable = ILockable(self.wrapper) lockable.lock() lockable.unlock() self.assertFalse(lockable.locked()) self.assertEquals(0, Lock.query.count())
def lockOnEditBegins(obj, event): """Lock the object when a user start working on the object """ lockable = ILockable(obj) if not lockable.locked(): lockable.lock()