Making Guice more Scala friendly

Guice might be one of the few libraries that is easier to use in Java than it is in Scala. The main reason for this is the absence of class literals in Scala. Instead of writing Service.class in Scala we write classOf[Service] which is longer and less readable. To illustrate this lets compare two Guice modules, one defined in Java and the other in Scala.

Below we have a small Guice module (copied from the documentation of AbstractModule) defined in Java.

public class MyModule extends AbstractModule {
  protected void configure() {
    bind(Service.class).to(ServiceImpl.class).in(Singleton.class);
    bind(CreditCardPaymentService.class);
    bind(PaymentService.class).to(CreditCardPaymentService.class);
    bindConstant().annotatedWith(Names.named("port")).to(8080);
  }
}

In Scala the above code would be:

class MyModule extends AbstractModule {
   protected def configure() {
     bind(classOf[Service]).to(classOf[ServiceImpl]).in(classOf[Singleton])
     bind(classOf[CreditCardPaymentService])
     bind(classOf[PaymentService]).to(classOf[CreditCardPaymentService])
     bindConstant().annotatedWith(Names.named("port")).to(8080)
   }
 }

As you can see the code is longer and it looses the DSL feel that it has in the Java version. This fact may lead Scala developers away from Guice since defining Guice modules in Scala feels awkward and leaves a lot to be desired.

For this reason I’ve created a small project, called sse-guice, that extends Guice’s internal DSL with methods that make defining Guice modules in Scala more pleasant.

What I’ve done is to extend the binder interfaces of Guice (defined in com.google.inject.binder package) and add a method that takes a Manifest for each method that takes a Class as a parameter. Furthermore I’ve extended the AbstractModule class (the entry point of the Guice internal DSL) and added a bind method that accepts a Manifest and I’ve also overridden all the methods that return a binder interface to return the extended binder interfaces provided by sse-guice.

By utilizing sse-guice the above module can be rewritten as:

class MyModule extends ScalaModule {
  protected def configure() {
    bind[Service].to[ServiceImpl].in[Singleton]
    bind[CreditCardPaymentService]
    bind[PaymentService].to[CreditCardPaymentService]
    bindConstant().annotatedWithName("port").to(8080)
  }
}

As you can see the code now is shorter, easier to read and feels like a proper internal DSL.

Another benefit of using Manifest as a parameter is that we can now avoid creating TypeLiterals when we bind generic types. To bind a generic type in Guice you have to write:

bind(new TypeLiteral[Validator[Registration]] {}).to(classOf[RegistrationVSpec])

but when using sse-guice we can simply write:

bind[Validator[Registration]].to[RegistrationVSpec]

because Manifest also holds any type arguments and sse-guice automatically creates a TypeLiteral when the Manifest contains type arguments.

Using self types for trait composition

While using traits in a small Scala project, I finally understood when to use self types. Self types are often characterized by Scala newbies as an incomprehensible language feature with no obvious usage. After coding with traits for a while I understood that self types are an essential information hiding tool for composing traits.

I am coding a small JMX library in Scala, similar to Spring’s JMX module and to the jmxutils library. In my project I have a MBeanInfoAssembler trait, that is a strategy interface, whose role is to create a ModelMBeanInfo from a Class. Implementations of that trait will use reflection to discover the attributes and operations that will be used to export instances of the Class to JMX.

trait MBeanInfoAssembler {  
  def createMBeanInfo(clazz: Class[_]): ModelMBeanInfo
}

The first implementation of the trait was the SimpleMBeanInfoAssembler class which uses reflection and some conventions to discover the attributes and operations.

class SimpleMBeanInfoAssembler extends MBeanInfoAssembler {

  def createMBeanInfo(clazz: Class[_]): ModelMBeanInfo =
    new ModelMBeanInfoSupport(clazz.getName,
                              clazz.getSimpleName,
                              attributes(clazz),
                              Array(), 
                              operations(clazz),
                              Array())

