Java EE második rész

By 2015.10.01JAVA

Sziasztok!

Az előző részben megismerkedtünk a JavaEE fogalmával. Ez a cikk, ahogy ígértem, gyakorlatiasabb lesz. Telepíteni fogunk egy Weblogic alkalmazásszervert, és deployolunk egy példa alkalmazást.

Mielőtt belevágunk: jelen bejegyzés feltételezi, hogy már rendelkezünk telepített JDK-val, és Maven-nel. Az mvn parancs futtatásához szükséges a Maven könyvtárában lévő bin könyvtár hozzáadása a PATH környezeti változóhoz.

1.Weblogic telepítése és konfigurálása

Mi az Oracle Weblogic 12c verzióját fogjuk használni. Jelenleg  a legfrissebb verzió a 12.1.3. A telepítés és konfigurálás nem teljes körű, csakis a példa alkalmazásunk futtatásához szükséges beállításokat érintjük. Normál esetben futtatnánk node managert, managed szervereket, clustert konfigurálnánk, datasource-okat vennénk fel, stb. De most csak egy egyszerű alapértelmezett domainnel rendelkező alkalmazás szervert fogunk futtatni. A példaprogramunknak ez bővelnelegendő lesz.

1.1. Letöltés és telepítés

Töltsük le a Weblogic 12c -t a következő weboldalról:
http://www.oracle.com/technetwork/middleware/weblogic/downloads/wls-for-dev-1703574.html

Jelöljük be az “Accept License Agreement”-et, majd töltsük le a “Zip distribution Update 2 for Mac OSX, Windows, and Linux” linkről. Ez egy frissített alap zip csomag lesz, 190MB mérettel. Itt be kell jelentkeznünk az Oracle felhasználói nevünkkel (e-mail cím), ha még nem rendelkezünk felhasználóval, regisztráljunk.

Csomagoljuk ki a letöltött wls1213_dev_update2.zip fájlt egy könyvtárba. Ha minden jól ment, létrejött egy wls12130 nevű könyvtár. Mielőtt tovább lépnénk állítsunk be egy környezeti változót. Ez a middleware home lesz, azaz MW_HOME, ami a most kicsomagolt wls12130 könyvtárunkra kell hogy mutasson. Ez azért  szükséges, hogy a Weblogic szkriptjei biztosan tudják, hogy hol van maga a middleware home.

Futtassuk le a configure.sh vagy a configure.cmd parancsot, attól függően milyen oprendszert használunk. A szkript kicsomagolja nekünk a szükséges jar-okat, és létrehoz bár alapbeállítást, majd rákérdez, hogy akarunk-e új domaint beállítani. Ha szerentnénk (és mi most szeretnénk :), mert alap telepítést végzuünk) válaszoljunk egy “y”-al. A szkript létrehoz nekünk egy domaint, majd megkérdezi, hogy mi legyen a Weblogic indításához szükséges felhasználói név és jelszó. Ide most írjuk be felhasználói névnek, hogy “weblogic”, jelszónak pedig, hogy “welcome1”. Ha mindent jól csináltunk, már fut is a weblogic-unk a 7001-es porton. Mivel nem szeretnénk, hogy újra kelljen konfigurálni az alkalmazásszervert minden indításnál, most lépjünk ki ctrl+c -vel, majd indítsuk el mégegyszer a következő módon:

user_projects/domains/mydomain/startWebLogic.sh (illetve .cmd)

Az indítás után ha meglátjuk a “Server state changed to RUNNING.” üzenetet, már biztosra vehetjük, hogy fut az alkalmazásszerverünk. Alap beállítás esetén minden interface-en figyelni fog a 7001-es porton.

1.2.Konfigurálás

Ha már fut a Weblogic, nyissunk egy böngészőt, és lépjünk be az admin console-ra a következő címen: http://localhost:7001/console

