1

I am copying the structure of the example Xtext Web project for multiple dsl's using the Entities and StateMachine example. I am using Gradle as my build system. I have a class MyGeneratorModule in both of my grammar projects. In my workflow I reference it like this:
configuration = MyGeneratorModule {...}
I can run the workflow fine in each project, but when I try to perform a jettyRun from the web project I get this error:

Task :com.selinc.logic.program:generateXtextLanguage FAILED
0    [main] ERROR mf.mwe2.launch.runtime.Mwe2Launcher  - [XtextLinkingDiagnostic: null:17 Couldn't resolve reference to JvmType 'MyGeneratorModule'.

Am i missing something in the workflow or gradle build? Here is a more complete example of my languages build.gradle file and workflow:

mwe2:

component = XtextGenerator {
        configuration = MyGeneratorModule { // <- This is what is not resolving
            project = StandardProjectConfig {
                baseName = baseName
                rootPath = rootPath
                runtimeTest = {
                    enabled = true
                }
                web = {
                    enabled = true
                    root = "../myWebProject"
                    src = "../myWebProject/src/main/java"
                    srcGen = "../myWebProject/src/main/xtext-gen"
                    assets = "../myWebProject/src/main/webapp"
                }
                mavenLayout = true
            }
            code = {
                encoding = "UTF-8"
                lineDelimiter = "\r\n"
                fileHeader = "/*\n * generated by Xtext \${version}\n */"
            }
        }
        cleaner = {
            exclude = "MyOtherLanguageWebModule.java"
        }
        language = StandardLanguage {
            name = "MyLang"
            fileExtensions = "lang"
            serializer = {
                generateStub = false
            }
            webSupport = {
                generateHtmlExample = true
                framework = "CODEMIRROR"
                generateJsHighlighting = false
                generateServlet = false
                generateWebXml=true 
            }
            junitSupport = {
                junitVersion = "5"
            }
        }
    }

build.gradle:

    dependencies {
    testCompile "org.junit.jupiter:junit-jupiter-api:5.1.0"
    testRuntime "org.junit.jupiter:junit-jupiter-engine:5.1.0"
    testCompile "org.eclipse.xtext:org.eclipse.xtext.testing:${xtextVersion}"

    compile project(':myOtherLang')
    compile project(':myXCoreModel')
    compile project(":util")

    compile group: 'org.eclipse.xtext', name: 'org.eclipse.xtext.ecore', version: '2.15.0'
    compile "org.eclipse.xtext:org.eclipse.xtext.xbase:${xtextVersion}"
}
sourceSets {
    mwe2 {}
}
configurations {
    mwe2 {
        extendsFrom compile
    }
    mwe2Compile.extendsFrom mainCompile
    mwe2Runtime.extendsFrom mainRuntime
}
sourceSets.mwe2.java.srcDir 'generator'

dependencies {
    mwe2Compile "org.eclipse.emf:org.eclipse.emf.mwe2.launch:2.9.1.201705291010"
    mwe2Compile "org.eclipse.xtext:org.eclipse.xtext.common.types:${xtextVersion}"
    mwe2Compile "org.eclipse.xtext:org.eclipse.xtext.xtext.generator:${xtextVersion}"
    mwe2Compile "org.eclipse.xtext:xtext-antlr-generator:[2.1.1, 3)"

    //added for xcore support
    mwe2Compile 'org.eclipse.emf:org.eclipse.emf.ecore.xcore:1.3.1'
    mwe2Compile 'org.eclipse.emf:org.eclipse.emf.codegen.ecore.xtext:+'
}

task generateXtextLanguage(type: JavaExec) {
    main = 'org.eclipse.emf.mwe2.launch.runtime.Mwe2Launcher'
    classpath = project.sourceSets.mwe2.runtimeClasspath
    inputs.file "path/GenerateMyLang.mwe2"
    inputs.file "path/MyLang.xtext"
    outputs.dir "src-gen"
    args += "path/GenerateMyLang.mwe2"
    args += "-p"
    args += "rootPath=/${projectDir}/.."
}

test {
    useJUnitPlatform()
}
generateXtext.dependsOn(generateXtextLanguage)
clean.dependsOn(cleanGenerateXtextLanguage)
eclipse.classpath.plusConfigurations += [configurations.mwe2]
Zannith
  • 429
  • 4
  • 21

1 Answers1

1

i have doubts if this will work. the code you copy from does not generate an xtext language you should move custom modules to a separate gradle project and thus compile it separately. alernatively you can experiment with gradle buildSrc/separate source folder code

(am not sure if this works for this usecase)

dependencies {
    compile "org.eclipse.xtext:org.eclipse.xtext:${xtextVersion}"
    compile "org.eclipse.xtext:org.eclipse.xtext.xbase:${xtextVersion}"
}
sourceSets {
    mwe2 {}
}
configurations {
    mwe2 {
        extendsFrom compile
    }
    mwe2Compile.extendsFrom mainCompile
    mwe2Runtime.extendsFrom mainRuntime
}
sourceSets.mwe2.java.srcDir 'generator'

dependencies {
    mwe2Compile "org.eclipse.emf:org.eclipse.emf.mwe2.launch:2.9.1.201705291010"
    mwe2Compile "org.eclipse.xtext:org.eclipse.xtext.common.types:${xtextVersion}"
    mwe2Compile "org.eclipse.xtext:org.eclipse.xtext.xtext.generator:${xtextVersion}"
    mwe2Compile "org.eclipse.xtext:xtext-antlr-generator:[2.1.1, 3)"
}

task generateXtextLanguage(type: JavaExec) {
    main = 'org.eclipse.emf.mwe2.launch.runtime.Mwe2Launcher'
    classpath = project.sourceSets.mwe2.runtimeClasspath
    inputs.file "src/org/xtext/example/mydsl/GenerateMyDsl.mwe2"
    inputs.file "src/org/xtext/example/mydsl/MyDsl.xtext"
    outputs.dir "src-gen"
    args += "src/org/xtext/example/mydsl/GenerateMyDsl.mwe2"
    args += "-p"
    args += "rootPath=/${projectDir}/.."
}

generateXtext.dependsOn(generateXtextLanguage)
clean.dependsOn(cleanGenerateXtextLanguage)
eclipse.classpath.plusConfigurations += [configurations.mwe2]
Christian Dietrich
  • 11,778
  • 4
  • 24
  • 32
  • Okay maybe i'm missing a simpler way to accomplish what i'm trying to do and the StateMachine/Entity example just confused me. My end goal is to have my two grammar projects and their corresponding .ide projects be setup for services through a single web project. I can give more information on that if needed. Is there maybe another example I could look at to give me direction? – Zannith Jan 02 '19 at 18:08
  • Well what about putting the servlet to a common web project then – Christian Dietrich Jan 02 '19 at 18:09
  • I believe that's the path I am currently trying. I have my single Servlet class and in its `init` method I am launching the webSetup for each dsl. Now to avoid the generation confusion in my original question. Instead of extending the `AbstractDslWebModule` class, I just extended the `DefaultWebModule` class. But something is still failing here. When the servlet runs It fails to inject the XtextServiceDispatcher instance I have bound – Zannith Jan 02 '19 at 20:30
  • doesnt the same as the jetty sample does work for you? – Christian Dietrich Jan 02 '19 at 20:35
  • No, that's where I am getting the error in my original question. I did have everything copied as exactly as I could. I could run the workflows and everything looked good in my workspace. But upon doing the jettyRun I would get that reference error – Zannith Jan 02 '19 at 20:47
  • Okay, After making that change I'm looking into this error `Task :com.selinc.logic.program:compileMwe2Java FAILED path/MyGeneratorModule.java:2: error: package org.eclipse.xtext does not exist import org.eclipse.xtext.Grammar;` followed by a bunch more errors regarding that `GeneratorModule` class – Zannith Jan 02 '19 at 21:00
  • Sure you changed the classpath correctly for the mwe deps – Christian Dietrich Jan 02 '19 at 21:01
  • fairly certain, but i was using mwe2 command not mwe2Compile (Not sure the exact difference) but if i change it to mwe2Compile I then get `ERROR XtextGeneratorResourceSetInitializer - Couldn't initialize Xcore support.` Updating my question to show my full build.gradle file – Zannith Jan 02 '19 at 21:11
  • Well I don’t know what all you use. That setup worked fine for me. Maybe you changed too much. – Christian Dietrich Jan 02 '19 at 21:12
  • Hm, I didn't think the xcore dependency would be relevant. Is it possible that would conflict? That is the only real difference I see between my project and the jetty example. Oh and i added some detail to my build.gradle file in the original question – Zannith Jan 02 '19 at 21:17
  • Am not sure maybe you should add the xcore stuff to mwe and mwecompile then – Christian Dietrich Jan 02 '19 at 21:44
  • I'm starting to worry this might be a conflict with xcore. I tried a few combinations of things. also ended up needing to mwe2 and mwe2Compile `emf.mwe2.launch`. Now it seems to have an issue parsing my xcore model with error `Content is not allowed in prolog`. I'm going to keep working on it tomorrow. Thank you for all your help on this – Zannith Jan 02 '19 at 22:17
  • I don’t understand why you don’t go the easy way and move the custom generator to a separate module then – Christian Dietrich Jan 03 '19 at 08:35
  • I got multiple languages recognized through my servlet now. But now I have injection issues. If I get those settled I will post how I set things up. Seems @Inject annotation doesn't work, but everything has to be retrieved through injector.getInstance, But that's another problem. Thanks again for your help! – Zannith Jan 03 '19 at 20:00
  • As a final comment on this, I had conflicting versions which caused additional issues causing me not to recognize the quick fix Christian suggested, but the solution to my original question was indeed simply pulling the generatorModule into a separate gradle project. I do wonder if the Xtext Jetty example could be changed to reflect this suggested structure. Unless it has its own reason to use that method of course – Zannith Jan 09 '19 at 17:27