Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » TMF (Xtext) » Programmatically access elements imported from another Ecore model
Programmatically access elements imported from another Ecore model [message #1271880] Sun, 16 March 2014 13:29 Go to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Hi all,

I have a simple Ecore Meta-Model which models a library that contains books (it's just a simple example). Both, library and books are characterized by a name.

I want to write a DSL that allows me to do something like this:

SelectedBook BookA
SelectedBook BookB


Where BookA and BookB are books defined in an instance of the ecore meta-model.

I followed this tutorial and I was able to implement the aforementioned DSL. Hence I can import books name for an Ecore model.

Now I need to write a model-to-text transformation that transform the DSL in java code. I'm using Epsilon.
I'm not sure if it is an Epsilon problem or not.
However when I try to access the books, the content of their fields (e.g. the string name) is null.

Do you have any idea on how it is possible to fix the problem?
Please let me know if you need further information.
Re: Programmatically access elements imported from another Ecore model [message #1271891 is a reply to message #1271880] Sun, 16 March 2014 14:16 Go to previous messageGo to next message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
How do you read the model? If standalone make sure you call the
support class of the resource service provider and load all relevant
resources to the resourceset

--
Need training, onsite consulting or any other kind of help for Xtext?
Go visit http://xtext.itemis.com or send a mail to xtext at itemis dot de


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Re: Programmatically access elements imported from another Ecore model [message #1271895 is a reply to message #1271891] Sun, 16 March 2014 14:34 Go to previous messageGo to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Hi Christian,

thanks for the answer.

To be honest I'm a little bit confused.
See below the code that invokes the M2T:

Thanks again.

public class MyDSLTransformation extends AbstractHandler {
	
	public MyDSLTransformation() {	
		
	}

	@Override
	public Object execute(ExecutionEvent event) throws ExecutionException {
		IFile sourcefile = null;
		IEditorPart editor = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage().getActiveEditor();
		if (editor != null) {
            IEditorInput input = editor.getEditorInput();
            if (input instanceof IFileEditorInput) {
            	sourcefile = ((IFileEditorInput)input).getFile();
            	System.out.println("File from editor: " + sourcefile.getLocation().toOSString());
            	if(sourcefile.getFileExtension().compareTo("MyDSLModel") != 0){
            		
            		sourcefile = null;
            		MessageDialog
					.openError(
							PlatformUI.getWorkbench()
									.getActiveWorkbenchWindow().getShell(),
							"Error on Editor Selection 2",
							"Please select the editor from which you want to generate code and execute command again.");
            	}
                
            }
            
        }
		
				
		if(sourcefile == null)
			return null;
		
		
		URL url = Platform.getBundle(Activator.PLUGIN_ID).getEntry("epsilon/main.egl");
		String fileURL = "";
		try {
			fileURL = FileLocator.toFileURL(url).toString();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	    
		
		IEglTransformParameter eglTransformParameter = TransformParameterFactory.createEglTransformParameter();
		eglTransformParameter.setTransformName("MyDSL generation");
		eglTransformParameter.setEglTransform(fileURL);
		eglTransformParameter.setPluginID(Activator.PLUGIN_ID);
		eglTransformParameter.setSourceMetaModelURI("http://www.example.org/MyDSL");
		eglTransformParameter.setSourceModelFilePath(sourcefile.getLocation().toOSString());
		eglTransformParameter.setSourceName("Source");
		eglTransformParameter.setSourceReadOnLoad(true);
		eglTransformParameter.setSourceStoreOnDisposal(false);
		
		eglTransformParameter.setOutputRoot("file:" + sourcefile.getProject().getLocation().toOSString());
		
		//get transform service
		
		//do transform
		EGLTransformer transformer = new EGLTransformer(eglTransformParameter);
		transformer.transform();
		
		return null;
	}

}


public class EGLTransformer {
	
	IEglTransformParameter parameter;
	
	public EGLTransformer(IEglTransformParameter param) {
		parameter = param;
		
	}
	
	public void transform()
	{
		//URL transformationEntry = Platform.getBundle(parameter.getPluginID()).getEntry(parameter.getEglTransformation());
		URL transformationEntry = null;
		try {
			transformationEntry = new URL(parameter.getEglTransformation());
		} catch (MalformedURLException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		URL resolvedTransformationURL = null;
		URI transformURI = null;
		
		try {
			resolvedTransformationURL = FileLocator
					.resolve(transformationEntry);
			transformURI = resolvedTransformationURL.toURI();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (URISyntaxException e) {
			e.printStackTrace();
		}
		
		

		EglFileGeneratingTemplateFactory eglTemplateFactory = new EglFileGeneratingTemplateFactory();
		IEolExecutableModule eglModule = new EglTemplateFactoryModuleAdapter(
				eglTemplateFactory);
		try {
			eglTemplateFactory.setOutputRoot(parameter.getOutputRoot());
			eglModule.parse(transformURI);
		} catch (EglRuntimeException e2) {
			e2.printStackTrace();
		} catch (Exception e) {
			e.printStackTrace();
		}

		if (eglModule.getParseProblems().size() > 0) {
			System.err.println("Parse errors occured...");
			for (ParseProblem problem : eglModule.getParseProblems()) {
				System.err.println(problem.toString());
			}
		}
		eglModule.getContext().getNativeTypeDelegates().add(new ExtensionPointToolNativeTypeDelegate());
		
		EmfModel emfModel = new EmfModel();
		emfModel.setName(parameter.getSourceName());
		emfModel.setMetamodelUri(parameter.getSourceMetaModelURI());
		emfModel.setModelFile(parameter.getSourceModelFilePath());
		emfModel.setReadOnLoad(parameter.isSourceReadOnLoad());
		emfModel.setStoredOnDisposal(parameter.isSourceStoreOnDisposal());
		try {
			emfModel.load();
		} catch (EolModelLoadingException e) {
			e.printStackTrace();
		}
		
		eglModule.getContext().getModelRepository().addModel(emfModel);
		try {
			eglModule.execute();
		} catch (EolRuntimeException e) {
			e.printStackTrace();
		}
		eglModule.getContext().getModelRepository().dispose();
	}

}
Re: Programmatically access elements imported from another Ecore model [message #1271906 is a reply to message #1271895] Sun, 16 March 2014 15:24 Go to previous messageGo to next message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
Sorry I cannot help you with that. Maybe you can ask in the forum of
your transformation tool on how to read multiple input files

--
Need training, onsite consulting or any other kind of help for Xtext?
Go visit http://xtext.itemis.com or send a mail to xtext at itemis dot de


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Re: Programmatically access elements imported from another Ecore model [message #1271917 is a reply to message #1271906] Sun, 16 March 2014 15:58 Go to previous messageGo to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Thank anyway Christian,

I'm trying to do it in standalone.
Just for understanding your first answer.

However I have the same problem:


            LibraryPackage.eINSTANCE.eClass();
	    LibraryDSLPackage.eINSTANCE.eClass();
	    
	    // Register the XMI resource factory for the .website extension
	    Resource.Factory.Registry reg = Resource.Factory.Registry.INSTANCE;
	    Map<String, Object> m = reg.getExtensionToFactoryMap();
	    m.put("librarymodel", new XMIResourceFactoryImpl());
	    m.put("librarydsl", new XMIResourceFactoryImpl());
	    
	    // Obtain a new resource set
	    ResourceSet resSet = new ResourceSetImpl();

	    
	    // Get the resource
	    Resource libraryModelResource = resSet.getResource(URI
	        .createURI(PATH_TO_ECORE_MODEL), true); // for model I mean the file containing the library, not the meta-model
	    LibraryModel libraryModel = (LibraryModel) libraryModelResource.getContents().get(0);
	    System.out.println(libraryModel.getName()); // this works
	    
	    new LibraryDSLStandaloneSetup().createInjectorAndDoEMFRegistration();
	    Resource libraryDSLResource = resSet.getResource(URI
		        .createURI(PATH_TO_DSL_MODEL), true);
	    LibraryDSL libraryDSL = (LibraryDSL) libraryDSLResource.getContents().get(0);
	    System.out.println(libraryDSL.getSelectedBooks.get(0).getName()); // this prints "null"
	    
	    


The first println returns the name of the library, while the second prints "null".
Re: Programmatically access elements imported from another Ecore model [message #1271934 is a reply to message #1271917] Sun, 16 March 2014 16:49 Go to previous messageGo to next message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
Hi I still dont see you calling your xxxsupport class

--
Need training, onsite consulting or any other kind of help for Xtext?
Go visit http://xtext.itemis.com or send a mail to xtext at itemis dot de


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Re: Programmatically access elements imported from another Ecore model [message #1271956 is a reply to message #1271934] Sun, 16 March 2014 18:15 Go to previous messageGo to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Tanks Christian.

I got it.

As you said initially I had to instantiate the LiraryModelSupport class and call the method registerServices.

I'll try to see if I can use the same approach with Epsilon.
Is there a specific point where I have to register the service or is the effect global?

Thanks again,
Luca
Re: Programmatically access elements imported from another Ecore model [message #1271970 is a reply to message #1271956] Sun, 16 March 2014 19:06 Go to previous messageGo to next message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
Hi,

i dont know epsilion but in a standalone java app it is global.


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Re: Programmatically access elements imported from another Ecore model [message #1272007 is a reply to message #1271970] Sun, 16 March 2014 21:44 Go to previous messageGo to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Thanks again Christian.

The last question:

let's suppose that LibraryModel is importing elements from another Ecore model: AuthorsModel.

What should I do for accessing the data in author model?
I tried the same procedure but something got wrong.
See the code below.
The last line is printing null.

Thanks,
Luca

P.S.:
The DSL and the MWE2 includes the author meta model.
However the DSL is not directly importing elements of the Author Model. That's because I don't need it.
I tried to import them to see if that was the problem, but it didn't work.

             
	    // Register the XMI resource factory for the .website extension
	    Resource.Factory.Registry reg = Resource.Factory.Registry.INSTANCE;
	    Map<String, Object> m = reg.getExtensionToFactoryMap();
	    m.put("librarydsl", new XMIResourceFactoryImpl());
	    m.put("librarymodel", new XMIResourceFactoryImpl());
	     m.put("authormodel", new XMIResourceFactoryImpl());
	    
	    ResourceSet resSet = new ResourceSetImpl();

	    
	    

            LibraryPackage.eINSTANCE.eClass();
	    LibraryModelSupport libraryModelSupport = new LibraryModelSupport();
	    libraryModelSupport.registerServices(true);
	    Resource libraryModelResource = resSet.getResource(URI.createURI(PATH_TO_LIBRARY_MODEL), true);
            LibraryModel libraryModel = (LibraryModel) libraryModelResource.getContents().get(0);
	    System.out.println(libraryModel.getName()); // this works

            AuthorPackage.eINSTANCE.eClass();
	    AuthorModelSupport authorModelSupport = new AuthorModelSupport();
	    authorModelSupport.registerServices(true);
	    Resource authorModelResource = resSet.getResource(URI.createURI(PATH_TO_AUTHOR_MODEL), true);
            AuthorModel authorModel = (AuthorModel) authorModelResource.getContents().get(0);
	    System.out.println(authorModel.getName()); // this works
	    
	    LibraryDSLPackage.eINSTANCE.eClass();
	    new LibraryDSLStandaloneSetup().createInjectorAndDoEMFRegistration();
	    Resource libraryDSLResource = resSet.getResource(URI.createURI(PATH_TO_DSL_MODEL), true);
	    LibraryDSL libraryDSL = (LibraryDSL) libraryDSLResource.getContents().get(0);
	    System.out.println(libraryDSL.getSelectedBooks.get(0).getName()); // now this prints the correct name
            System.out.println(libraryDSL.getSelectedBooks.get(0).getAuthor().Name()); //  this print null

[Updated on: Sun, 16 March 2014 22:18]

Report message to a moderator

Re: Programmatically access elements imported from another Ecore model [message #1272020 is a reply to message #1272007] Sun, 16 March 2014 22:27 Go to previous messageGo to next message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
Hi,

how is the reference done between the models? relative path? platform:/resource uri ...


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Re: Programmatically access elements imported from another Ecore model [message #1272024 is a reply to message #1272020] Sun, 16 March 2014 22:38 Go to previous messageGo to next message
Luca Gherardi is currently offline Luca GherardiFriend
Messages: 62
Registered: November 2010
Member
Hi

I'm not sure if I have completely understand your question.

The DSL grammar is importing the author meta-model in this way:

import "http://www.example.org/authormodel" as authorModel


The MWE2 contains the following lines:

registerGeneratedEPackage = "org.example.authorModel.AuthorPackage"
registerEcoreFile = "platform:/resource/org.example.authorModel.model/models/authorModel.ecore"
registerGenModelFile = "platform:/resource/org.example.authorModel.model/models/authorModel.genmodel"


For the Library Mode (Ecore) I used the "Load Resource..." command.
The references in the XML are done in this way:
<eStructuralFeatures xsi:type="ecore:EReference" name="cdmFunction" eType="ecore:EClass ../../org.example.authorModel.model/models/authorModel.ecore#//Author"/>

However this was done automatically by the Ecore editor.

Thanks,
Luca
Re: Programmatically access elements imported from another Ecore model [message #1272028 is a reply to message #1272024] Sun, 16 March 2014 22:54 Go to previous message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14665
Registered: July 2009
Senior Member
Sorry then I have no idea on that

--
Need training, onsite consulting or any other kind of help for Xtext?
Go visit http://xtext.itemis.com or send a mail to xtext at itemis dot de


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de
Previous Topic:Common Terminal-Grammar generates Compile-Errors
Next Topic:generate code as is from user input
Goto Forum:
  


Current Time: Wed Apr 24 17:46:54 GMT 2024

Powered by FUDForum. Page generated in 0.04416 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software

Back to the top