  private def attributes(c: Class[_]): Array[ModelMBeanAttributeInfo] = {
    //find the attributes from the class using reflection
  }

  private def operations(c: Class[_]): Array[ModelMBeanOperationInfo] = {
    //find the operations from the class using reflection
  }
}

In the above code I have removed the implementations of the attributes and operations methods because they are not important for this example. What is important is the createMBeanInfo method which just calls the ModelMBeanInfoSupport constructor with the results of the attributes and operations methods. If we leave the code like this, when we try to provide a second implementation of the MBeanInfoAssembler trait we will probably copy-paste that method’s code.

In Scala, traits can have concrete methods so our first though is to move the implementation of the createMBeanInfo method to the MBeanInfoAssembler trait. After doing that our trait becomes:

trait MBeanInfoAssembler {
  def createMBeanInfo(clazz: Class[_]): ModelMBeanInfo =
    new ModelMBeanInfoSupport(clazz.getName,
                              clazz.getSimpleName,
                              attributes(clazz),
                              Array(), 
                              operations(clazz),
                              Array())

  def attributes(c: Class[_]): Array[ModelMBeanAttributeInfo]

  def operations(c: Class[_]): Array[ModelMBeanOperationInfo]
}

and the implementation:

class SimpleMBeanInfoAssembler extends MBeanInfoAssembler {
  
  def attributes(c: Class[_]): Array[ModelMBeanAttributeInfo] = {
    //find the attributes from the class using reflection
  }

  def operations(c: Class[_]): Array[ModelMBeanOperationInfo] = {
    //find the operations from the class using reflection
  }
}

This refactoring has the obvious advantage of removing the repetition that would be needed to create multiple implementations of MBeanInfoAssembler but also one major disadvantage over our previous code.

In order to support the implementation of the createMBeanInfo method the MBeanInfoAssembler trait gets updated with two new public abstract methods (attributes and operations). Those methods are useless to the clients of the trait, who only want to create a ModelMBeanInfo from a Class, and are there only to support the trait’s implementation. To correct this defect in our design we need to do another refactoring by introducing a new trait and connecting the two traits together using a self type annotation.

If you are new to Scala you might wonder what is a self type? In the Scala documentation self types are described as a way to “declare the type of the value this explicitly” which might be accurate but sounds at least confusing for a newbie like me.

In a well designed object-oriented system we achive reuse and flexibility when our system has lots of small objects that have a single responsibility and are explicitely connected using interfaces that represent the role of the connection. Usually those connections are made using constructor arguments. The power of such system comes from the testability and reusability of the small objects and the flexibility of composing those objects to solve a particular problem.

Since traits in Scala can have code (method implementations), if we want to create an equally well designed and flexible system using traits we need to be able to do the same. The problem is that traits do not have constructors so we need a new construct to declare trait dependencies and also a way to compose traits together. The solution to the first problem are the self type annotations and the solution to the second is multiple inheritance.

In the previous example the MBeanInfoAssembler trait had many responsibilities assigned to it. It must be able to create a ModelMBeanInfo given a Class and it must also extract any metadata in order to find the right attributes and operations for the given Class. We decide to move the second responsibility to a new trait called MBeanMetadataExtractor that has the attributes and operations methods.

trait MBeanMetadataExtractor {
  
  def attributes(c: Class[_]): Array[ModelMBeanAttributeInfo]
  
  def operations(c: Class[_]): Array[ModelMBeanOperationInfo]
}

Now we need to update the MBeanInfoAssembler trait and to somehow connect it to the MBeanMetadataExtractor trait so it can use the attributes and operations methods. To do this we will use a self type annotation.

trait MBeanInfoAssembler {
  
  this: MBeanMetadataExtractor =>
  
  def createMBeanInfo(clazz: Class[_]): ModelMBeanInfo = {
    new ModelMBeanInfoSupport(clazz.getName,
                              clazz.getSimpleName,
                              attributes(clazz),
                              Array(),
                              operations(clazz),
                              Array())
  }
}

