Specification-By-Example for Model Transformations
At itemis one of our core development activities in a lot of our projects is the specification and implementation of model-to-model transformations. In a large project in the automotive domain we have been implementing a huge code base of transformations to and from a common domain model.
Two key points from this and other projects are:
- Providing a written prose specification for model transformations is often moot: The effort it takes to achieve in natural language the degree of detail and formality that is required for implementation is high. It is useful to use a formal specification for the transformation – which means that you almost have an implementation ready at this point.
- Domain models and the transformations are very complex. In the end, for eliciting the requirements, detailing the specification and providing documentation, examples of the source and target models for a transformation are vital.
Specification-by-example for an AUTOSAR model
So in this project we chose to enhance or even replace the specs with "Specification-By-Example". For all transformation steps and relevant source model variations, we keep a combination of source model and expected target model. For convenience, these are implemented in the test model language that I blogged about recently. The transformations are then implemented in Xtend (Xtend fragments are also directly written in discussion meetings).
Assume that we have an inplace-transformation for an AUTOSAR model (containing software components and ports), which should merge all the ports and interfaces of a component into one port and one merged interface. Our specification-by-example-files could look like this:
Note that our specification-by-example is based on Xtext models and can be used for any (EMF-based) meta-model. Xtext provides comfortable editing features that make it possible, to create such models during meetings. Since they are text files, they can be easily added to version control systems (such as git), and we can place them in the developer workspace for easy access.
After having such an example-based specification, the next step would be obviously to use the same approach for testing. The source file is the input and the target file is the expected output. Our test framework reads in the source model, applies the transformations and then uses the EMF Compare framework from Eclipse to compare the actual result to the expected result. If there are differences, the test will fail.
We have added a textual / HTML based formatting for the results of EMF Compare, so that we can easily see which elements have changed based on the output of the build system, such as Jenkins, without having to reproduce the transformation on the local machine first.
Improve your understanding of the transformation
The specification-by-example approach improves the teams understanding of the transformation and eases writing relevant tests. It also supports some of the approaches that some of my colleagues blogged about:
- Test Driven Development: As we directly use the specifications-by-example for test cases (and expand on them), we do have a set of test cases that is actually implemented before the first line of code is written and can directly be used to validate the code against. Usually, they will be supplemented by additional tests (e.g. unit tests).
- Agile Tests: It is in our "Definition of Done" to provide test cases for each transformation implementation of a sprint. In the sprint review the "before" and "after" models can be reviewed to discuss what has actually been implemented.
You want to learn more about our projects in the automotive domain?