• Keine Ergebnisse gefunden

5 Übersetzung des Scopes

5.1 Scope

Jeder Scope enthält eine primäre Aktivität, die beim Aktivieren des Scopes ausgeführt wird.

Die primäre Aktivität kann jede beliebige BPEL-Aktivität sein. Der Kontext eines Scopes wird durch seine spezifizierten Variables, PartnerLinks, MessageExchanges, CorrelationSets, EventHandlers, FaultHandlers, CompensationHandler und TerminationHandler gebildet.

Dieser Kontext beeinflusst die Ausführung aller Aktivitäten, die in diesem Scope eingeschlossen sind. Durch Verschachtelung von Scopes kann sogar eine Kontext-Hierarchie aufgebaut werden.

Beim Aktivieren eines Scopes werden seine primäre Aktivität sowie seine EventHandlers ausgeführt. Nach ihrem Beenden müssen alle Web Service Interaktionen, die auf einem PartnerLink oder anhand eines MessageExchanges, die in diesem Scope deklariert sind, ausgeführt werden, abgeschlossen sein. Dazu wird eine Überprüfung nach verwaisten IMAs (vgl. Abschnitt 3.2) durchgeführt. Eine solche verwaiste IMA existiert, wenn eine IMA auf einem PartnerLink oder MessageExchange, die in dem Scope oder seine Kinder-Scopes deklariert sind, offen bleibt. In diesem Fall wird der BPEL-Standardfehler bpel:missingReply signalisiert. In [OAS07a] sind die Kriterien spezifiziert, nach denen verwaiste IMAs entdeckt werden. Diese werden deswegen an dieser Stelle nicht erläutert, sondern es wird lediglich auf die genannte Spezifikation verwiesen.

Ein Scope wird entweder fehlerfrei oder mit einem Fehler beendet. Dabei werden drei Fälle unterschieden.

• normale Terminierung: die primäre Aktivität wird fehlerfrei beendet und es werden keine verwaiste IMAs entdeckt. Danach werden die EventHandlers deaktiviert, wobei die aktiven EventHandlers-Instanzen zu Ende ausgeführt werden. Der CompensationHandler wird installiert und damit wurde der Scope fehlerfrei ausgeführt.

• interner Fehler: in der primären Aktivität wird einen Fehler signalisiert. Alle aktiven Aktivitäten innerhalb der primären Aktivität, sowie alle laufenden EventHandlers-Instanzen werden terminiert. Ein entsprechender FaultHandler wird ausgeführt. Der Scope wird mit einem Fehler beendet.

externe Terminierung: der aktive Scope wird durch ein Termination-Signal (aufgrund eines externen Fehlers oder einer Completion Condition) gestoppt. Alle aktiven

<scope>

<variables>?

</variables>

<partnerLinks>?

...

</partnerLinks>

<messageExchanges>?

...

</messageExchanges>

<correlationSets>?

...

</correlationSets>

<eventHandlers>?

...

</eventHandlers>

<faultHandlers>?

...

</faultHandlers>

<compensationHandler>?

...

</compensationHandler>

<terminationHandler>?

...

</terminationHandler>

<flow>

</flow>

</scope>

Listing 18: Definition eines Scopes

In Abbildung 21 ist das Scope-EWFN dargestellt.

EWFN sind ausserdem die Plätze Variables, Correlations, PartnerLinks, P1 und P2 enthalten. Auf diese wird von allen enthaltenen EWFNs zugegriffen und sie werden von der Scope-Transition T1 initialisiert. Wie jede andere BPEL-Aktivität verfügt das Scope-EWFN über die generische Schnittstelle für alle EWFNs, nämlich die Plätze start, ended und failed.

Die Plätze to_MW und from_MW bilden die Schnittstelle zu der Middleware-Komponente.