The syntax of the self type annotation is this: MBeanMetadataExtractor => and it tells the compiler that a MBeanInfoAssembler can be implemented in a class only if that class also implements the MBeanMetadataExtractor trait. Using this assumption the compiler makes the methods of the MBeanMetadataExtractor available for use in the MBeanInfoAssembler (in our case the attributes and operations methods).

The class SimpleMBeanInfoAssembler now has to implement both MBeanInfoAssembler and MBeanMetadataExtractor.

class SimpleMBeanInfoAssembler extends MBeanInfoAssembler with MBeanMetadataExtractor {
  
  def attributes(c: Class[_]): Array[ModelMBeanAttributeInfo] = {
    //find the attributes from the class using reflection
  }
  
  def operations(c: Class[_]): Array[ModelMBeanOperationInfo] = {
    //find the operations from the class using reflection
  }
}

By doing the above changes we were able to hide the attributes and operations methods from the clients of the MBeanInfoAssembler trait. Obviously those methods exist in the public interface of SimpleMBeanInfoAssembler but in a well designed system other classes will connect with SimpleMBeanInfoAssembler by using one of its traits (interfaces) so this is not a problem.

In conclusion, if we want to move method implementations inside traits then we risk polluting the interface of those traits with abstract methods that support the implementation of the concrete methods and are unrelated with the main responsibility of the trait. A solution to this problem is to move those abstract methods in other traits and compose the traits together using self type annotations and multiple inheritance.

Statically weaving JPA entities for EclipseLink using Maven

EclipseLink provides advanced JPA features such as lazy-loading, change tracking and fetch groups using bytecode weaving. To use bytecode weaving you can either dynamically instrument your entity classes at runtime (via a jvm agent) or use a tool to statically process the .class files after compilation. In this post we will present how to use EclipseLink’s static weaver in a Maven project.

To enable static weaving in a Maven based project we have to add the Eclipselink weaver in the process-classes phase of the Maven’s build life cycle. The process-classes phase happens after the compile phase and allows the post-processing of files generated in compile phase. In our case, the EclipseLink weaver will post-process the .class files produced by the compiler to add extra bytecodes that implement the desired JPA functionality (lazy-loading, etc).

In the below code we use the Maven AntRun plugin to call (via the java ANT task) the command line version of the EclipseLink’s static weaver. Please note that the class name of the weaver is org.eclipse.persistence.tools.weaving.jpa.StaticWeave and not org.eclipse.persistence.tools.weaving.StaticWeave as the EclipseLink JPA Extensions wiki page says.

<build>
 <plugins>
   <plugin>
     <artifactId>maven-antrun-plugin</artifactId>
     <executions>
       <execution>
         <phase>process-classes</phase>
         <configuration>
           <tasks>
             <java classname="org.eclipse.persistence.tools.weaving.jpa.StaticWeave"
                   classpathref="maven.runtime.classpath" fork="true">
               <arg line="-loglevel FINE -persistenceinfo src/main/resources target/classes target/classes"/>
             </java>
           </tasks>
         </configuration>
         <goals>
           <goal>run</goal>
         </goals>
       </execution>
     </executions>
   </plugin>
 </plugins>
</build>

In addition to the pom.xml changes in order to use static weaving in EclipseLink you have to set the eclipselink.weaving property to static in the META-INF/peristence.xml file.

<property name="eclipselink.weaving" value="static" />

For more information about EclipseLink’s static weaving see the How to Configure Static Weaving for JPA Entities section of the Using EclipseLink JPA Extensions wiki page.

Using Dependency Injection in Struts2 for stateless EJBs part 2

This is the second, and last part of the Using Dependency Injection in Struts2 for stateless EJBs series of posts. In this post I will present a utility class that can be used to make the creation of Guice bindings for EJB3s easier.

