Resource filtering in gradle eclipse buildship

buildship
eclipse

(Adriano dos Santos Fernandes) #1

I’m converting a maven project with has resource filtering (substitution of ${properties} in config files) also working inside eclipse. I just save a property file and the builtin maven plugin (m2e) saves the processed file in the target folder.

I’m now converting this project to gradle and used the “filter ReplaceTokens”. It works in the command like when I do “gradle assemble” and saves the processed file to the build directory.

But inside eclipse the imported gradle project just uses a “bin” directory and there the file is not processed when saved.

May this be an incorrect use of gradle/buildship by me or that feature as maven does is not supported in buildship? If it’s supported, can you point me to a small project doing this?


(Stefan Oehme) #2

Hey Adriano,

this is not yet supported by Buildship. We would need task execution on auto build for that. That’s high on our priority list. If you are interested in contributing that feature, I’d be happy to walk you through the design process.

Cheers,
Stefan


(Julien HENRY) #3

Hi,

Same context: moving from Maven to Gradle, and on Eclipse side from m2e to BuildShip.

I’m interested to see proper resource filtering in Buildship. I can maybe help, since this “high priority” topic doesn’t seem to have been addressed after more than a year :slight_smile:

What is the best place to discuss this? Is there a JIRA / GitHub ticket somewhere?

Thanks

Julien


(Donát Csikós) #4

Hi,

The current state of affair is that the eclipse Gradle plugin can configure resource filters, but this information is not available via the EclipseProject model in the Tooling API. To implement the story one has to extend EclipseProject and consume the new information in the Buildship synchronization model.

You can follow up on this issue at eclipse/buildship#271 and on the linked stories. You can contribute to Gradle/Buildship via pull requests, we gladly guide you through the process.


(Julien HENRY) #5

Hi,

I have the impressions that we put 2 different things under the “resource filtering” concept.

  1. src/main/resources folder contains files that should be available on the classpath (to allow finding them with myClass.getResources()), but that should not be considered as source code. For example Eclipse should not try to compile .java files under src/test/resources, and also probably not validate all .js files in node_modules. The problem is that in Eclipse, there is no concept of “resource” folder. So there is a need to tell Eclipse to “filter” some files from being processed by the auto-build.

  2. variable substitution during resource files processing. This is called “filtering” in Maven, and I think this is why this is confusing. In Gradle we are using something like:

    processResources {
      filter ReplaceTokens, tokens: [
        'project.buildVersion': xxxxx
      ]
    }
    

In Eclipse, we wants to ensure that at runtime (like when running JUnit tests) the classpath contains the “resolved” resources, not the original ones.

I remember m2e spent a lot of time trying to find a working solution, that would not trigger recursive auto-builds.

When importing a Maven project into Eclipse with m2e, resource folders have all their content excluded:
<classpathentry excluding="**" kind="src" output="target/classes" path="src/main/resources">

It means Eclipse will not touch resources files at all. I guess the Maven Builder will take care to copy resources to the output folder, applying variable substitution if needed. I think the Gradle Builder could do the same.


(Donát Csikós) #6

Maybe there’s a solution for your use case. You can adjust the Eclipse project generation in the build script. You can define the same excluding pattern:

apply plugin: 'eclipse'

eclipse {
    classpath {
        file {
            whenMerged {
                def src = entries.find { it.path == 'src/main/resources' }
                src.excludes = ['**']
            }
        }
    }
}

Or, you can transform the sources folder to a directory inside the Gradle classpath container:

import org.gradle.plugins.ide.eclipse.model.Library
apply plugin: 'eclipse'

eclipse {
    classpath {
        file {
            whenMerged {
                entries.removeAll { it.path == 'src/main/resources' }
                entries += new Library(fileReference(file('src/main/resources')))
            }
        }
    }
}

(Julien HENRY) #7

That’s interesting options, but if I’m correct, none is 100% correct.

Option 1 (adding ‘**’ exclusion) alone will prevent files from being copied to the output folder. And consequently, running unit tests from Eclipse will not “see” them.

Option 2 doesn’t work because libraries are not exported to downstream projects. Using the Eclipse UI, I found that adding a class folder (+export it) is likely what is the more appropriate behavior.

Still the 2 options doesn’t support variable interpolation…