Diese wird das Terminieren aller laufenden Aktivitäten, ausgenommen Kinder-Scopes, in dem Scope veranlassen. Über den Plätze terminate_CS werden alle Kinder-Scopes aufgefordert ihre aktiven inneren Aktivitäten zu terminieren und das Terminieren über den Platz terminated_CS zu propagieren. Dieses Verhalten wird für den aktuellen Scope anhand der Plätze terminate und terminated_toFS gewährleistet. Der CH-Platz bildet die Schnittstelle zu einer Compensation-Aktivität (vgl. Abschnitt 5.6), die in dem Vater-Scope eingeschlossen ist.

In diesem Platz werden die IDs der fehlerfrei ausgeführten Scope-Instanzen gespeichert, die dann von einer Compensation-Aktivität in DCO (vgl. Abschnitt 5.5) aufgerufen werden. Der Platz IDs speichert die ID der nächsten zu erzeugenden Scope-Instanz. Über den Platz P2 wird die Entdeckung von verwaisten IMAs vorgenommen. Dieser Platz stellt eine Aggregation der P2-Plätze aller Kinder-Scopes, d.h. in einem konkreten BPEL-Prozessmodell wird dieser Platz durch die P2-Plätze aller Kinder-Scopes, einschließlich des Scopes selbst, ersetzt.

Der State-Platz speichert den Zustand des Scopes. Dabei werden folgende Werte unterschieden:

not_running: dieser Zustand ist der Default-Zustand für jeden Scope. Jeder State-Platz wird mit diesem Wert vorinitialisiert. Dieser Zustand signalisiert, dass der Kontrollfluss noch nicht bei dem Scope angekommen ist und dadurch eine ForcedTermination nicht laufen wird.

running: durch diesen Zustand wird signalisiert, dass eine ForcedTermination ausgeführt werden wird. wurde und dadurch keine ForcedTermination ausgeführt wird. Zusätzlich wird in diesem Zustand der CompensationHandler ausgeführt.

ended_notC: der CompensationHandler wird solange warten bis die Links in dem FaultHandlers und dem TerminationHandlers auf dem Wert false gesetzt worden sind.

terminating: eine ForcedTermination aus dem Vater-Scope wird durch diesen Zustand signalisiert. Dadurch wird der FaultHandler eine ForcedTermination nicht nochmals starten.

terminated: eine ForcedTermination aus dem FaultHandlers wird durch diesen Zustand signalisiert. Dadurch wird einer ForcedTermination aus dem Vater-Scope signalisiert, dass der FaultHandler zu Ende ausgeführt worden ist.

Die Evaluierung des Kontrollflusses im Scope-EWFN wird anhand der nachfolgenden Szenarien erläutert.

Im ersten Szenario wird angenommen, dass der Scope aktiviert wird und seine primäre Aktivität fehlerfrei ausgeführt wird. In diesem Fall liegt ein CF-Token auf dem start-Platz des

Scope-EWFNs. Die Transition T1 schaltet und liest aus dem Platz IDs die ID der erzeugenden Scope-Instanz. Bevor die ID zurückgeschrieben wir, wird sie inkrementiert. Durch diese ID wird der Zustand des Scopes dargestellt. Dieser Zustand besteht aus allen spezifizierten Variables, PartnerLinks, CorrelationSets sowie alle Tupel, die in den Plätzen P1 und P2 gespeichert werden und die der Entdeckung von Fehlern dienen. Die ID der Scope-Instanz wird in allen Tokens, die in dem Scope durchgereicht werden mit übertragen. Sie wird in dem History-Feld eines Kontrollfluss-Tokens (vgl. Abschnitt 2.3) als letzte Komponente angehängt. Wird der Kontrollfluss an den Vater-Scope zurückgegeben wird die ID aus dem History-Feld gelöscht. Als nächstes instanziert T1 alle Variables, PartnerLinks und CorrelationSets. Dazu werden die Plätze Variables, PartnerLinks und Correlations gebraucht.

