Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » TMF (Xtext) » use generated classes in DSL file, problem of missing type
use generated classes in DSL file, problem of missing type [message #1835810] Mon, 14 December 2020 01:55 Go to next message
Alexander Gornostaev is currently offline Alexander GornostaevFriend
Messages: 2
Registered: December 2020
Junior Member
Shortly, the problem is that when I'm writing my dsl file (with grammars inherited from xbase), I may need to use some classes, that are surely to be generated after the validation but that are not available during writing the file.
The question is, how do i configure Xtext and Xbase in order to use in my DSL file (the one with DSL extension, ".myx") classes that are not yet generated by JvmModelInferrer?

Here is the language grammar:
grammar org.xtext.example.mydsl.MyX with org.eclipse.xtext.xbase.Xbase

Model:
    expressions+=CommonExpression*;
    
CommonExpression: 
    Anime | AnimeResource
;

AnimeResource:
    'AnimeRes' name=ID '{'
    (args+=FullJvmFormalParameter)*
    '}'
;

Anime:
    'watch' name=ID body=XBlockExpression
;



Here is what i want to achive (test.myx):
AnimeRes Resource {
    
}


watch Watcher {
    val someStub = Resource.create()
}

So the dsl file looks like there is a static method defined for Resource class. But in reality, there must be additional parameters that should be passed to Resource, they are purely boilerplate in my case, that's why I don't want to pass them into "create" each time. How I want the generated file look like to achieve that:
package test;

public class Model {
  private int id= 0;
  
  public static class Resource {
    private int id;
    public Resource(final int id) {
      this.id = id;
    }
  }
  
  public class ResourceCreator {
    public Resource create() {
      return new Resource(id /* the creator is inner non-static class */));
    }
  }
  
  public ResourceCreator Resource = new ResourceCreator();
}


That way I'm kind of cheating. I have a variable that has the name of the class, and in the client code it looks like they use static method when they are really just using a builder that is named like the class. Here is the JvmModelInferrer to make similarly looking file:
class MyXJvmModelInferrer extends AbstractModelInferrer {

    def dispatch void infer(Model element, IJvmDeclaredTypeAcceptor acceptor, boolean isPreIndexingPhase) {
        acceptor.accept(element.toClass(QualifiedName.create("test", "Model"))) [
            for (expression : element.expressions) {
                switch (expression ) {
                    AnimeResource: {
                        members += expression.toClass(expression.name) [
                            static = true
                            visibility = JvmVisibility.PUBLIC
                            val _members = members
                            expression.args.forEach [
                                _members += expression.toField(name, parameterType) [
                                    static = false
                                    visibility = JvmVisibility.PUBLIC
                                ]

                            ]
                            members += expression.toField("id", typeRef(int))

                            members += expression.toConstructor [
                                val _parameters = parameters
                                expression.args.forEach [
                                    _parameters += it.toParameter(name, parameterType)
                                ]
                                _parameters += expression.toParameter("id", typeRef(int))
                                body = '''
                                    «FOR param : parameters»this.«param.name» = «param.name»;
                                    «ENDFOR»
                                '''
                            ]
                        ]
                        members += element.toClass(expression.name + "Creator") [
                            static = false
                            visibility = JvmVisibility.PUBLIC
                            members += element.toMethod("create", typeRef(expression.name)) [
                                val parameters = parameters
                                parameters.args.forEach [
                                    parameters += it.toParameter(name, parameterType)
                                ]
                                body = '''
                                    return new «expression.name»(
                                    «FOR param : parameters»
                                    «IF parameters.indexOf(param) < parameters.size - 1», 
                                    «ENDIF»
                                    «ENDFOR»id);
                                '''
                            ]
                        ]
                        members += expression.toField(expression.name, typeRef(expression.name + "Creator")) [
                            visibility = JvmVisibility.PUBLIC
                            initializer = '''
                                new «expression.name + "Context"»();
                            '''
                        ]
                    }
                }
            }
        ]
    }
}

The problem that I've faced with this approach is shown in the attached screenshot index.php/fa/39535/0/
So it seems that some linking fails but I can not understand what I should do to fix that and what bindings I should override and how.

Any help would be appreciated.
  • Attachment: OZjXW.png
    (Size: 31.38KB, Downloaded 116 times)
Re: use generated classes in DSL file, problem of missing type [message #1835838 is a reply to message #1835810] Mon, 14 December 2020 17:29 Go to previous message
Christian Dietrich is currently offline Christian DietrichFriend
Messages: 14664
Registered: July 2009
Senior Member
can you please provide a jvmmodelinferrer that actually compiles

cross post from https://stackoverflow.com/questions/65278762/xtext-use-generated-classes-in-dsl-file-problem-of-missing-type


Twitter : @chrdietrich
Blog : https://www.dietrich-it.de

[Updated on: Tue, 15 December 2020 18:00]

Report message to a moderator

Previous Topic:Programmatic serialization not using formatter preferences
Next Topic:Problems with JDK 14
Goto Forum:
  


Current Time: Tue Apr 16 04:28:25 GMT 2024

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

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

Back to the top