Class JavaThisBlock

java.lang.Object
com.cloudbees.groovy.cps.impl.JavaThisBlock
All Implemented Interfaces:
Block, Serializable

public class JavaThisBlock extends Object implements Block
Resolves the current Env.closureOwner() value.

In Groovy, the this keyword and closure interacts and therefore behaves differently from Java this. Specifically, Groovy tries to maintain an illusion that closure is a part of the native language feature and tries to hide the fact that it is implemented by another class.

So when executing inside a closure, like the following, this refers to Foo instance, not the instance of the anonymous closure class, which is the actual this as far as Java bytecode is concerned at the runtime.


 class Foo {
   def foo() {
     def closure = { ->
       this.x = 1;     
     }
     closure();     
   }
 }
 

So let's refer to the Java version of this as {code javaThis}, and let's refer to the Groovy version of this as groovyThis.

To make this more complicated, sometimes Groovy does need to refer to javaThis, to be able to refer to the closure itself. This happens when you call a method or access a property from inside the closure. In the following code, where a closure makes an assignment to a "dynamic variable" x, the actual translation of the code fragment is javaThis.x=1 (which would call Closure.setProperty(String, Object)), not groovyThis.x=1 (which would call Foo#setProperty()).


 class Foo {
   def foo() {
     def closure = { ->
       x = 1;     
     }
     ...     
   }
 }
 

Groovy defines no explicit syntax for javaThis. It can be only used implicitly.

Author:
Kohsuke Kawaguchi
See Also:
  • Constructor Details

    • JavaThisBlock

      public JavaThisBlock()
  • Method Details

    • eval

      public Next eval(Env e, Continuation k)
      Description copied from interface: Block
      Executes this expression, then pass the result to the given continuation when it's available.

      To be more precise, this method does not evaluate the expression by itself synchronously. Instead, the evaluation is done by the caller by repeatedly step executing the resulting Next object.

      Specified by:
      eval in interface Block