Für jede spezifizierte Variable wird ein Tupel mit dem Namen und der ID der Scope-Instanz in den Variables-Platz geschrieben. Das gleiche wird für die PartnerLinks und die CorrelationSets gemacht. Danach werden die Tupel in den Plätzen P1 und P2 instanziert und initialisiert. Dabei wird folgend vorgegangen. Für jeden spezifizierten PartnerLink werden ein oder mehrere Tupel in den Platz P1 geschrieben. Dieses neue Tupel wird folgend gebildet: im ersten Feld steht der spezifizierte PartnerLink, im zweiten Feld eine beliebige WSDL-Operation, die mit dem myRole-Attribut verknüpft ist, im dritten Feld ein beliebiges CorrelationSet aus dem Scope selbst oder einem Vorgänger-Scope und im letzten Feld, das der Zustand des Tupels repräsentiert, den Wert „open“. Das gleiche Verfahren wendet man für jedes spezifizierte CorrelationSet an. Der Unterschied besteht nur, dass im ersten Feld den Namen eines beliebigen PartnerLink aus dem Scope selbst oder einem Vorgänger-Scope und im dritten Feld den Namen des spezifizierten CorrelationSet steht. Die Instanzierung und Initialisierung der Tuples in dem P2-Platz wird ähnlich durchgeführt. Als nächstes wird die Transition T2 auf ein CF-Token auf dem ended-Platz der primären Aktivität warten.

Daraufhin wird der Zustand des Scopes auf den Wert ended gesetzt und DP-Tokens auf den start-Plätzen des Termination-, Fault- und EventHandlers produziert. Durch das Setzen des Zustands wird eine vom Vater-Scope signalisierte ForcedTermination nicht ausgeführt.

Irgendwann werden diese DP-Tokens auf den ended-Plätzen dieser Handlers landen, so dass die Transition T2 daraufhin den Zustand des Scope auf den Wert ended_notC setzt, ein Tupel mit dem Wert der aktuellen Scope-Instanz-ID in den CH-Platz und ein CF-Token auf den ended-Platz des Scope-EWFNs schreibt. Der Zustand ended_notC wird gebraucht, damit eine aufrufende Compensation-Aktivität abgeblockt wird, bis die Links im Fault- und TerminationHandler auf den Wert false gesetzt worden sind.

Im zweiten Szenario wird der Fall betrachtet, dass ein Fehler innerhalb der primären Aktivität signalisiert wird. In diesem Fall wird der FaultHandler die Kontrolle übernehmen und der Kontrollfluss wird wie im Abschnitt 5.2 ablaufen. Nachdem der FaultHandler zu Ende gelaufen ist, wird ein Token auf seinem ended-Platz landen. Ein CF-Token bedeutet dabei, dass der FaultHandler fehlerfrei ausgeführt wurde, dagegen signalisiert ein FAIL-Token, dass der FaultHandler mit einem Fehler beendet wurde. Die Transition T3 evaluiert im Fall eines CF-Tokens die TransitionCondition des Scopes, falls dieser einen Source-Container (vgl.

Abschnitt 4.7) spezifiziert. Danach wird ein DP-Token auf den start-Platz des

des FaultHandlers signalisiert. Der FaultHandler darf im Falle einer ForcedTermination zu Ende ausgeführt werden.

Im dritten Szenario wird eine ForcedTermination vom Vater-Scope signalisiert. In diesem Fall müssen die primäre Aktivität sowie alle laufenden EventHadlers terminiert werden.

Danach wird der TerminationHandler ausgeführt. Zu Beginn dieses Szenarios liegt ein CF-Token auf dem terminate-Platz des Scope-EWFNs. Die Transition T4 schaltet und setzt den Zustand des Scopes auf terminating. Durch diesen Zustand wird der FaultHandler nicht laufen, falls gleichzeitig mit einer vom Vater-Scope signalisierten ForcedTermination ein Fehler in der primären Aktivität signalisiert wird. Danach führt T4 die signalisierte ForcedTermination durch. Dazu wird ein zweistufiges Verfahren angewendet. Im ersten Schritt werden alle laufenden Aktivitäten in dem Scope, ausgenommen Kinder-Scopes, terminiert. Im zweiten Schritt werden alle Kinder-Scopes rekursiv terminiert. Das Terminieren aller Aktivitäten, ausgenommen Scopes, wird im Scope-EWFN folgend durchgeführt: es wird die Middleware-Komponente über den Platz to_MW aufgerufen. Ein Token in diesem Platz signalisiert der Middleware, dass sie alle Tokens aus dem Scope-EWFN, ausgenommen Kinder-Scope-EWFNs, entziehen soll. Dadurch wird der Kontrollfluss in dem Scope gestoppt. Allerdings benötigt man zusätzlich weitere Schritte, damit garantiert wird, dass alle Aktivitäten auch den Status ihrer Links auf den Wert false setzen werden.

