EJB3 - Konfiguration

Soulfly2111

Grünschnabel
Hi

Ich versuche mich schon seid einiger Zeit mit EJB3 - vergebens. Irgendwie will das einfach nicht. Irgendwie erkennt er das EJB nicht. Ich habe die Zeile ROT markiert, wo eine NullpointerException geworfen wird. Obwohl ich aus dem Buch "EJB in Action" entnommen habe, dass eine Annotation von @EJB vollkommen ausreicht. Leider gibt das Buch nicht her, wie die Einbindung genau auszusehen hat. Naja....genau das was ich eigenltlich brauche (Muss ich doch mit JNDI arbeiten ?)


Die WebApp funktioniert einwandfrei. Also JSP läuft und das HttpServlet auch :)

Ich hoffe das mir einer weiterhelfen kann. Leider habe ich im Internet für mich kein passendes Beispiel gefunden. So wie es aussieht erkennt JBoss das EJB:
Auszug aus dem MBean Inspector:
Code:
JMX MBean View 

MBean Name: Domain Name: jboss.j2ee 
 service:  EJB3 
 name:  HelloUserBean 
 ear:  helloworld.ear 
 jar:  helloworld.jar 
MBean Java Class: org.jboss.ejb3.stateless.StatelessDelegateWrapper 

Back to Agent View  Refresh MBean View

Meine Applikation:
Ich habe die Datei hellworld.ear erstellt. Die Datei enthält
helloworld.war (WebApp)
helloworld.jar (EJB)
META-INF/application.xml


application.xml​
Code:
<!DOCTYPE application PUBLIC "-//Sun Microsystems,
Inc.//DTD J2EE Application 1.2//EN"
        "http://java.sun.com/j2ee/dtds/application_1_2.dtd">
<application>
    <icon>
    </icon>
    <module>
        <ejb>helloworld.jar</ejb>
    </module>
    <module>
        <web>
            <web-uri>helloworld.war</web-uri>
            <context-root>/helloworld</context-root>
        </web>
    </module>

    <display-name>Hello World EJB3</display-name>
    <description>Hello World EJB3</description>
    <!-- <security-role>
        <description>the customer role</description>
        <role-name>customer</role-name>
    </security-role>
    -->
</application>

helloworld.jar

HelloUser
Code:
@Local
public interface HelloUser {
    public String createHello(String username);
}
HelloUserBean
Code:
@Stateless
public class HelloUserBean implements HelloUser {
    public String createHello(String username) {
        return "Hello: " + username;
    }
}

helloworld.war

HelloController
Code:
public class HelloController extends HttpServlet {
    public static LinkedHashMap<String, Integer> counter = new LinkedHashMap<String, Integer>();
    @EJB    
    private HelloUserBean helloUserBean;

    public String createHello(String username) {

        try {
             // HIER IMMER NULLPOINTEREXCEPTION
            return helloUserBean.createHello(username); 

        } catch (Exception e) {
            e.printStackTrace();
        }

        return "No Hello for you ";
    }

    public void doGet(HttpServletRequest request,
                      HttpServletResponse response)
            throws ServletException, IOException {
       Integer count = counter.get(request.getParameter("name"));
       if(count==null)
            count = 0;
       counter.put(request.getParameter("name"), ++count);
       response.sendRedirect("index.jsp?ejbname="+createHello("Mr.Help")+"&name=" + request.getParameter("name") + "&count="+count) ;
    }

    public void doPost(HttpServletRequest request,
                       HttpServletResponse response)
            throws ServletException, IOException {
        doGet(request, response);
    }
}

index.jsp
Code:
<%--

--%>
<%@ page contentType="text/html;charset=ISO-8859-1" language="java" %>
<html>
<head><title>Hello EJB3 World </title></head>
<body>
<%
    if  (request.getParameter("name")!=null ) {
        out.println("Hallo: " + request.getParameter("name"));
        out.println("Dies ist ihr " + request.getParameter("count") + ". Besuch");
    }
%>
<form action="HelloWorld.form" method="POST">
    <input type="text" name="name" SIZE=25>
    <input type="reset" name="reset" VALUE="Löschen">
    <input type="submit" NAME="submit" VALUE="Sag Hallo">
</form>

<a href="Statistik.stat" >Statistik</a>

<%
   out.println("EJB " + request.getParameter("ejbname") + " Parabens");
%>

</body>
</html>


web.xml
Code:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
    <display-name>hnejb3</display-name>

    <servlet>
        <servlet-name>HelloWorld</servlet-name>
        <servlet-class>hn.ejb.example01.web.HelloController</servlet-class>
    </servlet>

      <servlet>
        <servlet-name>Statistik</servlet-name>
        <servlet-class>hn.ejb.example01.web.StatistikServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>HelloWorld</servlet-name>
        <url-pattern>*.form</url-pattern>
    </servlet-mapping>

    <servlet-mapping>
        <servlet-name>Statistik</servlet-name>
        <url-pattern>*.stat</url-pattern>
    </servlet-mapping>
</web-app>
 
Zuletzt bearbeitet:
Naja, ich kenn mich mit EJB leider nicht aus. Aber warum die NullpointerException kommt, sollte eigentlich klar sein: Die Variable wurde nicht initialisiert.