Introducing EjbBinder

Our goal is to make an easier API, specifically for creating bindings of EJB3s, and make the specification of the JNDI name optional, when possible. The below code is a new version of the EjbModule class that uses a new class, called EjbBinder, that we are going to present in this post.

public class EjbModule implements Module {

  public void configure(Binder binder) {
    // Bind Context to the default InitialContext.
    binder.bind(Context.class).to(InitialContext.class);

    EjbBinder ejbs = new EjbBinder(binder, new GlassfishEjbJndiNameStrategy());
    ejbs.bindRemote(CurrencyManagerRemote.class);
    ejbs.bind(DatesManagerRemote.class, "com.tzavellas.dates.ejb.DatesManagerBean");
  }
}

EjbBinder contains two methods named bind and bindRemote. The bind method receives as arguments the expected class and JNDI name and simply uses Binder and JndiItegration to create a binding. The bindRemote method takes as an argument the remote interface of a sesion EJB3 and creates a binding using a JNDI name retrieved from the EjbJndiNameStrategy, that is specified in the EjbBinder constructor (BTW the CurrencyManagerRemote EJB interface in the above code does not relate with the application that we developed in the previous post and it is here to illustrate the bindRemote method).

The definition of the EjbJndiNameStrategyinterface:

public interface EjbJndiNameStrategy {

  String interfaceToJndiName(Class<?> beanInterface);
}

The implementation of EjbBinder:

import com.google.inject.Binder;
import com.google.inject.binder.ScopedBindingBuilder;
import static com.google.inject.jndi.JndiIntegration.fromJndi;

public class EjbBinder {

  private Binder binder;
  private EjbJndiNameStrategy jndiNameStrategy;

  public EjbBinder(Binder binder, EjbJndiNameStrategy nameStrategy) {
    this.binder = binder;
    this.jndiNameStrategy = nameStrategy;
  }

  public <T> ScopedBindingBuilder bindRemote(Class<T> beanInterface) {
    return bind(beanInterface,
                jndiNameStrategy.interfaceToJndiName(beanInterface));
  }

  public <T> ScopedBindingBuilder bind(Class<T> beanInterface, String jndiName) {
    return binder.bind(beanInterface)
                 .toProvider(fromJndi(beanInterface, jndiName));
  }
}

Application Server Specific Naming Strategies

When you create a new EJB and you do not specify a JNDI name, the application server assigns a default name for you. So, if you have an implementation of EjbJndiNameStrategy that uses the naming rules of your application server you could avoid the need to specify a JNDI name when creating the EJB and when creating the binding of the EJB to Guice.

Below we have two implementations of the EjbJndiNameStrategy that can infer the JNDI name of an EJB’s remote client interface using the remote interface’s class for the Glassfish and JBoss application servers.

For the Glassfish application server the default global JNDI name of an EJB with a remote interface is the fully qualified name of the remote interface.

public class GlassfishEjbJndiNameStrategy implements EjbJndiNameStrategy {

  public String interfaceToJndiName(Class beanInterface) {
    return beanInterface.getName();
  }
}

For the JBoss application server the default JNDI name for the remote interface of an EJB is earName/beanName/remote.

//WARNING: Not tested!
public class JbossEjbJndiNameStrategy implements EjbJndiNameStrategy {

  private String earName = "";

  public JbossEjbJndiNameStrategy() { }

  public JbossEjbJndiNameStrategy(String earName) {
    if (earName != null && "".equals(earName.trim()))
      this.earName = earName + "/";
  }

  public String interfaceToJndiName(Class<?> beanInterface) {
    return earName + interfaceToBeanName(beanInterface) + "/remote";
  }

  protected String interfaceToBeanName(Class<?> beanInterface) {
    String name = beanInterface.getSimpleName();
    if (name.endsWith("Remote"))
      name = name.replace("Remote", "");
    return name + "Bean";
  }
}