Overview
unmigrated-inline-wiki-markup |
---|
...
{span:style=float: right; margin-left: 20px;}
{html}
<object width="400" height="250"><param name="movie" value="http://www.youtube.com/v/9JqxbfzsWOQ?fs=1&hl=en_US&rel=0"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="always"></param><embed src="http://www.youtube.com/v/9JqxbfzsWOQ?fs=1&hl=en_US&rel=0" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="400" height="250"></embed></object>
{html}
{span} |
Wiki Markup |
---|
{div}
This example shows how to create a Stateful session EJB using annotations.
A Stateful session bean is a session bean whose instances can maintain the conversational state with the client. The conversational state of the stateful session bean, which describes the conversation between a specific client and a session bean, is contained in the fields of the stateful session bean.
Simply put, when you create a stateful bean an actual instance is created by the container and *dedicated* to you and only you. Every call you make will go to your instance. Further, your instance will not be shared with anyone unless you give them a reference to your stateful bean. The instance will last until you remove it or until it times-out and is removed by the container.
With EJB 3.0, it's now possible to write stateful session bean without specifying a deployment descriptor; you basically have to write just a remote or local business interface, which is a plain-old-java-interface, annotated with the @Remote or @Local annotation the stateful session bean implementation, a plain-old-java-object which implements the remote or the local business interface and is annotated with the @Stateful annotation
_This example is the "simple-stateful" example located in the [openejb-examples.zip|OPENEJB:Download] available on the download page._
{div} |
Wiki Markup |
---|
{div:style=clear:both;}{div} h1. |
The
...
Code
...
In
...
this
...
example
...
we
...
develop
...
a
...
simple
...
counter
...
stateful
...
session
...
EJB.
...
Every
...
stateful
...
session
...
bean
...
implementation
...
must
...
be
...
annotated
...
using
...
the
...
annotation
...
@Stateful
...
or
...
marked
...
that
...
way
...
in
...
the
...
ejb-jar.xml
...
file.
Bean
Wiki Markup |
---|
h2. Bean {snippet:id=code|url=openejb3/examples/simple-stateful/src/main/java/org/superbiz/counter/CounterImpl.java|lang=java} |
In
...
EJB
...
3.0
...
session
...
beans
...
do
...
not
...
need
...
to
...
implement
...
the
...
javax.ejb.SessionBean
...
interface.
...
You
...
can
...
simply
...
annotate
...
it
...
as
...
@Stateful
...
if
...
you
...
want
...
it
...
to
...
be
...
a
...
stateful
...
session
...
bean.
...
Users
...
of
...
EJB
...
2.x
...
may
...
notice
...
the
...
bean
...
actually
...
implements
...
the
...
business
...
interfaces!
...
In
...
the
...
prior
...
version
...
of
...
EJB
...
implementing
...
the
...
remote
...
interface
...
(which
...
derives
...
from
...
javax.ejb.EJBObject)
...
in
...
your
...
bean
...
was
...
just
...
not
...
allowed.
...
Now
...
there
...
is
...
no
...
javax.ejb.EJBObject
...
requirement,
...
so
...
implementing
...
the
...
business
...
interfaces
...
is
...
standard
...
practice
...
for
...
EJB
...
3.0.
...
Local
...
business interface
Wiki Markup |
---|
interface {snippet:id=code|url=openejb3/examples/simple-stateful/src/main/java/org/superbiz/counter/CounterLocal.java|lang=java} |
Local
...
interfaces
...
in
...
EJB
...
are
...
pass-by-reference
...
interfaces.
...
Meaning
...
that
...
normal
...
java
...
semantics
...
are
...
used
...
for
...
passing
...
arguments,
...
return
...
values
...
and
...
exceptions.
...
A
...
business
...
local
...
interface
...
can
...
be
...
any
...
plain
...
java
...
interface.
...
There
...
are
...
no
...
restrictions
...
on
...
the
...
method
...
arguments,
...
return
...
types,
...
or
...
throws
...
clauses.
...
Unless
...
specified
...
otherwise,
...
every
...
interface
...
your
...
bean
...
implements
...
(and
...
it's
...
parent
...
class
...
implements
...
and
...
so
...
on)
...
is
...
considered
...
to
...
be
...
a
...
local
...
business
...
interface.
...
You
...
can
...
use
...
the
...
@Local
...
annotation
...
to
...
explicitly
...
state
...
that
...
an
...
interface
...
is
...
a
...
local
...
interface,
...
but
...
this
...
is
...
not
...
required.
...
You'll
...
notice
...
that
...
in
...
EJB
...
3.0
...
the
...
Local
...
Business
...
Interface
...
of
...
a
...
stateless
...
session
...
bean
...
does
...
not
...
need
...
to
...
extend
...
from
...
javax.ejb.EJBLocalObject
...
and
...
does
...
not
...
need
...
a
...
javax.ejb.EJBLocalHome
...
interface
...
as
...
they
...
did
...
in
...
EJB
...
2.x
...
and
...
prior.
...
Per
...
the
...
vocabulary
...
of
...
the
...
EJB
...
spec,
...
interfaces
...
that
...
implement
...
javax.ejb.EJBLocalObject
...
or
...
javax.ejb.EJBLocalHome
...
are
...
considered
...
Component
...
Interfaces
...
and
...
the
...
plain
...
java
...
interface
...
above
...
is
...
considered
...
a
...
Business
...
Interface.
...
Remote
...
business interface
Wiki Markup |
---|
interface {snippet:id=code|url=openejb3/examples/simple-stateful/src/main/java/org/superbiz/counter/CounterRemote.java|lang=java} |
Remote
...
interfaces
...
are
...
pass-by-value
...
interfaces.
...
Meaning
...
that
...
all
...
method
...
parameters,
...
return
...
values,
...
and
...
exceptions
...
are
...
serialized
...
on
...
every
...
call.
...
The
...
result
...
is
...
that
...
you
...
get
...
a
...
copy
...
of
...
the
...
original
...
object
...
and
...
not
...
the
...
original
...
object.
...
The
...
advantage
...
is
...
of
...
course
...
that
...
Remote
...
interfaces
...
can
...
be
...
used
...
to
...
invoke
...
an
...
EJB
...
across
...
a
...
network
...
in
...
a
...
client-server
...
fashion.
...
There
...
are
...
no
...
restrictions
...
on
...
the
...
Remote
...
interface
...
itself,
...
but
...
there
...
are
...
on
...
the
...
data
...
passed
...
in
...
and
...
out
...
of
...
the
...
remote
...
interface.
...
The
...
values
...
passed
...
into
...
a
...
method
...
or
...
returned
...
from
...
a
...
method
...
of
...
a
...
Remote
...
interface
...
must
...
be
...
serializable
...
.
...
It
...
is
...
fine
...
for
...
the
...
method
...
signature
...
to
...
be,
...
for
...
example,
...
"public
...
Object
...
myMethod(Object
...
myParam)"
...
as
...
long
...
as
...
the
...
value
...
passed
...
in
...
and
...
returned
...
implements
...
java.io.Serializable
...
.
...
As
...
stated
...
above,
...
the
...
Remote
...
Business
...
Interface
...
of
...
a
...
bean
...
can
...
be
...
any
...
plain
...
old
...
interface.
...
It
...
does
...
not
...
need
...
to
...
extend
...
javax.ejb.EJBObject,
...
it
...
does
...
not
...
need
...
a
...
javax.ejb.EJBHome,
...
the
...
methods
...
do
...
not
...
need
...
to
...
throw
...
javax.rmi.RemoteException,
...
and
...
the
...
bean
...
class
...
can
...
implement
...
it!
...
At
...
minimum
...
the
...
interface
...
must
...
be
...
annotated
...
with
...
@Remote
...
either
...
in
...
the
...
interface
...
itself
...
or
...
in
...
the
...
bean
...
class,
...
or
...
the
...
interface
...
must
...
be
...
declared
...
via
...
<business-remote>
...
in
...
the
...
ejb-jar.xml.
...
Writing
...
a
...
unit
...
test
...
for
...
the
...
example
...
Writing
...
an
...
unit
...
test
...
for
...
the
...
stateful
...
session
...
EJB
...
is
...
quite
...
simple.
...
We
...
need
...
just
...
to
...
write
...
a
...
setup
...
method
...
to
...
create
...
and
...
initialize
...
the
...
InitialContext,
...
and
...
then
...
write
...
our
...
test
...
methods
setUp
Wiki Markup |
---|
h4. setUp {snippet:id=setup|url=openejb3/examples/simple-stateful/src/test/java/org/superbiz/counter/CounterImplTest.java|lang=java} h4. |
Test
...
the
...
local
...
business interface
Wiki Markup |
---|
interface {snippet:id=local|url=openejb3/examples/simple-stateful/src/test/java/org/superbiz/counter/CounterImplTest.java|lang=java} h4. |
Test
...
the
...
remote
...
business interface
Wiki Markup |
---|
interface {snippet:id=remote|url=openejb3/examples/simple-stateful/src/test/java/org/superbiz/counter/CounterImplTest.java|lang=java} { |
Info | ||||||
---|---|---|---|---|---|---|
| =
|
| ||||
}
Note that JNDI names for Java SE clients are not standardized by the EJB spec. This is unfortunate and something being addressed in EJB 3.1. The default schema that OpenEJB uses is ejbName + interfaceType (i.e. Local, Remote, LocalHome, RemoteHome), so in our example "CounterImpl" + "Local" and "CounterImpl" + "Remote". You can in fact change this default to be absolutely [ |JNDI Names]including interface class name, ejb class name, and more. {info} h1. Running Running the example is fairly simple. In the |
Running
Running the example is fairly simple. In the "simple-stateful"
...
directory
...
of
...
the
...
...
...
,
...
just
...
run:
...
$
...
mvn
...
clean
...
install
...
Which
...
should
...
create
...
output
...
like
...
the
...
following.
No Format |
---|
} ------------------------------------------------------- T E S T S ------------------------------------------------------- Running org.superbiz.counter.CounterImplTest Apache OpenEJB 3.0 build: 20080408-04:13 http://openejb.apache.org/ INFO - openejb.home = /Users/dblevins/work/openejb-3.0/examples/simple-stateful INFO - openejb.base = /Users/dblevins/work/openejb-3.0/examples/simple-stateful INFO - Configuring Service(id=Default Security Service, type=SecurityService, provider-id=Default Security Service) INFO - Configuring Service(id=Default Transaction Manager, type=TransactionManager, provider-id=Default Transaction Manager) INFO - Configuring Service(id=Default JDK 1.3 ProxyFactory, type=ProxyFactory, provider-id=Default JDK 1.3 ProxyFactory) INFO - Found EjbModule in classpath: /Users/dblevins/work/openejb-3.0/examples/simple-stateful/target/classes INFO - Configuring app: /Users/dblevins/work/openejb-3.0/examples/simple-stateful/target/classes INFO - Configuring Service(id=Default Stateful Container, type=Container, provider-id=Default Stateful Container) INFO - Auto-creating a container for bean CounterImpl: Container(type=STATEFUL, id=Default Stateful Container) INFO - Loaded Module: /Users/dblevins/work/openejb-3.0/examples/simple-stateful/target/classes INFO - Assembling app: /Users/dblevins/work/openejb-3.0/examples/simple-stateful/target/classes INFO - Jndi(name=CounterImplLocal) --> Ejb(deployment-id=CounterImpl) INFO - Jndi(name=CounterImplRemote) --> Ejb(deployment-id=CounterImpl) INFO - Created Ejb(deployment-id=CounterImpl, ejb-name=CounterImpl, container=Default Stateful Container) INFO - Deployed Application(path=/Users/dblevins/work/openejb-3.0/examples/simple-stateful/target/classes) Tests run: 2, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.698 sec Results : Tests run: 2, Failures: 0, Errors: 0, Skipped: 0 {noformat} |