Gradle plugin - custom task closure delegate error


(martinhanus.gradle) #1

Hi,

I’m working on custom plugin and I encountered problem with closure delegates. I created simple custom task

class DevelBuildTask extends DefaultTask {
    private Logger log
      DevelBuildTask() {
        log = project.getLogger()
    }
      private void runMaven(String tempCmd, File tempDir) {
        String cmd = ""
        if (System.properties.get('os.name').toLowerCase().contains("win")) {
            cmd = cmd.concat("cmd /c ")
        }
        cmd = cmd.concat(tempCmd)
        File runDir = tempDir != null ? tempDir : new File(".")
          Process proc = cmd.execute(null, runDir)
        proc.inputStream.eachLine {line ->
            log.debug(line)
        }
    }
}

In my plugin class I have

class DevelPlugin implements Plugin<Project> {
    void apply(final Project project) {
            project.task('build', type: DevelBuildTask) << {
                println("Running Build subsystem task ...")
            }
    }
}

When I try to run this, I get following exceptions:

Caused by: groovy.lang.MissingPropertyException: Could not find property 'log' on task ':build'.
        at org.gradle.api.internal.AbstractDynamicObject.propertyMissingException(AbstractDynamicObject.java:43)
        at org.gradle.api.internal.AbstractDynamicObject.getProperty(AbstractDynamicObject.java:35)
        at org.gradle.api.internal.CompositeDynamicObject.getProperty(CompositeDynamicObject.java:94)
        at com.ysoft.gradle.DevelBuildTask_Decorated.getProperty(Unknown Source)
        at com.ysoft.gradle.DevelBuildTask$_runMaven_closure1.doCall(DevelBuildTask.groovy:123)
        at com.ysoft.gradle.DevelBuildTask.runMaven(DevelBuildTask.groovy:119)
        at com.ysoft.gradle.DevelBuildTask.this$4$runMaven(DevelBuildTask.groovy)

To me, It seems like “log.debug(line)” has delegate set to target method, in this case “proc.inputStream.eachLine”. But as as far as I know, all closures should by default have set delegation to OWNER_FIRST. However, I’m not sure if there isn’t some “gradle magic” happening in background. Any help is much appreciated.

Thanks


(René Groeschke) #2

Hello Matthew, I think the problem is that you try to access a private property from a closure.

Can you retry your code with replacing

private Logger log

with

Logger log

cheers, René


(martinhanus.gradle) #3

Hi Rene

Your fix works. I can use log instance (and also call other methods) once I removed ‘private’ access modifier.

Thanks for your help