Sofort-
kontakt
In unserem vorherigen Blog-Beitrag haben wir bereits Die Grundlagen des neuen Workflow-Moduls erklärt. Der jetzige Blog-Beitrag dagegen ist eine Schritt-für-Schritt-Anleitung um das Workflow-Modul um neue Workflow-Ereignisse und -Antworten zu erweitern und richtet sich an Dynamics NAV-Entwickler/innen.
Um beim Lesen dieser umfangreichen Anleitung nicht den „roten Faden“ zu verlieren, haben wir sie mithilfe folgender Kapiteln strukturiert:
1. Eigene Workflow-Ereignisse erstellen
1.1. Erstellen der Publisher-Funktion „SetDefaultsWorkflow“
1.2. Erstellen der Codeunit „My Workflow Event“
1.3. Erstellen der Funktion „MyWorkflowEventCode“
1.4. Erstellen der „Subscriber“-Funktion „AddMyEventsToLibrary“
1.5. Erstellen der „Subscriber“-Funktion „RunWorkflowSetCustomerDefault“
1.6. Das erstellte Ereignis im RTC testen
2. Eigene Workflow-Antworten erstellen
2.1. Erstellen einer neuen Codeunit
2.2. Erstellen der „Subscriper“-Funktion „MyWorkflowResponseCode“
2.3. Erstellen der neuen Funktion „AddMyWorkflowResponsesToLibrary“
2.4. Erstellen der Funktion „MyWorkflowResponse“
2.5. Erstellen der Funktion „ExecuteMyWorkflowResponses“
3. Eigene Antwortoption erstellen
3.1. Einfügen eines Feldes in die Tabelle „Workflow Step Argument“
3.2. Einfügen eines Feldes auf die Seite/Page „Workflow Response Options“
3.3. Eintragen der Eigenschaften des Feldes „My New Response Option“
3.4. Ändern des Codes in der Funktion „AddMyWorkflowResponsesToLibrary“
3.5. Löschen des Datensatzes aus der Tabelle „Workflowreaktion“
3.6. Einstellen eines weiteren Parameters in der Funktion „MyWorkflowResponse“
3.7. Erstellen einer neuen lokalen Variable in der Funktion „MyWorkflowResponse“
3.8. Abgleichen des fertigen Codes
3.9. Testen der Workflow-Antwort
1. Eigene Workflow-Ereignisse erstellen
Es wird zunächst eine „Herausgeber“-Funktion („Publisher“) erstellt, welche von anderen Funktionen „abonniert“ („Subscriber“) werden kann. Als Beispiel werden wir ein Ereignis erstellen, das ausgelöst wird, sobald das Feld „Kontakt“ auf der „Debitorenkarte“ geändert wird.
1.1. Erstellen der „Publisher“-Funktion „SetDefaultsWorkflow“
In der Tabelle „Customer“ (ID 18) erstellen wir die neue Funktion „SetDefaultWorkflow“. Dafür gehen wir in das Fenster „C/AL Globals“ in die Registerkarte „Functions“ und geben den Namen unserer neuen Funktion in die neue Zeile ein.

Anschließend gehen wir in die Eigenschaften der Funktion und tragen folgende Änderungen ein:

Als vorerst letzten Schritt gehen wir in den C/AL Code-Editor und suchen die Funktion „Contact - OnValidate“, da das Workflow Event jedes Mal ausgelöst werden soll, sobald der Datensatz im Feld „Kontakt“ geändert wird. Dort geben wir „SetDefaultWorkflow(Rec);“ ein.

Wichtig ist hierbei zu beachten, dass die von uns erstellte Funktion erst am Ende eingefügt wird, da der „OnValidate“-Trigger erst durchlaufen muss.
1.2. Erstellen der Codeunit „My Workflow Event“
Gehen wir nun über den Object-Designer in die Übersicht der Codeunits und klicken unten links auf „New“ um eine neue leere Codeunit erstellen zu können. Diese speichern wir unter dem Namen „My Workflow Event“ (ID 50000). Natürlich lässt sich auch ein anderer Name oder eine andere ID verwenden.
1.3. Erstellen der Funktion „MyWorkflowEventCode“
Nun gehen wir in die „C/AL Globals“ und erstellen die neue Funktion „MyWorkflowEventCode“.

In den „C/AL Locals“ gehen wir in die „Return Value“-Registerkarte und geben folgendes ein:

1.4. Erstellen der „Subscriber“-Funktion „AddMyEventsToLibrary“
Nun wird es Zeit unsere „Subscriber“ zu erstellen, welche das „Publisher“-Event „SetDefaultsWorkflow“ abonnieren. Dafür gehen wir wieder in die „C/AL Globals“ und erstellen die Funktion „AddMyEventsToLibrary“.

