IBM Rational Software Development Platform
Inhalt:
Allgemeine Vorgaben:
Installation
Eigenes Server-Profile
Eigene Datenbank
Codeformatter
Sonstige Info:
CView
Websphere-Logdateien
Bugs
Allgemeine Vorgaben
Installation
Siehe Anleitung auf Hr. Drehers Seite. Nach Ausführen von "launchpad.exe" wird
die Option "IBM Rational(R) Application Developer V6.0 installieren" gewählt.
Scheinbar klappt die Installation nicht wenn auf Laufwerk D: installiert werden soll
(das führt nach Abschluss der Installation zu der Meldung "IBM Rational Application Developer V6.0 wird noch immer
ausgeführt, allerdings ist IBM WebSphere Application Server V6.0 Integrated Testenvironment
möglicherweise nicht ausführbar. Weitere Informationen finden Sie im Installationshandbuch.").
Das Verzeichnis "runtimes\base_v6" fehlt, dadurch fehlt auch die J2EE 1.4-Unterstützung des Servers.
Beim Start der Installation wird der Haken bei "Zusätzliche Funktionen\Sprachpakete" entfernt
(Deutsche Version hat einen nervigen Bug und ist nicht verständlicher als die englische):
Anschließend den Fixpack 6.0.1.1 für den Rational Application Developer installieren.
Das gibt es hier: http://www-1.ibm.com/support/docview.wss?uid=swg24010926&rs=0&cs=utf-8&context=SSRTLW&dc=D400&loc=en_US&lang=en&cc=US
Oder bei mir.
Update des Servers auf 6.0.2.5:
Update-Packages "RP602" (Refresh Pack 6.0.2) und "FP6025" (Fix Pack 6.0.2.5) von IBM herunterladen:
http://www-1.ibm.com/support/docview.wss?rs=180&uid=swg27004980, gibt es alternativ von mir.
Zuerst den Refresh-Pack installieren: Entpacken. Das komplette Verzeichnis "updateinstaller" in das Verzeichnis
"C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\" kopieren und Update
durch Aufrufen von "update.exe" starten. Hat man die Daten in das falsche Verzeichnis
kopiert kommt jetzt die Meldung "Keine Produkte gefunden", ansonsten taucht eine lange
Liste von WebSphere-Versionen auf. Es ist eine simple Weiter-Weiter-Installation,
deshalb keine Screenshots. Scheinbar faßt die Installation alle existierenden Profile an.
Nach Installation des Refresh Packs das Verzeichnis "C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\updateinstaller"
löschen und die gleiche Prozedur für den FixPack 6.0.2.5 wiederholen.
Dass man erfolgreich war sieht man wenn man die "Administrative Console" startet:
Eigenes Server-Profile
Um uns nicht gegenseitig ins Gehege zu kommen sollte jeder Student ein eigenes Profil
verwenden und dieses beim Abmelden sauber löschen !
Das Erzeugen eines Profils geht über mehrere Wege:
Im Menü "Window" -> "Preferences" wählen und in die Kategorie "Server" -> "WebSphere" gehen:
Mittels "Create Profile..." gelangen wir in einen Assistenten mittels dem wir ein neues Profil erzeugen
können.
Den Assistenten können wir auch direkt aufrufen: C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\bin\ProfileCreator\pctWindows.exe.
Seltsamerweise wird bei jedem Aufruf eine Installation vorbereitet...
Im ersten Schritt geben wir dem Profil einen aussagekräftigen Namen:
Wir legen den Pfad zum Profil fest.
Der Knotenname und der Hostname können auf dem Default belassen werden.
Im nächsten Schritt ("Zuordnung von Port-Werten") müssen wir alle Werte auf die Defaults
zurückstellen. Grund: wenn wir das nicht tun müssen wir später im Projekt zumindest
den "Bootstrap-Port" (2809) und den "Port für SOAP-Connector" (8880) anpassen. Da wir sowieso nicht mehr
als einen Server starten sollte das kein Problem darstellen wenn wir den gleichen Port in verschiedenen
Profilen verwenden.
Im Schritt "Definition eines Windows-Dienstes" entfernen wir natürlich den Haken
"Application-Server-Prozess als Windows-Dienst ausführen".
Das wars, und jetzt können wir erstmal Kaffekochen gehen.
Wenn der Assistent irgendwann mal fertig ist, bietet er uns noch die Option an, die Konsole
"Erste Hilfe" zu starten. Das können wir machen, müssen wir aber nicht. Sie dient hauptsächlich
zum Test des Servers und zum Starten/Stoppen. Falls wir doch mal den Drang nach ihr verspüren:
sie liegt im Server-Profil unter "\firststeps\firststeps.bat".
Für die Profis unter uns hier die Anleitung für die Kommandozeile (das Programm "wasprofile.bat"
befindet sich in C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\bin"):
wasprofile.bat -create
-profileName WolfgangProfile
-profilePath c:\temp\WolfgangProfile
-templatePath C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profileTemplates\default
-nodeName WolfgangNode
-cellName WolfgangCell
-hostName localhost
Die Zeilenumbrüche dienen nur der besseren Lesbarkeit !
Alle vorhandenen Profile anzeigen:
wasprofile.bat -listProfiles
Profil löschen (unbedingt vor dem Abmelden durchführen !
wasprofile.bat -delete -profileName WolfgangProfile
Die Profile-Registry findet sich hier:
C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\properties\profileRegistry.xml
Auszug (für das oben erzeugte Beispielprofil):
<?xml version="1.0" encoding="UTF-8"?>
<profiles>
<profile isDefault="true" name="default" path="C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profiles\default" template="C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profileTemplates\default"/>
<profile isDefault="false" name="WolfgangProfile" path="c:\temp\WolfgangProfile" template="C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profileTemplates\default"/>
</profiles>
Jetzt definieren wir den Server im Eclipse:
In der Karteikarte "Servers" (hier sollte nur der Default-Server stehen) einen Rechtsklick und "New" -> "Server"
wählen.
Als Servertyp "WebSphere v6.0 Server" wählen.
Im nächsten Schritt geschieht das wichtigste überhaupt: das Profil wählen.
Den Servernamen unbedingt auf "server1" belassen, wenn man hier etwas anderes einträgt wird
kein gültiger Server erzeugt.
Des woars.
Jetzt können wir den Server per Rechtsklick starten, oder auch per Kommandozeile (ihr wißt ja, die Harten...):
Für letzteres ins Profile wechseln und folgendes aufrufen:
bin\startServer.bat server1 -profileName WolfgangProfile
Das Stoppen geht genauso:
bin\stopServer.bat server1 -profileName WolfgangProfile
Universal Test Client:
Unser neu erzeugtes Profil enthält direkt nach dem Erzeugen noch nicht den Universal Test Client, mittels dem
wir Beans einfach und schnell testen können.
Er wird allerdings beim ersten Deploy einer Anwendung aus Eclipse heraus zugefügt. Wir finden
ihn im Unterverzeichnis "installedApps\myCell\IBMUTC.ear" in unserem Profil.
Eigene Datenbank
Per Default landen die Daten all unserer Entity-Beans in einer Datenbank namens "TopDownDB" im Verzeichnis
"C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\cloudscape\". Dies ist nicht gut, besser wäre es pro Anwendung
eine eigene Datenbank anzulegen.
Dies geht so:
- Zuerst eine neue Enterprise Application anlegen, die ein EJB-Project enthält.
- Eine Entity Bean zufügen.
- Jetzt die Datenbankdefinition erzeugen. Am besten jetzt tun, da ansonsten später ein Assistent zuschlägt
und uns die Default-Datenbank "TopDownDB" erzeugt. Dazu: Rechtsklick auf den Deployment Deskriptor des EJB-Projekts,
"EJB to RDB Mapping" -> "Generate Map" wählen.
Wir wählen im ersten Schritt die Option "Create a new backend folder".
In Schritt 2 das Mapping nach "TopDown"-Verfahren (Datenbank wird aus der Bean-Struktur erzeugt) erzeugen.
In Schritt 3 einen Datenbanknamen vergeben, der individuell sein sollte (im Beispiel: "KnaufDB").
- Das Ergebnis im Project Explorer sollte so aussehen (Das Beispiel enthält eine Bean namens "EigeneBean" mit den
Feldern "id" und "name"):
Im EJB-Projekt unter "META-INF\CLOUDSCAPE_V51_1\backends" liegt das Schema-Mapping unserer Bean. In "Databases" liegt
unsere KnaufDB.
- Jetzt muss man eine DataSource (Verbindung zur Datenbank im Deployment Deskriptor der Enterprise Application)
anlegen. Das passiert automatisch wenn wir die Anwendung jetzt erst (nach dem Erzeugen des Schema-Mappings)
auf den Server packen.
- Falls wir nachträglich etwas an den Feldern der Bean ändern oder neue Beans zufügen, müssen wir das
Datenbankschema aktualisieren (wird uns durch Fehlermeldungen deutlich gemacht). Dazu wieder "EJB to RDB Mapping" ->
"Generate Map" wählen. ACHTUNG: der Menüpunkt ist disabled wenn wir die zugehörige Datei "Map.mapxmi" gerade geöffnet
haben. Das Mapping soll im bestehenden Backend Folder erfolgen, die Option "Create and map unmapped elements"
wird gewählt. Dadurch wird das Mapping ohne weitere Interaktion komplett neu erzeugt.
Nachträgliches Ändern des Database Mappings:
Schritt 1: Zuerst einmal ändern wir den Namen des Schema-Mappings (das im Beispiel der Standard "TopDownDB" ist): Rechtsklick auf
"Databases" -> "TopDownDB" und "Open" wählen. Jetzt können wir das Backend beliebig umbenennen.
Schritt 2: Ändern des Namens im Deployment Deskriptor der Enterprise Application. Dazu den Deployment Deskriptor der
Enterprise Application öffnen. Auf die Karteikarte "Deployment" wechseln. In der Liste "JDBC provider list" den Provider
"A Cloudscape v5 JDBC provider" wählen. In der Liste der Data Sources darunter "Cloudscape v5 unit test data source" mit
dem JNDI-Namen "jdbc/Default" wählen. Jetzt deren Properties ändern: den "databaseName" von "TopDownDB" auf den neuen Namen
setzen.
Die Property "createDatabase" kann man auf den Wert "create" ändern damit die Datenbank beim Deploy automatisch
erzeugt wird, allerdings ist das wohl nur dann nötig wenn man die Anwendung direkt auf den Server deployed, ohne
Hilfe des WebSphere Entwicklungsumgebung.
ACHTUNG: Ich empfehle alle automatisch generierten Codedateien im Bean-Projekt anschließend zu löschen und neu erzeugen
zu lassen, da es scheinbar einige gibt die fest am Namen der Datenbank hängen und jetzt als "freie" Sourcedateien
unsere Arbeit stören.
Codeformatter
Damit der Quellcode zumindest innerhalb einer Projektgruppe bei allen gleich aussieht empfehle
ich die Codeformatierungs-Optionen von Eclipse zu vereinheitlichen. Dies geschieht über "Fenster" ->
"Benutzervorgaben" -> "Java" -> "Codedarstellung" -> "Codeformatierungsprogramm", wo man ein neues Profil zufügt.
Im folgenden die in meinen Beispielen verwendeten Einstellungen:
Mit nur 2 Leerzeichen Einrückungstiefe sparen wir Platz.
Ich bevorzuge öffnende Klammern auf der gleichen Spalte wie die schließende Klammer, also
viele Zeilenumbrüche.
Passend zu den Zeilenumbrüchen vor öffnenden Klammern mag ich sie auch nach schließenden Klammern.
Die maximale Zeilenlänge bis zu einem vom CodeFormatter erzwungenen Zeilenumbruch würde
ich von 80 auf 120 erhöhen.
Sonstiges KnowHow
CView
Mittels des Tools "Cview" (C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\cloudscape\bin\embedded\cview.bat)
kann man einen Blick in die Datenbank werfen.
Bevor wir die Datenbank öffnen müssen wir den Server herunterfahren, da die DB nicht
zweimal gestartet werden kann (im Verzeichnis der Datenbank liegt eine Datei "db.lck") .
Beim ersten Start müssen wir eine Datenbankverbindung anlegen. Dies geht über "File" -> "Open...".
In dem Öffnen-Dialog gehen wir in das Verzeichnis "C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\cloudscape\"
(sollte bereits vorgewählt sein) und wählen "TopDownDB" aus.
Jetzt können wir uns durch die Datenbank klicken.
Logdateien
Falls mal der Bedarf danach besteht einen Blick ins Serverlog zu werfen: die Logdateien liegen unter diesem Pfad:
C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profiles\default\logs\server1\trace.log
Logausgabe über das Package java.util.logging
:
Die Logausgaben über das Packages "java.util.logging" landen im Default in einer Datei,
die wir hier finden: C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profiles\default\logs\activity.log.
Wir können nicht wie im Beispiel für JBoss in die Logging-Konfiguration eingreifen da WebSphere
einen eigenen Logging-Manager verwendet, der seine Config nicht aus "logging.properties" zieht.
Als Beweis: man öffne die Datei "C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profiles\default\bin\setupCmdLine.bat"
und betrachte diese Zeile:
SET WAS_LOGGING=-Djava.util.logging.manager=com.ibm.ws.bootstrap.WsLogManager -Djava.util.logging.configureByServer=true
Die erzeugten Logeinträge sind für uns nicht lesbares XML. Ein einziger Logeintrag sieht so aus (Beispiel "Kuchen", ejbActivate
der KuchenSingleBean):
<CommonBaseEvent creationTime="2005-10-04T20:59:22.703Z" globalInstanceId="turbotante:520:170" msg="ejbActivate" severity="10" version="1.0.1">
<extendedDataElements name="level" type="noValue">
<children name="name" type="string">
<values>INFO</values>
</children>
<children name="value" type="int">
<values>800</values>
</children>
</extendedDataElements>
<extendedDataElements name="sequenceNumber" type="long">
<values>403</values>
</extendedDataElements>
<extendedDataElements name="threadID" type="int">
<values>68</values>
</extendedDataElements>
<extendedDataElements name="localizable" type="string">
<values>yes</values>
</extendedDataElements><extendedDataElements name="loggerName" type="string">
<values>com.knauf.ejb.kuchen.KuchenSingleBean</values>
</extendedDataElements>
<extendedDataElements name="version" type="string">
<values>Platform 6.0 [BASE 6.0.0.0 o0444.14] </values>
</extendedDataElements>
<extendedDataElements name="correlationId" type="string">
<values>5-4136f1fd-6856406:turbotante</values>
</extendedDataElements>
<sourceComponentId component="com.knauf.ejb.kuchen.KuchenSingleBean" componentIdType="Unknown" executionEnvironment="Windows XP[x86]#5.1 build 2600 Service Pack 2" instanceId="localhostNode01Cell\localhostNode01\server1" location="turbotante" locationType="Hostname" processId="520" subComponent="Unknown" threadId="ORB.thread.pool : 1" componentType="http://www.ibm.com/namespaces/autonomic/WebSphereApplicationServer"/>
<msgDataElement msgLocale="de_DE">
<msgCatalogId>ejbActivate</msgCatalogId>
</msgDataElement>
<situation categoryName="ReportSituation">
<situationType xsi:type="ReportSituation" reasoningScope="EXTERNAL" reportCategory="LOG"/>
</situation>
</CommonBaseEvent>
Der Server bringt aber zum Glück eine Utility mit um diese Logeinträge anzuschauen. Hierzu den Server
starten und per Rechtsklick "Run administrative Console" aufrufen. Ein Browserfenster erscheint und
fordert einen Benutzernamen von uns. Hier müssen wir nichts eingeben sondern können direkt auf "Anmelden" klicken.
Im Baum rechts wird "Fehlerbehebung" -> "Laufzeitnachrichten" -> "Information" gewählt (da unsere Bean auf dem Loglevel
"INFO" loggt). Jetzt sollten wir unsere Logeinträge finden.
Eine andere Möglichkeit das Log anzuzeigen ist das Tool "Showlog" im Verzeichnis
"C:\Programme\IBM\Rational\SDP\6.0\runtimes\base_v6\profiles\default\bin". Wir übergeben ihm
die Logdatei und erhalten eine lesbarere Ausgabe: "showlog.bat ..\logs\activity.log".
Die Konfiguration für "activity.log" findet man ebenfalls im Administrative Client. Man geht
über "Fehlerbehebung" -> "Protokolle und Trace" -> "server1" -> "IBM Serviceprotokolle" und gelangt in
dieses Fenster:
Bugs
Nobody is perfect, deshalb gibt es hier die Sammlung der schlimmsten WebSphere-Klöpse.
EJB-Referenzen
Im KuchenZutat-Beispiel gibt es im Dialog für das Bearbeiten der
EJB-Relationship "Kuchen-Zutat" ein komisches Verhalten: Jedesmal wenn man den Dialog öffnet
und auf Finish klickt hat die Checkbox "Cascade Delete" der Rolle "zutaten" beim nächsten Öffnen ihren Check-Status gewechselt,
mit fatalen Auswirkungen für die Deklaration des Casacade Delete im Deployment Deskriptor.
Hier das Bild nochmal verlinkt:
So sollte es im Deployment-Deskriptor richtig sein (fett markiert die kritische Stelle):
<relationships>
<ejb-relation>
<ejb-relation-name>Kuchen-Zutat</ejb-relation-name>
<ejb-relationship-role id="EJBRelationshipRole_1129146778234">
<ejb-relationship-role-name>kuchen</ejb-relationship-role-name>
<multiplicity>Many</multiplicity>
<cascade-delete />
<relationship-role-source>
<ejb-name>Zutat</ejb-name>
</relationship-role-source>
<cmr-field>
<cmr-field-name>kuchen</cmr-field-name>
</cmr-field>
</ejb-relationship-role>
<ejb-relationship-role id="EJBRelationshipRole_1129146778250">
<ejb-relationship-role-name>zutaten</ejb-relationship-role-name>
<multiplicity>One</multiplicity>
<relationship-role-source>
<ejb-name>Kuchen</ejb-name>
</relationship-role-source>
<cmr-field>
<cmr-field-name>zutaten</cmr-field-name>
<cmr-field-type>java.util.Collection</cmr-field-type>
</cmr-field>
</ejb-relationship-role>
</ejb-relation>
</relationships>
Und so sieht es bei jedem zweiten Versuch aus (Cascade Delete ist in die falsche Relationship-Rolle gewandert !):
<relationships>
<ejb-relation>
<ejb-relation-name>Kuchen-Zutat</ejb-relation-name>
<ejb-relationship-role id="EJBRelationshipRole_1129146778234">
<ejb-relationship-role-name>kuchen</ejb-relationship-role-name>
<multiplicity>Many</multiplicity>
<relationship-role-source>
<ejb-name>Zutat</ejb-name>
</relationship-role-source>
<cmr-field>
<cmr-field-name>kuchen</cmr-field-name>
</cmr-field>
</ejb-relationship-role>
<ejb-relationship-role id="EJBRelationshipRole_1129146778250">
<ejb-relationship-role-name>zutaten</ejb-relationship-role-name>
<multiplicity>One</multiplicity>
<cascade-delete />
<relationship-role-source>
<ejb-name>Kuchen</ejb-name>
</relationship-role-source>
<cmr-field>
<cmr-field-name>zutaten</cmr-field-name>
<cmr-field-type>java.util.Collection</cmr-field-type>
</cmr-field>
</ejb-relationship-role>
</ejb-relation>
</relationships>
Beim Spielen hatte ich übrigens auch den Zustand erreicht dass in beiden Rollen <cascade-delete />
auftauchte. Immerhin hat der Validator sich darüber beschwert ;-)
ejbCreate (id)
Sofern eine Bean keine ejbCreate
-Methode mit dem Primary Key der Bean als Parameter (also z.B.
ejbCreate (java.lang.Integer id)
) hat, wird diese nach dem Finish-Klick im Dialog der EJB-Relationship erzeugt.
Diese "darf" man anschließend wieder entfernen (in der Outline "Demote from Home interface" wählen, anschließend die Methode
sowie die zugehörige ejbPostCreate
löschen).
Version 1.2.1.2, Stand 29.12.2005
Historie:
1.0.0.0 (19.10.2005): Erstellt
1.1.0.0 (29.10.2005): Anleitung für eigene Datenbank
1.1.1.0 (10.11.2005): Bugs
1.2.0.0 (13.11.2005): Installationsanleitung und Server-Update
1.2.1.0 (17.11.2005): Eigene Datenbank: nachträgliches Update des Mappings.
1.2.1.1 (13.12.2005): Fixpack 6.0.1.1
1.2.1.2 (29.12.2005): Server-Update auf 6.0.2.5