Wie man das Codegenerierungsframework des Enterprise Architect anpassen kann.
Dieser Artikel beschreibt wie Sie das Codegenerierungsframework des EA anpassen können, um den gewünschten Code aus Modellen zu generieren.
Ein paar einführende Worte:
Das Codegenerierungsframework des EA basiert auf Templates. Jedes Template hat einen Typ (Class, Attribute, Operation, etc.) und wird beim Generieren auf das gerade zu verarbeitende Modellelement angewendet. Mittels dem Template kann auf alle Eigenschaften des zu verarbeitenden Modellteils zugegriffen werden. Im Kontext des Attributes auf alles, was das Attribut betrifft. Im Kontext der Klasse, alle Eigenschaften der Klasse, auch auf die Liste der Attribute, allerdings nicht auf die Eigenschaften jedes einzelnen Attributes. Attributeigenschaften können nur über das Attribut-Template abgefragt werden!
In den Templates können Modelleigenschaften über sogenannte Substitutionsmakros abgefragt werden. Als Ergebnis erhält man Zeichenketten, die wiederum mit Stringmanipulations-Funktionen bearbeitet werden können. Zum Beispiel können damit Zeichen ersetzt werden etc. Über Kontrollstrukturen wie z. B. if-then-else und variablen, können Bedingungen in das Template eingearbeitet werden.
Das Framework bietet eine vordefinierte Liste von Substitutionsmakros, um auf Mdelleigenschaften zuzugreifen und Funktionen, um die Ergebnisse weiter zu verarbeiten.
Nun kommen wir zu dem interessanteren Teil dieses Artikels. Möchten Sie eine Modelleigenschaft abfragen, welche noch nicht durch ein Substitutionsmakro geliefert wird oder eine komplexere Modellstruktur verarbeiten, können Sie das Framework selbständig erweitern!
Das Codegenerierungsframework bietet eine Funktion mit Namen EXEC_ADD_IN(…) mit dessen Hilfe ein selbstgeschriebenes Add-in (EA Erweiterung) aufgerufen werden kann. In dem Add-in hat man Zugriff auf das gesamte Modell und kann beliebige Berechnungen durchführen. Als Ergebnis der aufgerufenen Funktion erwartet EXEC_ADD_IN einen String als Rückgabewert.
Als konkretes Beispiel möchte ich ein Problem eines unserer Kunden aufgreifen. Aktuell ist die vordefinierte Funktion EASL_GET(…), welche es erlaubt aus dem Modell zusätzliche Eigenschaften abzufragen, auf den gerade verarbeiteten Modellzweig im Project Browser beschränkt! Möchte man damit z. B. auf ein Modellelement zugreifen, welches in einem anderen Paket liegt, ist dies nicht möglich.
Wir können nun unsere eigene Funktion MyEASL_GET(…) schreiben und mit Hilfe von EXEC_ADD_IN aus einem Code-Template aufrufen. Der Aufruf aus dem Template sieht dann folgendermaßen aus:
public string MyEASL_GET(Repository rep, object args)
{
string result = „“;
try
{
var p = (Array) args;
var what = p.GetValue(0) as string;
var owner = p.GetValue(1) as string;
var name = p.GetValue(2) as string;
switch (what)
{
case „element“:
Element ownerElement = rep.GetElementByGuid(owner);
result = ownerElement != null ? GetElementProperty(rep, ownerElement, name) : „“;
break;
case „attribute“:
EA.Attribute diagramByGuid = rep.GetAttributeByGuid(owner);
result = diagramByGuid != null ? GetAttributeProperty(rep, diagramByGuid, name) : „“;
break;
}
}
catch (Exception e)
{
rep.CreateOutputTab(Output);
rep.EnsureOutputVisible(Output);
rep.WriteOutput(Output, string.Format(„Error in Function MyEASL_GET: {0}„, e.Message), 0);
}
return result;
}
Dieser Aufruf führt zur Ausführung folgender Add-in Operation:
public static string GetElementProperty(EA.Repository repo, EA.Element element, string name)
{
Type elementAsType = element.GetType();
PropertyInfo property = elementAsType.GetProperty(name);
if (property != null) //there is a property of name: name
{
object value = property.GetValue(element, null);
return value.ToString();
}
throw new Exception(string.Format(„EA Element of type: {0} do not has aproperty with name: {1}„, element.Type, name));
}
Die eigentliche Arbeit wird allerdings von dieser Operation geleistet:
Mit der Operation MyEASL_GET(…) kann man nun generisch auf alle Eigenschaften eines Elements zugreifen. Die Operation MyEASL_GET(…) übernimmt dabei lediglich die Aufgabe, die richtige Operation aufzurufen.
Jede beliebige Eigenschaft eines Elements oder Attributes kann nun abgefragt werden. In dem Operationsparameter „name“ wird der Eigenschaftsnamen, dessen Wert abgefragt werden soll, übergeben. Die Variable $GUID, beim Aufruf aus dem Template, übergibt die eindeutige ID des Modellelements, von dem die Eigenschaft abgefragt werden soll. Die Zeichenkette „element“ erlaubt es Eigenschaften eines Elements abzufragen und wird von der Operation MyEASL_GET(…) ausgewertet.
Wird nun MyEASL_GET aus einem Attribute-Template aufgerufen, beinhaltet $GUID die guid des Attributes. Wird als 3. Parameter „attribut“ übergeben, kann jede Attributeigenschaft abgefragt werden.
Falls sie weitere Informationen oder Unterstützung bezüglich der Anpassung des Codegenerierungsframework suchen, schreiben sie einfach an: vendor@Sparxsystems.eu.
Eine Alternative zum EA-Codegenerator ist das Codegenerierungsframework UML2Code unseres Partners LieberLieber.