Dettagli relativi a una trasformazione modello-a-modello che specifica un URI come destinazione

È possibile modificare il codice sorgente generato per una trasformazione modello-a-modello per consentire agli utenti di specificare un URI (Uniform Resource Identifier) come file di modello di destinazione.

L'esecuzione di una trasformazione modello-a-modello genera un modello in memoria. Per impostazione predefinita, come parte della post-elaborazione della trasformazione, il framework di trasformazione scrive il contenuto del modello in memoria generato in un file nello spazio di lavoro. Quando un utente crea una configurazione di trasformazione per la trasformazione modello-a-modello, l'utente può specificare il file come contenitore di destinazione della trasformazione o creare un nuovo contenitore di destinazione. In una configurazione di trasformazione, una proprietà di configurazione denominata "target container" contiene il nome file del modello di destinazione. Questo file deve essere presente nello spazio di lavoro prima che la trasformazione venga eseguita.

Questo progetto di trasformazione di esempio mostra come fornire agli utenti un modo alternativo per configurare il contenitore di destinazione personalizzando il codice sorgente della trasformazione generato. In qualità di autore della trasformazione, dopo aver generato il codice sorgente per una trasformazione modello-a-modello, è possibile personalizzare il codice in modo che l'utente della trasformazione possa specificare un URI, anziché un file di modello, come contenitore di destinazione della trasformazione. Non occorre che il file identificato dall'URI sia presente prima che la trasformazione venga eseguita; la trasformazione crea il file nel caso in cui non esista.

Questo esempio contiene un semplice modello di associazione di trasformazione che definisce solo un'associazione da un modello UML a un modello UML; l'associazione assegna un nome al modello di destinazione generato, nome che viene ricavato da quello del modello di origine.
Nota: il nome interno di un modello non deve necessariamente corrispondere al nome del file che contiene il modello nel file system.
Dal momento che il modello di associazione in questo esempio è semplice, la trasformazione generata mostra solo la personalizzazione richiesta per supportare l'utilizzo di un URI per specificare un contenitore di destinazione. La trasformazione non copia elementi dal modello di origine al modello di destinazione.
Questo esempio mostra come personalizzare i seguenti elementi della trasformazione generata:
  • Il punto di estensione della trasformazione nel file plugin.xml generato
  • Il metodo isTargetElementValid nella classe validator della trasformazione generata
  • Il metodo createRootTransformation nella classe fornitore della trasformazione generata denominata Uri4targetTransformationProvider

Personalizzazione del file plugin.xml

Dopo aver generato il codice sorgente della trasformazione, nel file plugin.xml, nel punto di estensione della trasformazione, la proprietà denominata targetModelType elenca questo tipo di modelli che un utente della trasformazione può specificare come contenitore della destinazione. Per impostazione predefinita, questa proprietà è impostata su resource, quindi nella configurazione di trasformazione, l'utente deve specificare un file che sia presente nello spazio di lavoro. Nel file plugin.xml personalizzato, la proprietà targetModelType è impostata su none.

Nel file plugin.xml, l'elemento estensione della trasformazione generata contiene una nuova proprietà di trasformazione denominata URI modello di destinazione. In questo esempio, nell'editor e nella procedura guidata Configurazione di trasformazione, nella scheda Proprietà, nel campo URI modello di destinazione, l'utente specifica un valore stringa per la proprietà.

Personalizzazione della classe validator della trasformazione

La procedura guidata configurazione di trasformazione e l'editor utilizzano la classe validator della trasformazione personalizzata generata denominata Uri4targetTransformationValidator per convalidare le impostazioni nella configurazione di trasformazione. Per impostazione predefinita, l'implementazione del metodo isTargetElementValid restituisce true solo se il contenitore di destinazione configurato è un file. In questo esempio, l'implementazione predefinita viene sovrascritta e restituisce true se come contenitore di destinazione è stato specificato un valore. Una implementazione più efficace potrebbe eseguire una convalida specifica della trasformazione o del progetto sull'URI indicato dall'utente.

Il seguente frammento di codice mostra l'implementazione predefinita del metodo isTargetElementValid che la trasformazione genera:
    /**
     * <!-- begin-user-doc -->
     * <!-- end-user-doc -->
     * @see com.ibm.xtools.transform.authoring.TransformationValidator#isTargetElementValid(java.lang.Object)
     * @generated
     */
    protected boolean isTargetElementValid(Object target) {
    	//Remove @generated tag to add more target validation checks
    	return super.isTargetElementValid(target);
    }
