PDA

View Full Version : Aufrufverschachtelung RPG und Java



Seiten : [1] 2

it-wolf
06-02-02, 18:06
Aktuelles Problem auf der iSeries:

Ein RPG-Programm ruft einen Java Parser auf, der eine XML-Datei verarbeitet.
Bei bestimmten Ende-Tags wird mit einer jt400 Klasse ein RPG-Programm aufgerufen(mehrfach), das Geschäftslogik abarbeitet.
Dieses RPG-Programm ruft ein CL-Program auf. In dem CL-Programm wird mit dem CL-Befehl JAVA eine Java-Anwendung zum Versenden einer e-Mail mit den Java Mail Klassen von SUN aufgerufen.

Genau beim Aufruf dieser Java-Anwendung kommt es zum Fehler "JVAB544 - Nicht überwachte Ausnahme empfangen".

Irgendwie kommt der Job aber trotz dieses Fehlers zu Potte, dauert aber viel zu lange (ca. 15 Minuten, statt der geschätzten 2 Minuten).

Frage:
Weiß jemand, ob auf der iSeries aus einer Java Anwendung heraus über ein CL/RPG-Programm nicht wieder eine Java Anwendung aufgerufen werden darf? Oder eventuell sogar einen work around?

Danke für jeden Tip
it-wolf

CMueller@must.de
07-02-02, 08:10
Vorab "oute" ich mich gleich mal: Konkrete Erfahrung mit Java auf AS/400 habe ich (noch) keine. Aber bei meinen Erfahrungen mit Rekursionen auf der AS halte ich den geäußerten Verdacht nicht für unbegründet, dass Java-RPG-Java-Stacks problematisch sein könnten.

Weg von Verdächtigungen, hin zum Workarround:
Könnte es eine Lösung sein, die mail-Daten vom RPG-Programm in einer Datei zu puffern, und dann vom Basis-Java-Thread wieder abzuarbeiten?

Gruß, Chr****** Müller

torsten
07-02-02, 09:15
Vielleicht noch zwei andere Gedanken zu dem Problem:

Wenn der 1. Aufruf per QSH oder JAVA auf der AS400 erfolgt, der zweite über JT400, der dritte via CL und JAVA cmd (wenn ich das alles richtig verstanden habe), sollte der letzte Aufruf in einem eigenen Job und seiner eigenen VM laufen, also keine Rekursionsprobleme verursachen. Der pgmcall aus der Toolbox sollte einen QZRCSRVS Job auslösen.

Gruß

Torsten

it-wolf
07-02-02, 16:16
Danke für die guten Tips.

Ich habe noch einen Fehlerhinweis in einem der unzähligen Print-outputs gefunden, wo steht, dass ein Zugriff auf ein zerstörtes Objekt versucht wurde. Ich meine auch irgendwo gelesen zu haben, dass man bestimmen kann, ob eine neue JVM aufgemacht wird oder nicht, finde aber die Stelle nicht mehr.

Der Vorschlag, aus dem 2.RPG Programm wieder in das Java Basis Programm zurückzukehren ist sicherlich der optimale Weg. Allerdings bedeutet das eine nicht unerhebliche Änderung der Ablaufstruktur, deswegen hebe ich mir diese Lösung als letzten Weg auf.

Vorher versuche ich noch ein paar Varianten mit QSH CMD(Java ...) und SBMJOB CMD(Java ...). Allerdings habe ich dabei im Moment das Problem, dass sich die Jobs zu überholen scheinen, d.h. der zweite Job findet die Datei nicht, die der erste Job gerade erstellt hat.

Es kann sich nur noch um Stunden handeln!

it-wolf
08-02-02, 10:26
Die Nacht brachte die Erleuchtung!

Durch die Entkoppelung über Submit läßt sich das Problem lösen. Allerdings bin ich dabei in einen andern Fehler bei der Parameterübergabe gestolpert. Die CL-Statements dazu sind:

