def __call__(self): self.errors = {} transition = self.selected_transition id = transition.id if self.request.get('form.actions.delete', False) == 'Delete': self.authorize() #delete any associated rules also. self.actions.delete_rule_for(self.selected_transition) self.selected_workflow.transitions.deleteTransitions([id]) # now check if we have any dangling references for state in self.available_states: if id in state.transitions: transitions = list(state.transitions) transitions.remove(id) state.transitions = tuple(transitions) msg = _( 'msg_transition_deleted', default=u'"${id}" transition has been successfully deleted.', mapping={'id': id}) return self.handle_response(message=msg) elif self.request.get('form.actions.cancel', False) == 'Cancel': msg = _( 'msg_deleting_canceled', default=u'Deleting the "${id}" transition has been canceled.', mapping={'id': id}) return self.handle_response(message=msg) else: return self.handle_response(tmpl=self.template)
def __call__(self): self.errors = {} transition = self.selected_transition transition_id = transition.id if self.request.get('form.actions.delete', False): self.authorize() #delete any associated rules also. self.actions.delete_rule_for(self.selected_transition) self.selected_workflow.transitions.deleteTransitions([transition_id]) # now check if we have any dangling references for state in self.available_states: if transition_id in state.transitions: transitions = list(state.transitions) transitions.remove(transition_id) state.transitions = tuple(transitions) msg = _('msg_transition_deleted', default=u'"${id}" transition has been successfully deleted.', mapping={'id': transition_id}) return self.handle_response(message=msg) elif self.request.get('form.actions.cancel', False) == 'Cancel': msg = _('msg_deleting_canceled', default=u'Deleting the "${id}" transition has been canceled.', mapping={'id': transition_id}) return self.handle_response(message=msg) else: return self.handle_response(tmpl=self.template)
def not_empty(form, name): v = form.request.get(name, '').strip() if v is None or (type(v) in (str, unicode) and \ len(v) == 0) or (type(v) in (tuple, set, list) and len(v) == 0): form.errors[name] = _(u'This field is required.') return v
def not_empty(form, name): v = form.request.get(name, '').strip() if v is None or (type(v) in (str, unicode) and \ len(v) == 0) or (type(v) in (tuple, set, list) and len(v) == 0): form.errors[name] = translate(_(u'This field is required.'), context=form.request) return v
def id(form, name, container): id = form.request.get(name, '').strip() putils = getToolByName(form.context, 'plone_utils') id = generate_id(putils.normalizeString(id), container.objectIds()) try: checkValidId(container, id) except: form.errors[name] = _(u'Invalid workflow name. Please try another.') return id
def __call__(self): if self.request.get('form.actions.confirm', False): self.authorize() count = self.portal_workflow._recursiveUpdateRoleMappings( self.portal, {self.selected_workflow.id: self.selected_workflow}) return self.handle_response( message=_('msg_updated_objects', default="Updated ${count} objects.", mapping={'count': count})) else: return self.handle_response(tmpl=self.template)
def id(form, name, container): elt_id = form.request.get(name, '').strip() putils = getToolByName(form.context, 'plone_utils') elt_id = generate_id(putils.normalizeString(unicode(elt_id, encoding='utf-8')), container.objectIds()) try: checkValidId(container, elt_id) except: form.errors[name] = translate(_(u'Invalid name. Please try another.'), context=form.request) return elt_id
def __call__(self): self.errors = {} state = self.selected_state transitions = self.available_transitions state_id = state.id self.is_using_state = False for transition in transitions: if transition.new_state_id == state_id: self.is_using_state = True break if self.request.get('form.actions.delete', False): self.authorize() if self.is_using_state: replacement = self.request.get('replacement-state', self.available_states[0].id) for transition in self.available_transitions: if state_id == transition.new_state_id: transition.new_state_id = replacement chains = self.portal_workflow.listChainOverrides() types_ids = [c[0] for c in chains if self.selected_workflow.id in c[1]] remap_workflow(self.context, types_ids, (self.selected_workflow.id, ), {state_id: replacement}) self.selected_workflow.states.deleteStates([state_id]) return self.handle_response( message=_('msg_state_deleted', default=u'"${id}" state has been successfully deleted.', mapping={'id': state_id})) elif self.request.get('form.actions.cancel', False) == 'Cancel': return self.handle_response( message=_('msg_state_deletion_canceled', default=u'Deleting the "${id}" state has been canceled.', mapping={'id': state_id})) else: return self.handle_response(tmpl=self.template)
def id(form, name, container): elt_id = form.request.get(name, '').strip() putils = getToolByName(form.context, 'plone_utils') elt_id = generate_id( putils.normalizeString(unicode(elt_id, encoding='utf-8')), container.objectIds()) try: checkValidId(container, elt_id) except: form.errors[name] = translate(_(u'Invalid name. Please try another.'), context=form.request) return elt_id
def __call__(self): self.errors = {} if not self.request.get('form.actions.add', False): return self.handle_response(tmpl=self.template) else: self.authorize() transition = validators.not_empty(self, 'transition-name') transition_id = validators.id(self, 'transition-name', self.selected_workflow.transitions) if not self.errors: # must have transition to go on workflow = self.selected_workflow workflow.transitions.addTransition(transition_id) new_transition = workflow.transitions[transition_id] clone_of_id = self.request.get('clone-from-transition') new_transition.title = transition if clone_of_id: # manage_copy|paste|clone doesn't work? clone_transition(new_transition, workflow.transitions[clone_of_id]) else: new_transition.actbox_name = transition new_transition.actbox_url = \ "%(content_url)s/content_status_modify?workflow_action=" + transition_id new_transition.actbox_category = 'workflow' new_transition.script_name = '' new_transition.after_script_name = '' # if added from state screen referenced_state = self.request.get('referenced-state', None) if referenced_state: state = self.selected_workflow.states[referenced_state] state.transitions += (new_transition.id, ) return self.handle_response(message=_( 'msg_transition_created', default= u'"${transition_id}" transition successfully created.', mapping={'transition_id': new_transition.id}), slideto=True, transition=new_transition) else: return self.handle_response(tmpl=self.template, justdoerrors=True)
def managed_permissions(wfid=None): if wfid is None: return [] site = getSite() wtool = getToolByName(site, 'portal_workflow') wf = wtool.get(wfid) items = [] for permission in wf.permissions: data = {} data['perm'] = permission data['name'] = _(permission) data['description'] = u'' items.append(data) return items
def __call__(self): self.errors = {} if not self.request.get('form.actions.add', False): return self.handle_response(tmpl=self.template) else: self.authorize() transition = validators.not_empty(self, 'transition-name') transition_id = validators.id(self, 'transition-name', self.selected_workflow.transitions) if not self.errors: # must have transition to go on workflow = self.selected_workflow workflow.transitions.addTransition(transition_id) new_transition = workflow.transitions[transition_id] clone_of_id = self.request.get('clone-from-transition') new_transition.title = transition if clone_of_id: # manage_copy|paste|clone doesn't work? clone_transition(new_transition, workflow.transitions[clone_of_id]) else: new_transition.actbox_name = transition new_transition.actbox_url = \ "%(content_url)s/content_status_modify?workflow_action=" + transition_id new_transition.actbox_category = 'workflow' new_transition.script_name = '' new_transition.after_script_name = '' # if added from state screen referenced_state = self.request.get('referenced-state', None) if referenced_state: state = self.selected_workflow.states[referenced_state] state.transitions += (new_transition.id, ) return self.handle_response( message=_('msg_transition_created', default=u'"${transition_id}" transition successfully created.', mapping={'transition_id': new_transition.id}), slideto=True, transition=new_transition) else: return self.handle_response(tmpl=self.template, justdoerrors=True)
def __call__(self): self.errors = {} if not self.request.get('form.actions.add', False): return self.handle_response(tmpl=self.template) else: self.authorize() state = validators.not_empty(self, 'state-name') state_id = validators.id(self, 'state-name', self.selected_workflow.states) if not self.errors: # must have state to go on workflow = self.selected_workflow workflow.states.addState(state_id) new_state = workflow.states[state_id] clone_of_id = self.request.get('clone-from-state') if clone_of_id: # manage_copy|paste|clone doesn't work? clone_state(new_state, workflow.states[clone_of_id]) new_state.title = state # if added from transition screen referenced_transition = self.request.get( 'referenced-transition', None) if referenced_transition: new_state.transitions = \ new_state.transitions + (referenced_transition, ) msg = _('msg_state_created', default=u'"${state_id}" state successfully created.', mapping={'state_id': new_state.id}) return self.handle_response( message=msg, slideto=True, state=new_state) else: return self.handle_response(tmpl=self.template, justdoerrors=True)
def __call__(self): self.errors = {} self.can_delete = len(self.assigned_types) == 0 if not self.can_delete: return self.handle_response( tmpl=self.template, message=_(u'You can not delete this workflow until no content ' u'types are specified to use this workflow.')) elif self.request.get('form.actions.delete', False) == 'Delete': self.authorize() #delete all rules also. for transition in self.available_transitions: self.actions.delete_rule_for(transition) self.portal_workflow.manage_delObjects([self.selected_workflow.id]) return self.handle_response(redirect=True) elif self.request.get('form.actions.cancel', False) == 'Cancel': return self.handle_response() else: return self.handle_response(tmpl=self.template)
class Base(BrowserView): """ We have so many different page templates so that they can be rendered independently of each of for ajax calls. It's also nice to break of the huge template files too. Form Action Guidelines... You can provide an ajax parameters set to true to specify that the form is being handled by ajax. If this is not specified, the form will be redirected to the base workflow form. Form validation will also be done. If the request is an ajax one, the validation will be sent back, if everything went well and validated, it'll send a {'status' : 'ok'} back. """ errors = {} next_id = None # the id of the next workflow to be viewed label = _(u'Workflow Manager') description = _(u'Manage your custom workflows TTW.') wrapped_dialog_template = ViewPageTemplateFile( 'templates/wrapped-dialog.pt') managed_permissions = managed_permissions @property @memoize def actions(self): return ActionManager() @property @memoize def allowed_guard_permissions(self): return allowed_guard_permissions @property @memoize def portal(self): utool = getToolByName(self.context, 'portal_url') return utool.getPortalObject() @property @memoize def portal_workflow(self): return getToolByName(self.context, 'portal_workflow') @property @memoize def available_workflows(self): return [ w for w in self.workflows if w.id not in plone_shipped_workflows ] @property @memoize def workflows(self): pw = self.portal_workflow ids = pw.portal_workflow.listWorkflows() return [pw[id] for id in sorted(ids)] @property @memoize def selected_workflow(self): selected = self.request.get('selected-workflow') if type(selected) == list and len(selected) > 0: selected = selected[0] if selected and selected in self.portal_workflow.objectIds(): return self.portal_workflow[selected] @property @memoize def selected_state(self): state = self.request.get('selected-state') if type(state) == list and len(state) > 0: state = state[0] if state in self.selected_workflow.states.objectIds(): return self.selected_workflow.states[state] @property @memoize def selected_transition(self): transition = self.request.get('selected-transition') if type(transition) == list and len(transition) > 0: transition = transition[0] if transition in self.selected_workflow.transitions.objectIds(): return self.selected_workflow.transitions[transition] @property @memoize def available_states(self): wf = self.selected_workflow if wf is not None: states = [wf.states[state] for state in wf.states.objectIds()] states.sort(lambda x, y: cmp(x.title.lower(), y.title.lower())) return states else: return [] @property @memoize def available_transitions(self): wf = self.selected_workflow if wf is not None: transitions = wf.transitions.objectIds() transitions = [wf.transitions[t] for t in transitions] transitions.sort( lambda x, y: cmp(x.title.lower(), y.title.lower())) return transitions else: return [] def authorize(self): authenticator = getMultiAdapter((self.context, self.request), name=u"authenticator") if not authenticator.verify(): raise Unauthorized def render_transitions_template(self): return self.workflow_transitions_template( available_states=self.available_states, available_transitions=self.available_transitions) def get_transition(self, id): if id in self.selected_workflow.transitions.objectIds(): return self.selected_workflow.transitions[id] @property @memoize def assignable_types(self): vocab_factory = getUtility( IVocabularyFactory, name="plone.app.vocabularies.ReallyUserFriendlyTypes") types = [] for v in vocab_factory(self.context): types.append(dict(id=v.value, title=v.title)) def _key(v): return v['title'] types.sort(key=_key) return types @property def assigned_types(self): types = [] try: chain = self.portal_workflow.listChainOverrides() nondefault = [info[0] for info in chain] for type_ in self.assignable_types: if type_['id'] in nondefault: chain = self.portal_workflow.getChainForPortalType( type_['id']) if len(chain) > 0 and chain[0] == \ self.selected_workflow.id: types.append(type_) except: pass return types def get_transition_list(self, state): transitions = state.getTransitions() return [t for t in self.available_transitions if t.id in transitions] def get_state(self, id): if id in self.selected_workflow.states.objectIds(): return self.selected_workflow.states[id] else: return None @property @memoize def next_url(self): return self.get_url() def get_url(self, relative=None, workflow=None, transition=None, state=None, **kwargs): url = self.context.absolute_url() if relative: url = url + '/' + relative.lstrip('/') else: url = url + '/@@workflowmanager' params = {} if not workflow: if self.next_id: params['selected-workflow'] = self.next_id elif self.selected_workflow: params['selected-workflow'] = self.selected_workflow.id else: params['selected-workflow'] = workflow.id if transition: params['selected-transition'] = transition.id if state: params['selected-state'] = state.id params.update(kwargs) if len(params) > 0: url = url + "?" + urlencode(params) return url @memoize def getGroups(self): gf = aq_get(self.context, '__allow_groups__', None, 1) if gf is None: return () try: groups = gf.searchGroups() except AttributeError: return () else: return groups @property @memoize def context_state(self): return getMultiAdapter((self.context, self.request), name=u'plone_portal_state') def wrap_template(self, tmpl, **options): ajax = self.request.get('ajax', None) if ajax: return tmpl(options=options) else: return self.wrapped_dialog_template(content=tmpl, options=options) @property def has_graphviz(self): return HAS_GRAPHVIZ def handle_response(self, message=None, tmpl=None, redirect=None, load=None, justdoerrors=False, slideto=False, **kwargs): ajax = self.request.get('ajax', None) status = {'status': 'ok'} if len(self.errors) > 0: status['status'] = 'error' if ajax: status['errors'] = [[k, v] for k, v in self.errors.items()] else: status['errors'] = self.errors elif redirect: status['status'] = 'redirect' if type(redirect) in (str, unicode): status['location'] = redirect else: status['location'] = self.next_url elif slideto: status['status'] = 'slideto' # either state or transition here... status['url'] = self.get_url(**kwargs) elif load: status['status'] = 'load' status['url'] = load else: status['status'] = 'ok' if message: status['message'] = zope.i18n.translate(message) if ajax: self.request.response.setHeader('X-Theme-Disabled', 'True') if tmpl and not justdoerrors: return tmpl.__of__(self.context)(**kwargs) else: return json.dumps(status) else: if redirect: return self.request.response.redirect(status['location']) elif status['status'] == 'load': return self.request.response.redirect(status['url']) elif tmpl: return self.wrap_template(tmpl, **kwargs) else: return self.request.response.redirect(self.next_url)
from plone.app.workflowmanager import WMMessageFactory as _ managed_permissions = [ {"perm": _(u"Add portal content"), "name": _(u"Add"), "description": _(u"Add content in this container.")}, { "perm": _(u"Modify portal content"), "name": _(u"Edit"), "description": _(u"Allows changing the content of an item."), }, { "perm": _(u"View"), "name": _(u"View"), "description": _(u"Not only means view HTML, but also FTP, WebDAV " u"and other forms of access."), }, {"perm": _(u"Review portal content"), "name": _(u"Review"), "description": _(u"Allowed to review the content.")}, {"perm": _(u"Change portal events"), "name": _(u"Change Events"), "description": _(u"Allow to update events")}, { "perm": _(u"List folder contents"), "name": _(u"List"), "description": _( u"List the contents of a folder. This doesn't check " u"if you have access to view the actual object listed." ), }, { "perm": _(u"Access contents information"), "name": _(u"Access"), "description": _( u"Allow access to content without necessarily viewing " u"the object. For example, in a list of results." ), },