java - @EJB annotation does not work for initialize bean within the EJB application -
i have maven project structure:
-myproject -myproject-ear -myproject-service -webservice -myproject-ejb
in myproject-ejb
have java packages:
-src/main/java/ -src/test/java/
i have ejb , corresponding bean implementation in
-src/main/java/org/mypackage/mybean.java -src/main/java/org/mypackage/mybeanimpl.java
in src/test/java/
have test called mybeantest.java following code:
import javax.ejb.ejb; import org.mypackage.mybean; import org.junit.*; public class mybeantest { @ejb private mybean mybean; @test public void testbean() { system.out.println("mybean: "+mybean); // prints null mybean.writetodb("hello", "world"); // fails since mybean null } }
when run unit test, mybean
null. wondering why @ejb
annotation not work. test package in same application bean, @ejb
should work.
any ideas?
edit 1
found this link same problem have, solution there doesn´t seem work me. doing wrong?
package org.myproject.ejb; import java.util.hashtable; import java.util.properties; import javax.ejb.ejb; import javax.naming.context; import javax.naming.initialcontext; import javax.naming.namingexception; import javax.servlet.servletexception; import org.myproject.ejb.mybean; import org.jboss.ejb.client.contextselector; import org.jboss.ejb.client.ejbclientconfiguration; import org.jboss.ejb.client.ejbclientcontext; import org.jboss.ejb.client.propertiesbasedejbclientconfiguration; import org.jboss.ejb.client.remoting.configbasedejbclientcontextselector; import org.junit.*; public class mybeantest { private mybean mybean; @before public void init() { try { properties clientprop = new properties(); clientprop.put("remote.connectionprovider.create.options.org.xnio.options.ssl_enabled", "false"); clientprop.put("remote.connections", "default"); clientprop.put("remote.connection.default.port", "4447"); clientprop.put("remote.connection.default.host", "localhost"); clientprop.put("remote.connection.default.connect.options.org.xnio.options.sasl_policy_noanonymous", "false"); ejbclientconfiguration cc = new propertiesbasedejbclientconfiguration(clientprop); contextselector<ejbclientcontext> selector = new configbasedejbclientcontextselector(cc); ejbclientcontext.setselector(selector); properties env = new properties(); env.put(context.url_pkg_prefixes, "org.jboss.ejb.client.naming"); env.put(context.security_principal, "admin"); env.put(context.security_credentials, "testing"); initialcontext ctx = new initialcontext(env); mybean = (mybean) ctx.lookup("java:app/myproject-ejb-1.0-snapshot/mybeanimpl"); } catch(namingexception ex) { ex.printstacktrace(); } } @test public void testbean() { system.out.println("ejb: "+mybean); // prints null } }
the error above configuration is:
warn: unsupported message received header 0xffffffff javax.naming.noinitialcontextexception: need specify class name in environment or system property, or applet parameter, or in application resource file: java.naming.factory.initial @ javax.naming.spi.namingmanager.getinitialcontext(namingmanager.java:662) @ javax.naming.initialcontext.getdefaultinitctx(initialcontext.java:307) @ javax.naming.initialcontext.geturlordefaultinitctx(initialcontext.java:344)
container resource injection, such @ejb, requires populated jndi directory , works within java ee managed components executing in java ee container. challenge unit testing. see jsr318 java ee 6 platform spec, section ee.5 resources, naming, , injection.
you're attempting jndi lookup - java se unit test app remotely connecting jndi context. disadvantages: must deploy full java ee 6 app precondition run test; test-bugfix-build-deploy-retest lifecycle can slow things.
some issues:
- your username/password properties different jboss doc;
- from doc appears jndi lookup name needs
"ejb:..."
rather"java:app/..."
because jboss ejb-client-project code uses intercept lookup. java ee 6 platform spec ee.5.2.2: names injava:app
namespace shared components in modules in single java ee app. if test separate jse app usingjava:app
, suspect jboss treats separate single java ee application, , lookup fail. - make sure lookup interface, not implementation class (i.e. ejb no interface view) remote access
- you're refering unusual reference showing direct use of ejbclientconfiguration & ejbclientcontext. seems not required/preferred.
try these actions:
include these properties:
clientprop.put("remote.connection.default.username", "admin"); clientprop.put("remote.connection.default.password", "testing");
change client reference:
java:app/myproject-ejb-1.0-snapshot/mybeanimpl ejb:<app-ear-name>/<module-jar-name>/<jboss-optional-distinct-name>/<bean-name>!<fully-qualified-classname-of-the-remote-interface>
e.g. if mybean stateless ejb deployed in myproject-ejb-1.0-snapshot.jar (without ear). then:
ejb:/myproject-ejb-1.0-snapshot//mybeanimpl!org.mypackage.mybean
if it's stateful ejb, add "?stateful" string.
setup
ejb-client.properties
directly (via file or program) , apply directly jndicontext
. see https://docs.jboss.org/author/display/as72/ejb+invocations+from+a+remote+client+using+jndi , https://docs.jboss.org/author/display/as72/scoped+ejb+client+contexts , http://middlewaremagic.com/jboss/?p=1177
in future: use cdi injection; junit + cdi
@mock
"pojo" unit testing; arquillian "java ee" unit/module testing in containers. avoid/reduce tests (2) above (jse client -> ejb). cdi supports:- java ee resource injection pojos (including
@ejb
annotation). still requires deployed java ee app/component , populated jndi directory lookup. managed beans pojos or java ee components (incl. ejbs) - inject "any" "any" superior @inject annotation. works without jndi directory, typesafe & bean scope-aware.
supports unit testing via simple mocking. use
@mock
&@specializes
declare replacement version bean. test ejb clients without ejbs. test ejbs pojos.
to enable cdi, include
beans.xml
file (can empty, if config via annotation).to declare managed bean:
- optional scope above class e.g.
@sessionscoped
- no-arg constructor /
@inject
on constructor
use inject reference:
@inject (optional @mydeclaredqualifier) private mybean mybean;
arquillian ("junit java ee 6") runs test code on java ee server. dynamically deploys test code configured container(s) , runs tests. supports @ejb annotation, jndi connection becomes simple , can include java ee classes in unit tests without mocking, or refactoring abstract away them.
- java ee resource injection pojos (including
Comments
Post a Comment