CHGVAR VAR(&CMD) VALUE('qsh cmd(''cd /lrjava; java NameDerJavaKlasse ' *CAT &FILEPARAMETER *TCAT ''')')

SBMJOB RQSDTA(&CMD) CPYENVVAR(*YES)


Was wir daraus lernen:

1. Die Aufruf-Kette "Java -> CL-Pgm -> Java" bringt erhebliche Probleme auf der iSeries, da sich anscheinend die JVMs gegenseitig verhaken.

2. Wird ein File Name als Zeichenkette, die länger als 32 Character ist, als Parameter an ein CL/RPG-Programm übergeben, muss sie mit Blanks auf die echte Länge aufgefüllt werden.
Wird dieselbe Zeichenkette an ein Java Programm übergeben, müssen die trailing Blanks vorher abgeschnitten werden. Ansonsten versucht Java auf eine Datei zuzugreifen deren Namen mit einigen Blanks endet.

Nochmanls Danke für die guten Tips!
Wolf

it-wolf
08-02-02, 15:21
Noch ein Nachsatz:

Die JVMs verhaken sich nicht, das war eine falsche Fährte. Ich habe es jetzt nochmal auf dem direkten Weg versucht:

CHGVAR VAR(&CMD) VALUE('qsh cmd(''cd /lrjava; java de.rentenbank.kreditxmlemail.SendXMLKreditAbrufRep ly ' *CAT &FILE *TCAT ''')')

CALL PGM(QCMDEXC) PARM(&CMD 512)

Der QCMDEXC ist erforderlich, damit die Blanks vorher mit *TCAT abgeschnitten werden können.

Alles Gute bis zur nächsten Stolperfalle.
Wolf

CMueller@must.de
08-02-02, 15:46
Finde ich super, dass wir auch an den sebstgemachten Erkenntnissen teilhaben dürfen!

BenderD
27-03-02, 12:23
Hallo,
Das Problem von RPG, CL und solchen Aufrufen sind Threading Probleme.
Alle aufgerufenen Programme müssen Threadsafe sein, bei RPG gibt es eine Option in den H Zeilen (irgendwas mit *SERIALIZE siehe RPG Referenz). Bei CL geht das garnicht => unpredictable Results, das was Sie da haben.
Aufrufe aus Java über RPG und zurück sind im Umfeld von Multi threaded Applications deadlock Kandidaten.
Einfachster Weg aus Java RPG aufzurufen (auch CL möglich) sind stored Procedures, d.h. RPG oder CL als stored Procedure registrieren und über SQL CALL aufrufen.
Von synchronen Aufrufen von Java und CL würde ich generell abraten, obwohl ich weiss, dass das manche nicht hören/wahrhaben wollen

mfg

Dieter Bender

torsten
27-03-02, 14:25
Ganz so dramatisch würde ich es nicht sehen ...

Sicherlich sind mehrfache Verschachtelungen wie im obigen Beispiel ziemlich fehleranfällig (deadlocks), dennoch spricht eigentlich wenig gegen einen synchronen call von java nach rpg. (z.B ProgramCall aus JT400 / im AS400 Objekt sicherheitshalber setTheadSafe(false) setzen).

Das geht natürlich genauso als Stored Procedure , vorausgesetzt man besitzt das entsprechende Lizenzprogramm (SQL DevKit ?).

Im übrigen bin ich für offene Diskussionen und gehe nicht gleich davon aus, das jemand
etwas nicht hören oder nicht wahrhaben will,
was im Einzelnen noch gar nicht diskutiert wurde ...

Gruß

Torsten

BenderD
27-03-02, 16:05
Hallo Torsten,

mit dem nicht wahrhaben war nicht das Forum gemeint, ich hatte da eher ein paar Diskussionen in der amerikanischen Java Mailing Liste und das IBM Marketing im Auge, die so tun als ob kreuz und Quer Aufrufe sinnvoll wären.
In Multithreaded Java applications ist es ein Design Kriterium aus synchronized Abschnitten nichts aufzurufen, was nicht final ist. Alles RPG was aus Java aufgerufen wird ist synchronized, also müssten die Java Methoden final sein, aber erklär das mal einem RPG Programmer.
Das mit den stored Procedures hilft nur in der einen Richtung, nämlich Java nach RPG, umgekehrt ist das wertlos, denn Java Methoden müssen als stored procedures static sein und welche sind das schon.
Fazit: es macht Sinn aus der neuen Welt bereits vorhandene Module zu nutzen, aber es macht keinen Sinn aus Rücksichtnahme in der neuen Welt Altlasten zu produzieren.
Abgesehen davon ist der Overhead für den Kontextwechsel auf der AS/400 eh schon ein KO Kriterium.

Dieter