Ekkor azt kell látnunk, hogy megjelenik egy weboldal a következő szöveggel:
Deploying application for /Console/ …
Majd kis idő elteltével megjelenik a bejelentkező oldal. Itt jelentkezzünk be a konfigurációnál megadott felhasználói névvel és jelszóval (weblogic:welcome1)

Bal oldalt a Domain Structure részben nyissuk le az Environment-et, majd kattintsunk a Servers-re. Középen meg kell jelennie és táblázatnak, melynek 1 sora van, és pedig a jelenleg futó szerverünk, melynek alapértelmezetten a neve myserver(admin). A State mezőben RUNNING-nak kell szerepelnie, a Health mezőben OK-nak, a Listen Port mezőben pedig a 7001-nek. Ha mindez rendben van, kész is vagyunk az első Weblogic telepítésünkkel, nincs más hátra, alkalmazást kell írnunk rá :)

2.Példaalkalmazás

A leggyorsabban úgy hozhatunk létre egy példaalkalmazást, hogy kihasználjuk a maven nyújtotta lehetőségeket. Archetype-ot fogunk generálni. Röviden: a maven archetype-ok előre definiált projekt struktúrák, melyeket amolyan vázként használhatunk. Jelen esetben nekünk egy olyan struktúra kell, melynek a pom.xml-jében már benne van a JavaEE 6-os interfész “provided“-ként (tehát csak fordítás időben kell) és rendelkezik webes résszel, a csomagolás típusa pedig war. Van is ilyen archetype a maven központi tárolójában, használjuk azt. Ehhez nincs is másra szükség, mint a megfelelően paraméterezett mvn parancsot lefuttatni. Hozzunk létre valahol egy projekt könyvtárat, vagy bármit, ki hogy szereti :), lépjünk be, és futtassuk a következő parancsot:

mvn archetype:generate -DgroupId=hu.zerotohero.example -DartifactId=javaee -Dversion=0.1-SNAPSHOT -Dpackage=hu.zerotohero.example.javaee -DarchetypeGroupId=org.codehaus.mojo.archetypes -DarchetypeArtifactId=webapp-javaee6 -DarchetypeVersion=1.5 -DinteractiveMode=false

Senkit se riasszon el a sok-sok paraméter, nagyon egyszerűek:
archetype:generate- generáljunk archetype-ot. világos :D
-DgroupId- legyen az a létrejövő projektünk groupId-ja
-DartifactId- legyen ez a létrejövő projektünk artifactId-ja
-Dversion- legyen ez a verzió száma
-Dpackage- legyen ez az alap package-ünk
-DarchetypeGroupId- itt adjuk meg az archetype groupId-ját, amiből generálni szerentnénk
-DarchetypeArtifactId- itt pedig az archetype artifactId-ját
-DarchetypeVersion- archetype verziója
-DinteractiveMode- itt adhatjuk meg, hogy a folyamat interaktív legyen-e. Tehát ha nem adunk meg minden paramétert, akkor a rendszer interaktív módban rákérdez, ellenkező esetben az alapértelmezett értéket fogja használni.

Ha lefuttattuk a parancsot, és látunk egy olyan üzenetet, hogy BUILD SUCCESS, akkor bizony létrejött a projektünk, melyet a “javaee” könyvtárban találunk meg. Lépjünk be a könyvtárba, és győződjünk meg róla, hogy a következő könyvtárak és fájlok jöttek létre:
pom.xml
src
src/main
src/main/java
src/main/java/hu
src/main/java/hu/zerotohero
src/main/java/hu/zerotohero/example
src/main/java/hu/zerotohero/example/javaee
src/main/webapp
src/main/webapp/index.jsp

A következő lépésekben létrehozunk EJB-t, Servletet, inicializáljuk a CDI-t, és módósítjuk az index.jsp-t, hogy egy használható kis példaalkalmazást kapjunk.

2.1. beans.xml

Ahhoz, hogy a CDI jól működjön, szükségünk van egy beans.xml fájlra. Ez EJB definíciókat tartalmazhat, a mi esetünkben csak egy üres xml fájlra van szükség.