Diese Funktion wird dafür sorgen, dass das Workflow-Event später in der Ereignis-Übersicht des Workflows erscheint.
Öffnen wir für diese Funktion die Eigenschaften und füllen die Felder folgendermaßen aus:

Nun erstellen wir eine neue globale Variable mit dem Namen „WorkflowEventHandling“, welche auf die Codeunit „Workflow Event Handling“ (ID 1520) zugreift.

Gehen wir jetzt wieder in den Code-Editor zurück und schreiben folgende Zeile Code in neue Funktion:
WorkflowEventHandling.AddEventToLibrary(MyWorkflowEventCode, DATABASE::Customer,'Das Feld Kontakt wurde geändert',0,FALSE);
Somit wäre nun dafür gesorgt, dass das Event mit den Worten „Das Feld Kontakt wurde geändert“ in der Übersicht der Workflow-Ereignisse erscheint.
1.5. Erstellen der „Subscriber“-Funktion „RunWorkflowSetCustomerDefault“
Zum Schluss erstellen wir eine weitere „EventSubscriber“-Funktion und benennen diese „RunWorkflowSetCustomerDefault“. Dabei gehen wir wie bereits in der ersten Funktion vor.
Nachdem wir die Eigenschaften entsprechen geändert haben, müssen wir eine lokale Variable erstellen, welche auf die Tabelle Customer zugreift.

Nun erstellen wir noch eine globale Variable und benennen diese „WorkflowManagement“, welche sich auf die Codeunit „Workflow Management“ (ID 1501) bezieht.

1.6. Das erstellte Ereignis im RTC testen
Gehen wir nun in die Übersicht „Workflow“ und erstellen einen neuen Workflow. Wir tragen dort einen beliebigen Namen in den Feldern „Code“ und „Beschreibung“ und wählen eine entsprechende Kategorie aus. Für unser Beispiel wählen wir den Code „HINWEIS KONTAKTFELD“ und die Beschreibung „Das Kontaktfeld auf der Debitorenkarte wurde geändert“.

Öffnen wir nun die Ereignisübersicht.

Bei der Bedingung können Sie nun eine beliebige Option setzen. Für unser Beispiel belassen wir den Standardwert „<Immer>“. Für die Antwort wählen wir, der Einfachheit halber, „Zeigen Sie die Nachricht „<Nachricht>“ an.“ aus und tragen in das entsprechende Feld „Meldung“ „Der Kontakt wurde geändert.“ ein.

Anschließend sollte unser Workflow folgendermaßen aussehen.

Nun müssen wir den Workflow nur noch aktivieren. Hierzu klicken wir in das Feld „Aktiviert“ und setzen somit das entsprechende Häkchen.
Gehen wir nun in eine beliebige Debitorenkarte und ändern den Wert des Feldes „Kontakt“.


Sobald wir nun diesen neuen Wert eingetragen haben, erscheint folgende Meldung:

2. Eigene Workflow-Antworten erstellen
Der Standard von Microsoft Dynamics NAV 2016 bietet im Bereich der Workflow-Antworten einen recht begrenzten Inhalt. Es besteht aber die Möglichkeit, das Workflow-Modul um eigene Workflow-Antworten zu erweitern.
Wir möchten nun das Beispiel aus dem vorherigen Kapitel aufgreifen und erweitern. Wird nämlich der Wert des Feldes „Kontakt“ geändert, soll die entsprechende Kontaktkarte aufgerufen werden. Ist dem eingetragenen Kontakt allerdings keine Kontaktkarte hinterlegt, soll eine entsprechende Meldung ausgegeben werden.
2.1. Erstellen einer neuen Codeunit
Im Object Designer erstellen wir eine neue Codeunit mit dem Namen „My Workflow Responses“.
2.2. Erstellen der „Subscriber“-Funktion „MyWorkflowResponseCode“
In dieser neuen Codeunit erstellen wir nun eine neue „Subscriber“-Funktion mit dem Namen „MyWorkflowResponseCode“. Dafür füllen wir die Eigenschaften wie bei den bisherigen „Subscriber“-Funktionen.
Öffnen wir nun die lokalen Variablen dieser Funktion und erstellen einen neuen Rückgabewert.

2.3. Erstellen der neuen Funktion „AddMyWorkflowResponseToLibrary“
Erweitern wir unsere Codeunit mit einer neuen Funktion, welche unsere Antwort in der Übersicht/Bibliothek der Workflowantworten einsetzt. Wir nennen sie daher „AddMyWorkflowResponsesToLibrary“.
Öffnen wir die Eigenschaften dieser Funktion und setzen die folgende Eigenschaften:

Nach diesem Schritt gehen wir in die „C/AL Locals“ und erstellen die neue Variable „WorkflowResponseHandling“, welche auf die Codeunit „Workflow Response Handling“ (ID 1521) zugreift.

