Xcore

If you often find yourself customizing the Ecore model with operations or redefining existing methods, you might want to try Xcore for maintaining your Ecore model. Xcore is a DSL for Ecore. It is implemented in Xtext and Xbase, allowing you to specify the Ecore model with a Java-like syntax. Besides the structure of the model, you can also use Xcore to specify the behavior of operations, derived features, and provide custom implementation of methods. Moreover, the mapping of data types to Java types is more straightforward in Xcore. Being a DSL based on Xtext/Xbase, with Xcore you do not need a .genmodel file to generate the Java code for your model; you just edit your file, and the Java code will be automatically generated on save.

In order to use Xcore, you need to install the feature "EMF - Eclipse Modeling Framework Xcore SDK" into your Eclipse, unless it is already installed.

In this section, we will implement a new Xtext DSL, for specifying libraries, books, and authors. The Ecore model will be specified with Xcore.

Creating the Xcore project

Let's create an Xcore project for defining the Ecore model for the DSL that we are going to implement in this section. Steps are as follows:

  1. Navigate to File | New | Project...; in the dialog, navigate to the Xcore category and click on Xcore Project.
  2. Specify org.example.library.model as the project name and press Finish.

In the model directory of the project, create an .xcore file, for example, Library.xcore. Here we define the Ecore model, using a Java-like syntax:

package org.example.library

class LibraryModel {
    contains Library[] libraries
}

abstract class Named {
    String name
}

class Library extends Named {
    contains Writer[] writers
    contains Book[] books
}

class Writer extends Named {
}

class Book {
    String title
    refers Writer[] authors
}

As soon as you save the file, the Java code for the Ecore model will be automatically generated in the src-gen folder. Containment references are specified with the keyword contains, while cross-references with the keyword refers. The fact that a reference is a multi-value reference is specified with the []. Of course, you can use the content assist while editing an Xcore file. The documentation of Xcore is https://wiki.eclipse.org/Xcore.

Creating the Xtext project from an existing Xcore model

We will now create a new Xtext project starting from the Ecore model implemented in Xcore.

Note

An Xcore project is an Xtext project, so you can directly use its Ecore model in your Xtext DSL.

In order to create the Xtext project, perform the following steps:

  1. Navigate to File | New | Project...; in the dialog, navigate to the Xtext category and click on Xtext Project From Existing Ecore Models.
  2. In the next dialog, press the Add… button to select a GenModel.
  3. Select the Library.xcore and press OK.
  4. Specify LibraryModel for the Entry rule.
  5. After you press Next, fill in the details for the following fields and press Finish:
    • Project name: org.example.library
    • Name: org.example.library.Library
    • Extensions: library

As in the School DSL, the first part of the grammar uses an import line to refer to the existing Ecore model:

grammar org.example.library.Library
      with org.eclipse.xtext.common.Terminals

import "org.example.library"

We replace the rules of the Library.xtext grammar completely with these grammar rules:

LibraryModel returns LibraryModel:
  libraries+=Library*;

Library returns Library:
  'library' name=STRING
  '{'
    ('writers' '{' writers+=Writer ( "," writers+=Writer)* '}' )?
    ('books' '{' books+=Book ( "," books+=Book)* '}' )?'
Writer returns Writer:
  name=STRING;

Book returns Book:
  'title' title=STRING
  ('authors' authors+=[Writer|STRING] ( "," authors+=[Writer|STRING])* )?
;

Valid programs for this DSL have the following shape:

library "A library" {
    writers {
        "A writer", "Another writer", "Third writer"
    }
    books {
        title "A book",
        
title "Another book"
            authors "Third writer", "A writer"
    }
}

library "An empty library" {
    
}

Remember to fix the LibraryStandaloneSetup before running any JUnit tests:

override register(Injector injector)   if (!EPackage.Registry.INSTANCE.containsKey(LibraryPackage.eNS_URI)) {
   Epackage.Registry.INSTANCE.put(LibraryPackage.eNS_URI,
         LibraryPackage.eINSTANCE);
  }
  super.register(injector)
}

Modifying the Xcore model

As in the previous DSLs, let's assume that we want to modify the Ecore model. Since we use Xcore, everything will be much easier since we can write a model operation directly in the Xcore file, keeping in mind that the body of an operation in Xcore uses the Xbase syntax. For example, we add a datatype Books that corresponds to the Java type Iterable<Book>, and we implement in the Writer class the getoperation:

type Books wraps Iterable<Book>

class Writer extendsextends Named {
    op Books getBooks() {
        (eContainer as Library).books.
            filter[authors.contains(this)]
    }
}

That's all we need to do. On saving the file, Xcore will automatically regenerate the Java code. We do not need to modify the generate code and specify the Javadoc @generated NOT, neither we need to create a separate Java file with ImplCustom.

The same holds if we want to give a custom implementation of methods such as toString. Differently from what we had to do in the previous example DSL, with Xcore it's just a matter of writing:

class Book {
...
  op String toString() {
    'title: "' + title + '"' +
      if (!authors.empty)
        ", by " + authors.map[name].join(", ")
  }
}

We can use the added operation in the validator, in the code generator, and in other parts of the DSL. This is left as an exercise.

Building an Xtext DSL that is based on Xcore with Maven/Tycho requires some ad-justments to the pom files. You can also generate the Java code from the Xcore model during the Maven build, using the xtext-maven-plugin. In the source code of the examples of the book, you will find all the pom files for this example DSL configured to use Xcore. Further and advanced details about using Xcore with Xtext can be found in the presentation Schill 2015.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.12.161.77