Az src/main/webapp könyvtár alatt hozzunk létre egy WEB-INF könyvtárat, majd azon belül hozzuk létre a beans.xml fájlunkat a következő tartalommal:


<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://java.sun.com/xml/ns/javaee" 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/beans_1_0.xsd">
</beans>

2.2.person bean

Most érkezett el az idő, hogy létrehozzuk az első Enterprise Java Bean-ünket :)

Az src/main/java/hu/zerotohero/example/javaee könyvtárban hozzunk létre egy PersonBean.java fájlt a következő tartalommal:

package hu.zerotohero.example.javaee;

import java.io.Serializable;
import javax.enterprise.context.SessionScoped;
import javax.inject.Named;

@Named
@SessionScoped
public class PersonBean implements Serializable {

    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

Amint látjuk az osztálynak egy változója van, a name. Ezt fogjuk használni adattárolásra. Megírtuk hozzá a megfelelő getter és setter metódusokat. Amitőól ez az osztály EJB lesz, az az osztályon lévő annotáció. Figyeljük meg, hogy rendelkezik egy @Named annotációval. Esetünkben ez mondja meg, hogy ez egy elnevezett menedzselt java bean lesz. A @SessionScoped annotáció pedig a példány életciklusát határozza meg. Jelen esetben egy sessionön belül egy példány lesz ebből az osztályból, ezért tudjuk adattárolásra használni. Hiszen ha minden egyes alkalommal újra példányosodna, a name változó tartalma elveszne. Itt kell még megjegyezni, hogy a session scope-ú ejb-knek kötelezően implementálniuk kell a java.io.Serializable interfészt, mivel a tartalmuk lehetséges, hogy szerializálva lesz.

2.3. person servlet

Most hogy megvagyunk az EJB-nkkel, hozzunk létre egy servletet, melyen keresztül módosítjuk majd az EJB-nk tartalmát (nevezetesen a name változót). Az src/main/java/hu/zerotohero/example/javaee könyvtárban hozzunk létre egy PersonServlet.java fájlt a következő tartalommal:


package hu.zerotohero.example.javaee;

import java.io.IOException;
import javax.inject.Inject;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet(urlPatterns = "/personServlet")
public class PersonServlet extends HttpServlet {

    @Inject
    private PersonBean personBean;