Gehen wir nun zurück in den Code-Editor und fügen folgende Zeile Code ein:
WorkflowResponseHandling.AddResponseToLibrary(WorkflowResponseCode, DATABASE::Customer, 'Öffnen Sie die Kontaktkarte, wenn vorhanden','GROUP 50000');
2.4. Erstellen der Funktion „MyWorkflowReponse“
Erstellen wir nun eine weitere Funktion, welche genutzt wird um unsere Antwort zu implementieren. In unserem Beispiel wäre das die Funktion „MyWorkflowResponse“.
Gehen wir anschließend wieder in die „C/AL Locals“ und tragen folgende Werte für die Parameter ein:

Zu guter Letzt tragen wir noch die folgende Zeile Code in unsere gerade erstellte Funktion:
Contact.SETRANGE(Name,Customer.Contact);
IF Contact.FINDFIRST THEN
PAGE.RUN(PAGE::"Contact Card",Contact)
ELSE
MESSAGE('Dem Kontakt ist keine Kontaktkarte zugeordnet');
In dieser Abfrage wird geprüft, ob eine Kontaktkarte zum eingetragenen Kontakt vorhanden ist. Ist dies der Fall wird diese Seite aufgerufen. Wenn nicht, erscheint die Meldung „Dem Kontakt ist keine Kontaktkarte zugeordnet“.
2.5. Erstellen der Funktion „ExecuteMyWorkflowResponses“
Nun erstellen wir noch eine Funktion, welche dafür sorgt dass unsere Workflowantwort ausgeführt wird. Daher nennen wir sie „ExecuteMyWorkflowResponses“.

Öffnen wir die Eigenschaften und füllen die Felder wie folgt:

Schreiben wir nun noch folgenden Code in die Funktion:
IF WorkflowResponse.GET(ResponseWorkflowStepInstance."Function Name") THEN
CASE WorkflowResponse."Function Name" OF
MyWFResponseCode:
BEGIN
MyWorkflowResponse(Variant);
ResponseExecuted := TRUE;
END;
END;
Nun können wir unsere Antwort in der entsprechenden Tabelle auswählen.
3. Eigene Antwortoption erstellen
Ihnen sind doch bestimmt schon die fett hinterlegten Antworten für ein bestimmtes Ereignis aufgefallen. Dabei handelt es sich um vom Standard vorgeschlagene Antworten zu dem jeweiligen Ereignis.
Wir möchten nun, dass unsere erstellte Antwortmöglichkeit vorgeschlagen wird, sobald unser erstelltes Ereignis aus dem ersten Teil ausgewählt wird, wie auf diesem Bild zu erkennen ist.

3.4. Ändern des Codes in der Funktion „AddMyWorkflowResponsesToLibrary“
Anschießend gehen wir zurück in die „AddMyWorkflowResponsesToLibrary “-Funktion in der „My Workflow Response“-Codeunit und ändern folgende Zeile Code:
WorkflowResponseHandling.AddResponseToLibrary(MyWorkflowResponseCode, DATABASE::Customer,'Öffnen Sie die Kontaktkarte, wenn vorhanden', 'GROUP 0');
in
WorkflowResponseHandling.AddResponseToLibrary(MyWorkflowResponseCode, DATABASE::Customer,'Öffnen Sie die Kontaktkarte, wenn vorhanden', 'GROUP 50000');
3.5. Löschen des Datensatzes aus der Tabelle „Workflowreaktion“
Damit unsere Änderungen nun greifen können, müssen wir den bereits vorhanden Datensatz in der Tabelle „Workflowreaktion“ löschen.
Suchen Sie dafür die Tabelle im Objekt Designer und führen Sie diese aus. Nun öffnet sich Ihnen der RTC und die Tabelle „Workflowreaktion“ wird aufgerufen. Suchen wir den Datensatz „Öffnen Sie die Kontaktkarte, wenn vorhanden“ und löschen diesen.
3.6. Einstellen eines weiteren Parameters in der Funktion „MyWorkflowResponse“
Zurück in der Funktion „MyWorkflowResponse“ öffnen wir die „C/AL Locals“ und geben den folgenden neuen Parameter an.

3.7. Erstellen einer neuen lokalen Variable in der Funktion „MyWorkflowResponse“
Außerdem erstellen wir eine neue lokale Variable mit dem Namen „WorkflowStepArgument“, welche auf die Tabelle „Workflow Step Argument“ (ID 1523) verweist.

3.8. Abgleichen des fertigen Codes
Ist dies soweit erledigt, sollte in Ihrem Code-Editor nun folgendes zu sehen sein:

3.9. Testen der Workflow-Antwort
Ist dies erledigt, sollten Sie nun als vorgeschlagene Antwortmöglichkeit unsere erstellte Antwort sehen.