Il seguente frammento di codice mostra l'implementazione personalizzata contenuta nell'esempio, che, ai fini di questo esempio, restituisce sempre true:
    /**
     * <!-- begin-user-doc -->
     * <!-- end-user-doc -->
     * @see com.ibm.xtools.transform.authoring.TransformationValidator#isTargetElementValid(java.lang.Object)
     * @generated NOT
     */
    protected boolean isTargetElementValid(Object target) {
        return true;
    }

Personalizzazione del fornitore della trasformazione

Nella classe personalizzata generata denominata Uri4targetTransformationProvider, l'implementazione predefinita del metodo createRootTransformation crea un'istanza della classe denominata RootTransformation, che a sua volta crea un'istanza della classe denominata ResourceTransform. L'implementazione predefinita della classe ResourceTransform utilizza un'implementazione denominata ResourceTargetRule che apre il file che rappresenta il contenitore di destinazione configurato. In questo esempio, il contenitore di destinazione configurato è un URI anziché un file; pertanto, un'implementazione di ResourceTransform personalizzata denominata ResourceFromUriTransform e una regola ResourceTargetRule personalizzata denominata ResourceFromUriTargetRule vengono aggiunte alla classe Uri4targetTransformationProvider.

L'implementazione personalizzata di ResourceFromUriTargetRule effettua le seguenti operazioni:
  • Crea il file specificato dall'URI, nel caso in cui non esista
  • Apre il file specificato dall'URI
  • Associa una risorsa modello in memoria al file e archivia l'oggetto file nel contesto di trasformazione root in modo che le altre regole di trasformazione possano recuperarlo
Il seguente frammento di codice mostra l'implementazione predefinita del metodo createRootTransformation che la trasformazione genera:
    /**
     * Creates a root transformation. You may add more rules to the transformation here
     * <!-- begin-user-doc -->
     * <!-- end-user-doc -->
     * @param transform The root transformation
     * @generated
     */
    protected RootTransformation createRootTransformation(ITransformationDescriptor descriptor) {
        return new RootTransformation(descriptor, new MainTransform());
    }
Il seguente frammento di codice mostra l'implementazione personalizzata del metodo createRootTransformation contenuta nell'esempio:
    /**
     * Creates a root transformation. You may add more rules to the transformation here
     * <!-- begin-user-doc -->
     * <!-- end-user-doc -->
     * @param transform The root transformation
     * @generated NOT
     */
    protected RootTransformation createRootTransformation(ITransformationDescriptor descriptor) {
        return new RootTransformation(descriptor, new MainTransform()) {
            @Override
             protected void addInitialExtractor(Transform mainTransform) {
                add(new ResourceListExtractor(new ResourceFromUriTransform(mainTransform)));
             }};
    }
    
Il seguente frammento di codice mostra le implementazioni personalizzate denominate ResourceFromUriTransform e ResourceFromUriTargetRule contenute nella classe Uri4targetTransformationProvider:
    protected class ResourceFromUriTransform extends ResourceTransform {
        public ResourceFromUriTransform(Transform mainTransform) {
            super(Uri4targetMessages.ResourceFromUriTransform_id);
            setName(Uri4targetMessages.ResourceFromUriTransform_name);
            add(new ResourceFromUriTargetRule());
            add(new ResourceContentsExtractor(mainTransform));
        }
    }

    protected class ResourceFromUriTargetRule extends ResourceTargetRule {
        @Override
        protected Object createTarget(ITransformContext context) {
            ResourceSet resourceSet = ((EditingDomain) context
.getPropertyValue(TransformAuthoringConstants.TARGET_EDITING_DOMAIN))
.getResourceSet();
            Resource resource = null;
            Object targetModelURIString = context.getPropertyValue("TargetModelURI"); //$NON-NLS-1$
            if (targetModelURIString instanceof String) {
                URI targetModelURI = URI.createURI((String)targetModelURIString);
                IPath targetModelPath = new Path(targetModelURI.path());                
                IWorkspaceRoot wsRoot = ResourcesPlugin.getWorkspace().getRoot();
                IFile targetModelFile = wsRoot.getFile(targetModelPath);
                ValidateEditRule.addAffectedFile(context, targetModelFile);
                resource = resourceSet.createResource(getPlatformURI(targetModelFile));
                ITransformContext rootContext = context;
                while (rootContext.getParentContext() != null)
                    rootContext = rootContext.getParentContext();
                rootContext.setPropertyValue(ITransformContext.TARGET_CONTAINER, targetModelFile);
            }
            return resource;
        }        
    }
Argomento principale: Trasformazione modello-a-modello che specifica un URI come destinazione

Feedback