    @Override
    protected void doGet(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws ServletException, IOException {
        personBean.setName(httpServletRequest.getParameter("name"));
        httpServletResponse.sendRedirect("index.jsp");
    }
}

 

Egy servlet létrehozása a JavaEE világban nagyon  egyszerű: leszármaztatjuk az osztályunkat a HttpServlet absztrakt osztályból, feltesszük a @WebServlet annótációt, melyben az urlPatterns paraméterében megadjuk, hogy mely útvonal esetén hívódjon meg, majd felüldefiniáljuk a kívánt metódust, mely esetünkben a doGet.

Mivel szeretnénk használni a nemrég létrehozott EJB-nket, nincs más dolgunk, mint felvenni egy változót, és rátenni az @Inject annotációt. Ezzel már el is értük az EJB-nket.

A doGet metódusban megkapjuk a request és a response osztályokat, a requestból kiolvassuk a paraméterünket, majd az injektált ejb-nkben beállítjuk azt a name változóba. Ezután pedig visszairányítjuk a böngészőt a kezdőoldalra, az index.jsp-re.

2.4 index.jsp

A webes része az alkalmazásunknak jelenleg sima JSP-vel működik, van is egy előre megírt index.jps fájlunk. Módosítsuk a meglévő fájlt úgy, hogy ki tudjuk használni az imént megírt EJB és servletünket. Módosítsuk a fájlt a következő képpen:


<%@page contentType="text/html" pageEncoding="UTF-8"%>
<jsp:useBean id="personBean" class="hu.zerotohero.example.javaee.PersonBean" scope="session"/>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
        <title>JSP Page</title>
    </head>
    <body>
        <h1>Hello World!</h1>
        Person name: ${personBean.name} <br/>
        <form action="personServlet" method="get">
            <input type="text" name="name" value="">
            <input type="submit" value="Set"/>
        </form>
    </body>
</html>

Amint látjuk, bekerült a második sorba egy <jsp:useBean> tag, amivel meg tudjunk mondani, hogy az attribútumokban definiált bean-t szeretnénk használni ebben a jsp-ben. Az id attribútum adja meg a bean hivatkozási nevét a jps-n belül, a class attribútum, hogy melyik osztályt szeretnénk használni, a scope pedig az életciklust.

Ezek után hivatkozhatunk az EJB-nkre a personBean névvel, és mint láthatjuk, behelyettesíthetjük az EJB-ben lévő name változó értékét a következő placeholderrel: ${personBean.name}. Továbbá létrehoztunk egy form-ot, mely a personServlet-re mutat, azaz arra az útvonalra, amit a servletünkben megadtunk, a method attribútumát pedig get-re állítottuk, mert azt dolgozzuk fel. A formon belül létrehoztunk egy input mezőt, melynek a neve name, mivel ezt az attribútumot olvassuk ki majd a servletünk doGet metódusában a request-ből.

3.Deployolás

Ha mindezzel megvolnánk, nincs más dolgunk, mint megépíteni a csomagot, és deployolni azt az alkalmazásszerverünkbe.

Adjuk ki az “mvn clean package” parancsot a “javaee“ könyvtárunkban. Miután a parancs lefutott, és megkaptuk a várva várt “BUILD SUCCESS” üzenetet, létrejött egy target könyvtárunk, mely tartalmazza a javaee-0.1-SNAPSHOT.war fájlt.

Következő lépésként menjünk vissza a Weblogic admin console-jára, majd a bal oldalon lévő Domain Structure részben kattintsunk a Deployments linkre. A középső részen kapnunk kell egy üres ráblázatot, mely felett Install, Update, Delete, Start, Stop gombok helyezkednek el. Kattintsunk az Install gombra, majd a betöltött oldalon a Note: feliratot követő szövegben az “upload your file” linkre. Ezután a Deployment Archive-nál válasszük ki a target könyvtárunkban létrejött javaee-0.1-SNAPSHOT.war fájlt, majd kattintsunk a Next gombra. Ekkor visszajutunk az előző oldalra, de a Path: sorban már a mi war fájlunk elérési útvonala lesz. Ha ezt leelenőriztük, újra kattinthatunk a Next gombra. A következő oldalon válasszuk ki a “Install this deployment as an application” opciót, majd újra kattintsunk a Next gombra. Az ezek után betöltődött oldalon már nem kell tennünk semmit, nyugodtan kattinthatunk a Finish gombra.

Ezek után a Deployments táblázat tartalmazni fogja a javaee-0.1-SNAPSHOT nevű alkalmazásunkat. Ha minden jól sikerült, akkor a State aktív, a Health pedig OK lesz.

Az alkalmazásunkat a következő címen érhetjük el:
http://localhost:7001/javaee-0.1-SNAPSHOT/

Ha betöltődött a Hello World alkalmazásunk, a Person name: alatt lévő beviteli mezőbe beírt érték a Set gomb megnyomása után bekerül az EJB-nk name változójába a servletünkön keresztül, majd a servlet által újra betöltött index.jsp már a megfelelő értéket írja a Person name: után.

Ennyi lenne egy minimál JavaEE alkalmazás :)

Összefoglalásként: telepítettünk egy alkalmazás szervert, megírtuk első JavaEE alkalmazásunkat és deployoltuk is az alkalmazásszerverünkbe. Nyilván ez egy nagyon egyszerű példa volt, de mégis szemlélteti, hogy ha megnézzük az elkészült war csomagunkat, nem látunk benne semmilyen függőségként csomagolt jar-t.

A következő részben pedig megismerkedünk a JPA-val :)