Dazu werden alle DP- und FAIL-Tokens in dem Scope-EWFN belassen und die entzogenen CF-Tokens durch DP-Tokens ersetzt. Dieses Verhalten muss sichergestellt werden, wenn eine ForcedTermination vom Vater-Scope, vom FaultHandler oder vom TerminationHandler signalisiert wird. Terminiert dagegen eine Compensation-Aktivität die CompensationHandler-Instanzen, dann reicht es aus, alle Tokens zu entziehen. Der Grund dafür ist, dass alle Links, die in einem CompensationHandler verwendet werden, in diesem spezifiziert sein müssen und daher ohne Bedeutung für eine DPE sind [OAS07a]. Das gewünschte Verhalten wird anhand des Tupels, das in den to_MW-Platz geschrieben wird, signalisiert. Dabei unterscheidet man die folgenden Werte: scope, fh, th, ch und eh. Zusätzlich muss der Kontrollfluss auch in allen Kinder-Scopes gestoppt werden. Dazu wird der Platz terminate_CS benutzt. Dieser Platz ist mit den terminate-Plätzen aller Kinder-Scopes identisch. Dadurch werden diese ihrerseits den Kontrollfluss beenden, so dass zum Schluss so viele CF-Tokens auf dem terminated_CS-Platz liegen, wie die Anzahl der Kinder-Scopes ist.

Die Transition T4 führt also wie beschrieben die ForcedTermination durch und danach schreibt ein DP-Token auf den start-Platz des FaultHandlers. Dadurch werden die Links im FaultHandler auf den Wert false gesetzt. Danach wird ein CF-Token auf den start-Platz des TerminationHandlers geschrieben und dieser wird dadurch ausgeführt. Im Fall eines CF-Tokens auf dem ended-Platz des TerminationHandlers wird der Zustand des Scopes auf den Wert terminated gesetzt und ein CF-Token auf dem terminated_toFS-Platz des Scope-EWFNs geschrieben. Dieser Platz ist mit dem terminated_CS-Platz des Vater-Scopes identisch. Bei einem FAIL-Token wird ebenfalls ein CF-Token auf den ended-Platz geschrieben. Der Grund dafür ist, dass ein Fehler in dem TerminationHandler nicht an den Vater-Scope weitergegeben wird.

Im letzten Szenario wird der Fall betrachtet, dass der Scope nicht ausgeführt wird, d.h. es liegt ein DP- oder FAIL-Token auf dem start-Platz des Scope-EWFNs. Die Transition T1 schreibt dieses Tokens in den start-Platz der primären-Aktivität. Irgendwann wird dieses Token in ihrem ended-Platz landen, die Transition T2 wird daraufhin DP-Tokens auf die start-Plätze des Fault- und TerminationHandlers schreiben und nachdem diese ihre Links auf den Status false gesetzt haben, wird ein DP- oder FAIL-Token auf den ended-Platz des Scope-EWFNs geschrieben.

Das Process-Element in einem BPEL-Prozess ist von der Syntax und Semantik einem Scope-Element sehr ähnlich. Daher wird auf eine Übersetzung des Process-Konstrukts in einem EWFN verzichtet. Die einzigen Unterschiede zu einem Scope-EWFN sind folgend aufgelistet.

Das Process-EWFN enthält keine TerminationHandler- und CompensationHandler-EWFNs.

Die Plätze terminate, terminated_toFS, CH und der F_save-Platz im FaultHandler werden nicht gebraucht.

Da ein Process keine Links spezifizieren darf, werden alle Schritte, die eine Evaluierung von TransitionConditions vornehmen, bei der Ausführung der Process-Transitionen, ignoriert.