Search code examples
groovygroovyshell

How to use @SourceURI annotation to retrieve the full path of the script file in Groovy 2.3?


I need to retrieve at runtime the full path of the script file in Groovy 2.3. Actually I have the same problem than the one described here: get path to groovy source file at runtime.

My script can be executed from GroovyShell or not.

My script is located at :

C:\users\myname\documents\scripts\myscript.groovy

=> I simpy want to retrieve this path at runtime.

If I use the solution that was accepted:

println new File(".").absolutePath

what I get is actually :

C:\groovy-2.3.7\.

which is the groovy home folder. That is not correct. The other proposed answer ie :

URL scriptUrl = getClass().classLoader.resourceLoader.loadGroovySource(getClass().name)

works only when my script is in the classpath, or when it is loaded at groovy startup using load directive in groovy-starter.conf. Otherwise it returns null. I could use this method but it is not satisfying because it is like passing a parameter and the goal here is that users to be able to execute the script from anywhere without modification or configuration.

I also red this JIRA who focus on this question: JIRA-1642

Solution seems to use the @SourceURI annotation that was created for this purpose. Problem is I am not able to make it work. I try to execute the code usage shown at: SourceURI

@groovy.transform.SourceURI def sourceURI
assert sourceURI instanceof java.net.URI
path = sourceURI.toString()
println "path = $path"

What I get is (groovy 2.3.7) is not the path but the source code :

path = data:,@groovy.transform.SourceURI%20def%20sourceURI%0A%0A%20assert%20sourceURI%20instanceof%20java.net.URI%0Apath%20=%20sourceURI.toString()%0Aprintln%20%22path%20=%20$path%22

How to use the @SourceURI annotation to retrieve the path of the script file ?


Solution

  • I was looking for the same script path information you were. I noticed that when running the following via the shell:

    @groovy.transform.SourceURI def sourceURI
    assert sourceURI instanceof java.net.URI
    sourceURI.properties.each { i -> 
        println i
    }
    

    I get the following, useful results (note the value in path):

    rawAuthority=null
    opaque=false
    scheme=file
    rawQuery=null
    port=-1
    rawUserInfo=null
    path=/home/ttresans/GroovyScripts/TestSourceURI.groovy
    class=class java.net.URI
    absolute=true
    schemeSpecificPart=/home/ttresans/GroovyScripts/TestSourceURI.groovy
    rawPath=/home/ttresans/GroovyScripts/TestSourceURI.groovy
    query=null
    fragment=null
    host=null
    authority=null
    rawFragment=null
    userInfo=null
    rawSchemeSpecificPart=/home/ttresans/GroovyScripts/TestSourceURI.groovy
    

    But if I paste the same thing into the GroovyConsole, I get the following:

    rawAuthority=null
    opaque=true
    scheme=data
    rawQuery=null
    port=-1
    rawUserInfo=null
    path=null
    class=class java.net.URI
    absolute=true
    schemeSpecificPart=,@groovy.transform.SourceURI def sourceURI
    assert sourceURI instanceof java.net.URI
    sourceURI.properties.each { i -> 
        println i
    }
    
    rawPath=null
    query=null
    fragment=null
    host=null
    authority=null
    rawFragment=null
    userInfo=null
    rawSchemeSpecificPart=,@groovy.transform.SourceURI%20def%20sourceURI%0Aassert%20sourceURI%20instanceof%20java.net.URI%0AsourceURI.properties.each%20%7B%20i%20-%3E%20%0A%20%20%20%20println%20i%0A%7D%0A
    

    This is on Groovy 2.3.9 on Ubuntu.

    So it seems like the GroovyConsole's startup might be a problem, but the annotation does in fact produce the desired path.