Action: cosa sono e come si creano

cancel
Showing results for 
Search instead for 
Did you mean: 
ventus85
Member II

Action: cosa sono e come si creano

Salve a tutti!

Vorrei sapere se ho capito bene cosa è un action e come viene creata una nuova, se mi date qualche conferma o mi correggete, ne sarò lieta.

In generale un'action (azione) è un qualcosa che l'utente può fare per esempio per un contenuto (per esempio un aggiornamento, un'eliminazione), sono come delle piccole unità di lavoro o componenti che possono essere configurate e possono essere eseguite anche runtime.
Un'azione consiste di una classe Action Executer e dalla dichiazione dei bean associati.
Analizzo per primo proprio la classe Action executer. Essa ha un metodo executeImpl che, per esempio, può prendere dei valori dei parametri e chiamare il NodeService.
Nella pratica contiene l'implementazione dell'azione.
Estende ActionExecuterAbstractBase.

public class TestExecuter extends  ActionExecuterAbstractBase{
   private NodeService nodeService;

   protected void executeImpl(Action action, NodeRef actionedUponNodeRef) {
       NodeRef nodeRef = (NodeRef) action.getParameterValue(PARAM_NOME);
       nodeService.XXX
       //… }
dove con XXX può fare qualcosa, tipo un get, un set o un'altra cosa.

Esiste poi una classe per il bean che, traducendo dall'inglese, gestisce la vista (view) per la configurazione dell'azione.

E' necessario poi fare la dichiarazione del bean.

<beans>
   <bean id="XXX" class="com.action.executer.TestExecuter" parent="actionexecuter">
       <property name="nodeService">
           <ref bean="NodeService" />
       </property>
   </bean>
   <bean id="extension.actionResourceBundles" parent="actionResourceBundles">
       <property name="resourceBundles">
           <list>
               <value>alfresco.extension.YYYY</value>
           </list>
       </property>
   </bean>
</beans>

Successivamente è necessario creare un resource bundle. Si crea un file che va salvato nella cartella alfresco/XXXche viene chiamato per esempio alfresco.extension.YYYY.properties. Il nome e il percorso sono corrispondenti a quelli dichiarati nel passaggio precedente.

Non ho capito bene il ruolo del resource bundle e se poi dobbiamo dichiarare altre cose.
Esiste qualche esempio completo delle classi che mi può aiutare a capire? Chiedo questo perchè dalle guide che ho linkato sotto non si capiscono alcune cose.
E se volessi usare un action per aggiungere un workflow? Avevo provato prima creando un nodo ma poi ho visto nel browser nodi di Alfresco che non veniva aggiunto anche perchè il nodo di un workflow che si trova in workspace://SpaceStore–>System–>workflow–>Package non aveva tutte le proprietà inserite, poi cercando di utilizzare la classe WorkflowService sempre senza successo, ma poi mi hanno gentilmente consigliato di fare un'action. Su Alfresco mi hanno anche detto che ci sono le action per i workflow predefiniti ma dove le trovo per vederle?

Grazie

Fonti che ho spulciato:
http://wiki.alfresco.com/wiki/Custom_Actions
http://ecmarchitect.com/images/articles/alfresco-actions/actions-article.pdf
7 Replies
openpj
Moderator
Moderator

Re: Action: cosa sono e come si creano

Le action sono delle procedure che vengono registrate all'interno del repository e che possono essere eseguite utilizzando qualunque interfaccia applicativa di Alfresco (web, share, Foundation API, Web Services, etc…).

Questo grazie al fatto che uno dei servizi di Alfresco è proprio l'ActionService che permette di eseguire le azioni che sono state attualmente registrate nel sistema.

Quindi una action può essere eseguita one-shot direttamente su un contenuto, oppure può essere configurata all'interno di una Rule di Alfresco per poter gestire eventuali comportamenti di esecuzioni che dipendono dalla gestione dei contenuti nel repository.

All'interno della SDK di Alfresco trovi un progetto di esempio che si chiama "Custom Action" forse ti aiuterà a comprendere meglio il tutto.

Spero ti possa essere utile  Smiley Wink
ventus85
Member II

Re: Action: cosa sono e come si creano

Ti ringrazio.

All'interno della SDK di Alfresco trovi un progetto di esempio che si chiama "Custom Action" forse ti aiuterà a comprendere meglio il tutto.

Intendi dentro l' SDK AlfrescoEmbedded?
openpj
Moderator
Moderator

Re: Action: cosa sono e come si creano

Intendi dentro l' SDK AlfrescoEmbedded?
No, intendo il progetto SDK CustomAction che trovi all'interno della SDK di Alfresco come uno dei progetti dell'ambiente di sviluppo.
ventus85
Member II

Re: Action: cosa sono e come si creano

Ok, ho capito!
Grazie.

Vi scriverò le novità, anche perchè in questo momento sto facendo un po' di confusione tra le tante cose di Alfresco, per esempio stavo leggendo la pagina http://wiki.alfresco.com/wiki/WorkflowAdministration che è un po' lunga e mi sono persa qualche cosa per la strada.  :lol:
alarocca_5413
Member II

Re: Action: cosa sono e come si creano

La action per eseguire un workflow esiste già ed il suo nome è "start-workflow". Vedi WorkflowAdministration, step 7:
http://wiki.alfresco.com/wiki/WorkflowAdministration#Step_7:_Integration_with_Rules_.28Optional.29

E questo è il codice:


package org.alfresco.repo.workflow;

import java.io.Serializable;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.alfresco.model.ContentModel;
import org.alfresco.repo.action.ParameterDefinitionImpl;
import org.alfresco.repo.action.executer.ActionExecuterAbstractBase;
import org.alfresco.service.cmr.action.Action;
import org.alfresco.service.cmr.action.ParameterDefinition;
import org.alfresco.service.cmr.dictionary.DataTypeDefinition;
import org.alfresco.service.cmr.repository.ChildAssociationRef;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.cmr.workflow.WorkflowDefinition;
import org.alfresco.service.cmr.workflow.WorkflowPath;
import org.alfresco.service.cmr.workflow.WorkflowService;
import org.alfresco.service.cmr.workflow.WorkflowTask;
import org.alfresco.service.namespace.NamespaceService;
import org.alfresco.service.namespace.QName;

public class StartWorkflowActionExecuter extends ActionExecuterAbstractBase
{
    public static final String NAME = "start-workflow";
    public static final String PARAM_WORKFLOW_NAME = "workflowName";
    public static final String PARAM_END_START_TASK = "endStartTask";
    public static final String PARAM_START_TASK_TRANSITION = "startTaskTransition";
       
    private NamespaceService namespaceService;
    private WorkflowService workflowService;
    private NodeService nodeService;
   
    public void setNamespaceService(NamespaceService namespaceService)
    {
        this.namespaceService = namespaceService;
    }
   
    public void setNodeService(NodeService nodeService)
    {
        this.nodeService = nodeService;
    }

   public void setWorkflowService(WorkflowService workflowService)
   {
      this.workflowService = workflowService;
   }


    @Override
    protected boolean getAdhocPropertiesAllowed()
    {
        return true;
    }
   
   @Override
   protected void addParameterDefinitions(List<ParameterDefinition> paramList)
   {
      paramList.add(new ParameterDefinitionImpl(PARAM_WORKFLOW_NAME, DataTypeDefinition.TEXT, false, getParamDisplayLabel(PARAM_WORKFLOW_NAME)));
        paramList.add(new ParameterDefinitionImpl(PARAM_END_START_TASK, DataTypeDefinition.BOOLEAN, false, getParamDisplayLabel(PARAM_END_START_TASK)));
        paramList.add(new ParameterDefinitionImpl(PARAM_START_TASK_TRANSITION, DataTypeDefinition.TEXT, false, getParamDisplayLabel(PARAM_START_TASK_TRANSITION)));
        // TODO: start task node parameter
   }

    @Override
   protected void executeImpl(Action ruleAction, NodeRef actionedUponNodeRef)
    {
        // retrieve workflow definition
        String workflowName = (String)ruleAction.getParameterValue(PARAM_WORKFLOW_NAME);
        WorkflowDefinition def = workflowService.getDefinitionByName(workflowName);
       
        // create workflow package to contain actioned upon node
        NodeRef workflowPackage = (NodeRef)ruleAction.getParameterValue(WorkflowModel.ASSOC_PACKAGE.toPrefixString(namespaceService));
        workflowPackage = workflowService.createPackage(workflowPackage);
        ChildAssociationRef childAssoc = nodeService.getPrimaryParent(actionedUponNodeRef);
        nodeService.addChild(workflowPackage, actionedUponNodeRef, WorkflowModel.ASSOC_PACKAGE_CONTAINS, childAssoc.getQName());
       
        // build map of workflow start task parameters
        Map<String, Serializable> paramValues = ruleAction.getParameterValues();
        Map<QName, Serializable> workflowParameters = new HashMap<QName, Serializable>();
        workflowParameters.put(WorkflowModel.ASSOC_PACKAGE, workflowPackage);
        for (Map.Entry<String, Serializable> entry : paramValues.entrySet())
        {
            if (!entry.getKey().equals(PARAM_WORKFLOW_NAME))
            {
                QName qname = QName.createQName(entry.getKey(), namespaceService);
                Serializable value = entry.getValue();
                workflowParameters.put(qname, value);
            }
        }

        // provide a default context, if one is not specified
        Serializable context = workflowParameters.get(WorkflowModel.PROP_CONTEXT);
        if (context == null)
        {
            workflowParameters.put(WorkflowModel.PROP_CONTEXT, childAssoc.getParentRef());
        }

        // start the workflow
        WorkflowPath path = workflowService.startWorkflow(def.id, workflowParameters);

        // determine whether to auto-end the start task
        Boolean endStartTask = (Boolean)ruleAction.getParameterValue(PARAM_END_START_TASK);
        String startTaskTransition = (String)ruleAction.getParameterValue(PARAM_START_TASK_TRANSITION);
        endStartTask = (endStartTask == null) ? true : false;
       
        // auto-end the start task with the provided transition (if one)
        if (endStartTask)
        {
            List<WorkflowTask> tasks = workflowService.getTasksForWorkflowPath(path.id);
            for (WorkflowTask task : tasks)
            {
                workflowService.endTask(task.id, startTaskTransition);
            }
        }
   }
}
ventus85
Member II

Re: Action: cosa sono e come si creano

Ciao alarocca,
come va?

Stamani ho guardato l'esempio indicatomi da OpenPj.
Per qualche utente (futuro) che deve guardarlo esso contiene tre file:
  • logger-action-context.xml: contiene il bean

  • loggerActionExecuter.java: è la classe con l'implementazione dell'action. Contiene in particolare il metodo executeImpl.

  • logger-action-message.properties: contiene i messaggi da mostrare.
Ok, la nebbia si sta diradando.
Smiley Very Happy

Ieri, come scritto, invece mi sono letta per bene la pagina http://wiki.alfresco.com/wiki/WorkflowAdministration. Ho ancora qualche dubbio (forse diversi) probabilmente la devo rileggere perché sennò faccio solo confusione.

Alarocca grazie per il codice della action start-workflow.
Ora devo vedere quanto mi servirà, se devo creare una nuova classe e così via.

Grazie.
ventus85
Member II

Re: Action: cosa sono e come si creano

Breve riepilogo…

In generale un'action (azione) è una procedura registrata all'interno del repository. Essa può essere utilizzata da un utente per esempio per modificare un contenuto (come un aggiornamento o un'eliminazione) attraverso un'interfaccia. Sono come delle piccole unità di lavoro o componenti che possono essere configurate e possono essere eseguite anche runtime.

Una action può essere eseguita one-shot (cosa si intendi con questo???) direttamente su un contenuto, oppure configurata all'interno di una regola di Alfresco.

Un'azione in genere è composta da una classe Java che contiene l'implementazione dell'azione, da un bean e da un'eventuale file con le proprietà.

La classe con l'implementazione (Action executer) estende ActionExecuterAbstractBase e ha l'override del metodo executeImpl. Questo metodo per esempio può prendere dei valori dei parametri e utilizzarli in quale modo.

Il file con il bean per la definizione e configurazione dell'azione è un file xml. Può contenere anche un bean per caricare il file delle proprietà): il secondo bean ha in particolare un tag property con nome "resourceBundle" e al suo interno una lista dei file delle proprietà.

Il terzo file (quello delle proprietà) è un .properties e contiene per esempio la traduzione dei messaggi da mostrare all'utente.