If you have Enterprise JavaBeans (EJB)
applications that are exposed using a no-interface view, you can expose
a RESTful interface to the enterprise bean using Java™ API for RESTful Web Services (JAX-RS).
By implementing JAX-RS annotated enterprise beans, you keep the EJB
functionality including transaction support, injection of Java EE components and resources, and other
EJB session bean capabilities.
Before you begin
Before EJB 3.1, enterprise beans that required an EJB local
client view also needed a separate Java interface,
usually located in a separate file, that declared the local view methods.
The enterprise bean specified that it implemented the EJB local view
interface using deployment descriptors or EJB annotations.
Using
the EJB 3.1 specification, you have the option of exposing a local
view of an enterprise bean without an explicit EJB local interface.
Instead, the enterprise bean has a no-interface client view that
is based on the public methods of your bean class. No-interface view
enterprise beans can be more simple to develop than a local view enterprise
bean for the following reasons:
- No-interface view enterprise beans do not require a separate Java interface declaration.
- No-interface view enterprise beans do not require specifying additional
metadata in the deployment descriptor or when using EJB annotations.
See the EJB 3.1 specification for more details on no-interface
views of an enterprise bean.
JAX-RS supports the use of enterprise
beans that declare a local business interface and no-interface view
enterprise beans.
우수 사례: Although you can
declare enterprise beans in different ways, it is a best practice
to directly implement the EJB business local interface and to always
declare the @javax.ejb.Local annotation. By using this method, the
EJB bean is required to implement the local business interface, which
eliminates errors in typing method names and changes to argument types.
By always using the @javax.ejb.Local annotation, if there are ever
multiple business interfaces, you can simply add the business interface
to the annotation value. You can also use this approach to modify
the enterprise bean using a deployment descriptor.
bprac
This
task describes implementing RESTful views of a no-interface view enterprise
bean.
About this task
You can create a simple enterprise bean with JAX-RS annotations.
Even though this task specifically describes how to implement RESTful
views of a no-interface view enterprise bean, it is important that
you consider the full scope of your application architecture and how
you want to expose resources as you decide your resource model and
determine which RESTful views are appropriate for your enterprise
beans application. These considerations are beyond the scope of this
task.
JAX-RS supports stateless and singleton session beans.
You can add JAX-RS annotations to the local interface of a session
bean. Also, with EJB 3.1, you can add JAX-RS annotations directly
to an EJB class if the enterprise bean exposes a no-interface view.
With
the EJB 3.1 packaging rules, you can add JAX-RS enterprise beans in
the web application archive (WAR) file either directly in the WEB-INF/classes
directory or using a Java archive
(JAR) file in the WEB-INF/lib directory. You can declare an enterprise
bean using annotations, or using an EJB deployment descriptor, or
using both annotations and a deployment descriptor.
JAX-RS
annotated enterprise beans in a stand-alone file or in a separate
ejb-jar file that is included in an EAR is not supported.
Procedure
- Create an enterprise bean. In the following
example, there is a simple EJB class called Organization.
This class takes advantage of the no-interface view class feature
introduced in the EJB 3.1 specification.
public class Organization {
public String getInformation() {
// return information via a String
}
}
- To expose an enterprise bean as a JAX-RS resource, complete
one of the following steps:
- In the WEB-INF/ ejb-jar.xml deployment descriptor file for
your enterprise bean, change your JAX-RS plain Java classes to become JAX-RS enabled enterprise
beans. For example, you can add the following code snippet to the
WEB-INF/ejb-jar.xml deployment descriptor:
<ejb-jar xmlns="http://java.sun.com/xml/ns/javaee" version="3.1"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/ejb-jar_3_1.xsd">
<!--
This file must exist in the WEB-INF/ directory of your WAR file.
See EJB 3.1 spec 20.4 for more details.
-->
<enterprise-beans>
<session>
<ejb-name>Organization</ejb-name>
<ejb-class>com.example.jaxrs.Organization</ejb-class>
<session-type>Stateless</session-type>
</session>
</enterprise-beans>
</ejb-jar>
If you want to make the enterprise
bean a singleton using the deployment descriptor, use <session-type>Singleton</
session-type> instead of <session-type>Stateless</session-type>.
- Add a @javax.ejb.Stateless annotation to the Java class of your enterprise bean. The following
example demonstrates a simple JAX-RS annotated enterprise bean:
package com.example.jaxrs;
@javax.ejb.Stateless
@javax.ws.rs.Path("/organization/")
public class Organization {
@javax.ws.rs.GET
@javax.ws.rs.Produces("text/plain")
public String getInformation() {
// return information via a String
}
}
If you want to make the enterprise bean a singleton
using annotations, use the EJB 3.1 @javax.ejb.Singleton annotation
instead of the @javax.ejb.Stateless annotation.
- Add JAX-RS annotations to the methods that you want to
expose as a RESTful interface to the enterprise bean. The
following example demonstrates adding JAX-RS annotations to the @javax.ejb.Stateless
enterprise bean.
package com.example.jaxrs;
@javax.ejb.Stateless
@javax.ws.rs.Path("/organization/")
public class Organization {
@javax.ws.rs.GET
@javax.ws.rs.Produces("text/plain")
public String getInformation() {
// return information via a String
}
}
- (optional) Add @javax.annotation.Resource annotated Java EE resource fields and properties
to your JAX-RS EJB classes to easily access resources in your application. The Java EE injections
do not work in plain Java classes
with JAX-RS annotations. Injecting @javax.annotation.Resource annotated Java EE resource fields and properties
to your JAX-RS EJB classes only works if your JAX-RS annotated classes
are either an enterprise bean or a Java Context
and Dependency Injection (JCDI) (JSR-299) managed bean; for example:
@javax.ejb.Stateless
@javax.ws.rs.Path("/organization/")
public class Organization {
@javax.annotation.Resource(name="jdcb/TestDataSource")
private javax.sql.DataSource datasource;
@javax.ws.rs.GET
@javax.ws.rs.Produces("text/plain")
public String getInformation() {
// read from the datasource
// return information via a String
}
}
In this example, if a data source is properly configured
with the correct JNDI name, a DataSource object is injected into the
resource class.
- (optional) Use JAX-RS @javax.ws.rs.core.Context injection
to obtain access to information about the request. You
can add a @javax.ws.rs.core.Context UriInfo field to your JAX-RS EJB
class to access information about the request URI; for example:
@javax.ejb.Stateless
@javax.ws.rs.Path("/organization/")
public class Organization {
@javax.ws.rs.core.Context
private UriInfo uriInfo;
@javax.ws.rs.GET
@javax.ws.rs.Produces("text/plain")
public String getInformation() {
// return information via a String
}
}
To read parameters from the request such as @javax.ws.rs.HeaderParam,
@javax.ws.rs.QueryParam, and @javax.ws.rs.PathParam, add a parameter
to your resource method; for example:
@javax.ejb.Stateless
@javax.ws.rs.Path("/organization/")
public class Organization {
@javax.ws.rs.GET
@javax.ws.rs.Produces("text/plain")
public String getInformation(@javax.ws.rs.QueryParam("page") String page) {
/* The QueryParam in the method parameter list will be set correctly. */
// Return information using a String
}
/* The following field will not be set. */
@javax.ws.rs.QueryParam("q")
private String willNotWork;
@javax.ws.rs.QueryParam("q")
public void setMyQueryParam(String q) {
/* This property will not be set. */
}
}
지원된 구성: JAX-RS field and property parameter
injection, such as @javax.ws.rs.QueryParam, is not supported.
sptcfg
- Add the EJB class to the WEB-INF/classes directory of your
WAR file or to a JAR that is located in your WEB-INF/lib directory. When a client makes a request to a JAX-RS annotated enterprise
bean, the JAX-RS runtime environment looks up and uses an EJB instance
of the class to invoke the resource method.
Results
You have enabled an existing enterprise bean with no-interface
view so that JAX-RS resources are exposed for consumption.