Änder die 4. Zeile im HelloController einfach in
Java:
private HelloUserBean helloUserBean = new HelloUserBean();
und dann sollte es (vielleicht) funktionieren, sofern das der einzige Fehler ist.
 
Da EJB mit DI (Dependency Injection )arbeitet, sollte eigentlich die EJB Umgebung die Initialisierung meiner Beans übernehmen. Mit den Zeilen:
Code:
@EJB    
private HelloUserBean helloUserBean;
sollte das eigentlich getan werden
 
Zuletzt bearbeitet:
Da EJB mit DI (Dependency Injection )arbeitet, sollte eigentlich die EJB Umgebung die Initialisierung meiner Beans übernehmen. Mit den Zeilen:
Code:
@EJB    
private HelloUserBean helloUserBean;
sollte das eigentlich getan werden

Wie gesagt: ich kenn mich mit EJB nicht aus. Und ich hoffe, dass hier auch mal wer reinschaut, der sich damit auskennt um dir die Problemlösung zu sagen. Aber in der Zeile wo du die Exception kriegst, ist helloUserBean ja offensichtlich null, sonst würde die Exception ja nicht auftreten. Mit anderen Worten: das EJB SOLLTE deine Variable dann wohl initialisieren, tut's aber nicht, sonst gäb es ja keinen Fehler...
Mein Rat wäre: die Initialisierung trotzdem von Hand machen, auch wenn es in der Theorie wohl nicht nötig sein sollte. Dann kannst du zumindest weiterarbeiten bis dir hier wer sagt, wo der Fehler ist...
 
Postet doch sowas in das J2EE Unterforum ;). Selbst instantiieren ist keine Lösung, da du damit eine Dependency zur Implementierung aufbaust, was eben genau nicht sein soll.

Hast du mal versucht der @EJB Annotation den Namen deiner Bean mitzugeben? Vielleicht gibts da nen Problem, weil die Property mit nem kleinen Buchstaben anfängt, deine Bean aber mit nem Großbuchstaben.

Ansonsten wundert es mich, dass das Servlet überhaupt initialisiert wird, da wohl eindeutig eine Dependency fehlt (deine EJB).

Was definitiv auch falsch ist, ist, dass du als typ der Property die Implementierung benutzt. Es muss wiefolgt aussehen:
Code:
@EJB
private HelloUser helloUserBean;

Ich vermute, dass ist der eigentliche Grund.

Gruß
Ollie
 
Leider funkioniert es immer nocht nicht !!


@MSProductions
Danke für die Hinweise. Habe die Zeilen geändert:
Code:
@EJB
static private HelloUser helloUserBean;
Habe es auch ohne static ausprobiert (Im Sun J2EE Tutorial war es mit static versehen)

Und habe auch versucht
Code:
@EJB(beanName = "HelloUserBean")
// und
@EJB(name = "HelloUserBean")
// und
@EJB(mappedName = "HelloUserBean")

Das EJB startet(soweit ich es sehen) aufjedenfall richtig:
17:04:25,312 INFO [EJBContainer] STARTED EJB: hn.ejb.example01.beans.HelloUserB
ean ejbName: HelloUserBean

Habe auch folgendes aus dem JavaEETutorial von Sun ausprobiert:
Code:
InitialContext ic = new InitialContext();
helloUserBean = (HelloUser) ic.lookup(HelloUser .class.getName());
Da wird aber eine Exception geworfen.

Code:
17:14:46,578 ERROR [STDERR] javax.naming.NameNotFoundException: hn.ejb.example01
.beans.HelloUser not bound


Habe ausserdem noch versucht @Locale zu @Remote zu ändern
Code:
@Remote
public interface HelloUser {
    public String createHello(String username);
}

Mit gleichem Effekt... es will einfach nicht...:confused:
 
Habe es hinbekommen. Nachdem ich folgendes auf der JBossseite gelesen habe:
Lookup of EJBs
@EJB annotations are usable in servlets and JSPs, but unfortunately, we have not yet updated tomcat to support it. Also, Tomcat works with the old XML format so you cannot use XML either. So for now, you must lookup the EJB via its global JNDI name. This is not compliant, but if you abstract out enough you'll be fine.

Also habe ich die jboss-web.xml erstellt mit:
Code:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE jboss-web PUBLIC
    "-//JBoss//DTD Web Application 4.2//EN"
    "http://www.jboss.org/j2ee/dtd/jboss-web_4_2.dtd">
<jboss-web>
	<context-root>StatelessWeb</context-root>
	<ejb-local-ref>
		<ejb-ref-name>ejb/HelloUserLocal</ejb-ref-name>
		<local-jndi-name>helloworld/HelloUserBean/local</local-jndi-name>
	</ejb-local-ref>
</jboss-web>

und habe die web.xml erweitert:

Code:
    <ejb-local-ref>
		<ejb-ref-name>ejb/HelloUserLocal</ejb-ref-name>
		<ejb-ref-type>Session</ejb-ref-type>
		<local-home>java.lang.Object</local-home>
		<local>hn.ejb.example01.beans.HelloUserBean</local>
	</ejb-local-ref>

Also keine Ahnung ob das alles so "best way" Lösung ist, bin auch noch relativ neu in der J2EE Welt... aber es funtzt.... :)
 

Neue Beiträge

Zurück