1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188
|
<chapter id="Guice1">
<title>Guice 3.0 Integration</title>
<para>RESTEasy has some simple integration with Guice 3.0. RESTEasy will scan the binding types for a Guice Module
for @Path and @Provider annotations. It will register these bindings with RESTEasy. The guice-hello
project that comes in the RESTEasy examples/ directory gives a nice example of this.</para>
<programlisting>
@Path("hello")
public class HelloResource
{
@GET
@Path("{name}")
public String hello(@PathParam("name") final String name) {
return "Hello " + name;
}
}
</programlisting>
<para>First you start off by specifying a JAX-RS resource class. The HelloResource is just that. Next you
create a Guice Module class that defines all your bindings:</para>
<programlisting>
import com.google.inject.Module;
import com.google.inject.Binder;
public class HelloModule implements Module
{
public void configure(final Binder binder)
{
binder.bind(HelloResource.class);
}
}
</programlisting>
<para>You put all these classes somewhere within your WAR WEB-INF/classes or in a JAR within WEB-INF/lib. Then
you need to create your web.xml file. You need to use the GuiceResteasyBootstrapServletContextListener as
follows</para>
<programlisting>
<![CDATA[
<web-app>
<display-name>Guice Hello</display-name>
<context-param>
<param-name>resteasy.guice.modules</param-name>
<param-value>org.jboss.resteasy.examples.guice.hello.HelloModule</param-value>
</context-param>
<listener>
<listener-class>
org.jboss.resteasy.plugins.guice.GuiceResteasyBootstrapServletContextListener
</listener-class>
</listener>
<servlet>
<servlet-name>Resteasy</servlet-name>
<servlet-class>
org.jboss.resteasy.plugins.server.servlet.HttpServletDispatcher
</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Resteasy</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
</web-app>
]]>
</programlisting>
<para>GuiceResteasyBootstrapServletContextListener is a subclass of ResteasyBootstrap, so you can use
any other RESTEasy configuration option within your web.xml file. Also notice that there is a
resteasy.guice.modules context-param. This can take a comma delimited list of class names that
are Guice Modules.</para>
<section>
<title>Request Scope</title>
<para>
Add the RequestScopeModule to your modules to allow objects to be scoped to the HTTP request by adding
the @RequestScoped annotation to your fields in resource classes. All the objects injectable via the @Context annotation are
also injectable, except ServletConfig and ServletContext.
Note that RequestScopeModule will already be added if any of your modules extends com.google.inject.servlet.ServletModule.
In such cases you should not add it again to avoid injector creation errors.
</para>
<programlisting>
<![CDATA[
import javax.inject.Inject;
import javax.servlet.http.HttpServletRequest;
import javax.ws.rs.core.Context;
import org.jboss.resteasy.plugins.guice.RequestScoped;
public class MyClass
{
@Inject @RequestScoped @Context
private HttpRequest request;
}
]]>
</programlisting>
</section>
<section>
<title>Binding JAX-RS utilities</title>
<para>
Add the JaxrsModule to bind javax.ws.rs.ext.RuntimeDelegate, javax.ws.rs.core.Response.ResponseBuilder, javax.ws.rs.core.UriBuilder, javax.ws.rs.core.Variant.VariantListBuilder and org.jboss.resteasy.client.ClientExecutor.
</para>
</section>
<section>
<title>Configuring Stage</title>
<para>
You can configure the stage Guice uses to deploy your modules by specific a context param, resteasy.guice.stage.
If this value is not specified, RESTEasy uses whatever Guice's default is.
</para>
<programlisting>
<![CDATA[
<web-app>
<display-name>Guice Hello</display-name>
<context-param>
<param-name>resteasy.guice.modules</param-name>
<param-value>org.jboss.resteasy.examples.guice.hello.HelloModule</param-value>
</context-param>
<context-param>
<param-name>resteasy.guice.stage</param-name>
<param-value>PRODUCTION</param-value>
</context-param>
<listener>
<listener-class>
org.jboss.resteasy.plugins.guice.GuiceResteasyBootstrapServletContextListener
</listener-class>
</listener>
<servlet>
<servlet-name>Resteasy</servlet-name>
<servlet-class>
org.jboss.resteasy.plugins.server.servlet.HttpServletDispatcher
</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Resteasy</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
</web-app>
]]>
</programlisting>
</section>
<section>
<title>Custom Injector creation</title>
<para>
GuiceResteasyBootstrapServletContextListener can be extended to allow more flexibility in the way the Injector and Modules
are created. Three methods can be overridden: getModules(), withInjector() and getStage(). Register your subclass as the
listener in the web.xml.
</para>
<para>
Override getModules() when you need to pass arguments to your modules' constructor or perform more complex operations.
</para>
<para>
Override withInjector(Injector) when you need to interact with the Injector after it has been created.
</para>
<para>
Override getStage(ServletContext) to set the Stage yourself.
</para>
<programlisting>
<![CDATA[
<web-app>
<!-- other tags omitted -->
<listener>
<listener-class>
org.jboss.resteasy.plugins.guice.GuiceResteasyBootstrapServletContextListener
</listener-class>
</listener>
</web-app>
public class MyServletContextListener extends GuiceResteasyBootstrapServletContextListener
{
@Override
protected List<? extends Module> getModules(ServletContext context)
{
return Arrays.asList(new JpaPersistModule("consulting_hours"), new MyModule());
}
@Override
public void withInjector(Injector injector)
{
injector.getInstance(PersistService.class).start();
}
}
]]>
</programlisting>
</section>
</chapter>
|