1. richard_hauswald
  2. hessian-guice

Overview

hessian-guice

hessian-guice provides with an easy way to export interface implementations as hessian web service using guice.

Build status

Build Status

Usage

Include as maven dependency

hessian-guice is available on central and can be included as maven dependency using the following snippet:

<dependency>
    <groupId>de.rhauswald.guice.hessian.hessian-guice</groupId>
    <artifactId>hessian-guice</artifactId>
    <version>${your desired version}</version>
</dependency>

Released versions are tagged using the version number. Choose the most recent one from the tag list in the box on the right side of this page. As soon as the jgitflow-maven-plugin supports updating version numbers in README.md files this paragraph will be updated with the latest version with each release.

Annotation based configuration

Convention over configuration

Annotation based configuration is using conventions to reduce the configuration effort to a minimum. To export all your services using the url schema "http(s)://server.name.tld/<contextPath>/<ApiInterfaceClassSimpleName>;" simply annotate each api implementation class with @HessianWebService...

package ...;

import ...UserService;
import de.rhauswald.guice.hessian.HessianWebService;

@HessianWebService
public class UserServiceImpl implements UserService {
    ...
}

... and hand over an instance of HessianWebServicesModule to the guice injector factory in your GuiceServletContextListener:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule("your web service implementations package")
        );
    }
}

Given you're deploying a war named example-web-service.war into a jetty serving http on port 80 into context path example-web-service, UserServiceImpl will be served using the url http://localhost/example-web-service/UserService.

Auto binding of annotated web service api implementations

hessian-guice will also bind the api class to the annotated api implementation. You can disable that behavior using the bindApiClazzToAnnotatedInstance property of the @HessianWebService annotation:

package ...;

import ...UserService;
import de.rhauswald.guice.hessian.HessianWebService;

@HessianWebService(bindApiClazzToAnnotatedInstance = false)
public class UserServiceImpl implements UserService {
    ...
}
Custom url pattern for a web service implementation

@HessianWebService allows to customize the url under which the web service will be available. To export this service using the url schema "http(s)://server.name.tld/<contextPath>/[urlPrefix]/users" provide @HessianWebService with a url:

package ...

import ...UserService
import de.rhauswald.guice.hessian.HessianWebService;

@HessianWebService(urlPattern = "/users")
public class UserServiceImpl implements UserService {
    ...
}
Multiple interfaces implemented by the web service implementation

In case your service implementation implements multiple interfaces you have to tell hessian-guice which of these interfaces is the one of your api:

package ...

import ...UserService
import ...AnotherInterface
import de.rhauswald.guice.hessian.HessianWebService;

@HessianWebService(apiClazz = UserService.class)
public class UserServiceImpl implements UserService, AnotherInterface {
    ...
}
Url prefixing your hessian web services

You can also define a url prefix under which your hessian web services will be mapped. To export your service using the url schema "http(s)://server.name.tld/<contextPath>/hessian-web-services/UserService" provide the constructor of HessianWebServicesModule with a UrlPrefix:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;
import de.rhauswald.guice.hessian.UrlPrefix;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule(UrlPrefix.forPrefix("hessian-web-services"), "your web service implementation package")
        );
    }
}

Given you're deploying a war named example-web-service.war into a jetty serving http on port 80 into context path example-web-service, UserServiceImpl will now be served using the url http://localhost/example-web-service/hessian-web-services/UserService.

Manual configuration

hessian-guice also supports manual configuration in the EDSL style of GuiceServletContextListener. To manually bind UserServiceImpl to url "http(s)://server.name.tld/<contextPath>/Users" hand over a customized instance of HessianWebServicesModule to the guice injector factory in your GuiceServletContextListener:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;
import ...UserService;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule(){
                    @Override
                    protected void configureHessianWebServices() {
                        serveHessianWebService(UserService.class).usingUrl("/Users");
                    }
                }
        );
    }
}

Make sure that your web service implementation is known to guice using the api class as key. In other words: Make sure that a call to Injector.getInstance(UserService.class) will return your web service implementation instance.

Manual configuration on steroids

In case your classpath contains multiple implementations of your API class simple key consisting of just the API class is not enough. To tell hessian-guice which instance should be used to serve hessian web service request simply hand over the binding key to the serverHessianWebService method:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.Key;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;
import ...UserService;
import ...UserServiceHessianImpl;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule(){
                    @Override
                    protected void configureHessianWebServices() {
                        serveHessianWebService(UserService.class, Key.get(UserServiceHessianImpl.class)).usingUrl("/Users");
                    }
                }
        );
    }
}

The key you're providing is used to retrieve the actual instance to which a web service call will be dispatched. So you can work with all the com.google.inject.Key features of guice.

Manual configuration mixed with annotation based configuration

hessian guice also supports this. Given you want to use conventional configuration for all services but one, simply remove/do not add the @HessianWebService annotation to the one you want to configure the manual way and hand over a customized instance of HessianWebServicesModule to the guice injector factory in your GuiceServletContextListener:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;
import ...UserService;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule("your web service implementation package"){
                    @Override
                    protected void configureHessianWebServices() {
                        serveHessianWebService(UserService.class).usingUrl("/Users");
                    }
                }
        );
    }
}

Url prefixes can also be applied to all web services configured using annotation based configuration:

package ...;

import com.google.inject.Guice;
import com.google.inject.Injector;
import com.google.inject.servlet.GuiceServletContextListener;
import de.rhauswald.guice.hessian.HessianWebServicesModule;
import de.rhauswald.guice.hessian.UrlPrefix;
import ...UserService;

public class WebServiceGuiceServletContextListener extends GuiceServletContextListener {
    @Override
    protected Injector getInjector() {
        return Guice.createInjector(
                /* your guice modules */
                new HessianWebServicesModule(UrlPrefix.forPrefix("hessian-web-services"), "your web service implementation package"){
                    @Override
                    protected void configureHessianWebServices() {
                        serveHessianWebService(UserService.class).usingUrl("/Users");
                    }
                }
        );
    }
}