12.3. JPA (Java Persistence API)

Die Java Plattform Erweiterung JPA ermöglicht dem Modellierer das Modell mit persistenzspezifische Informationen auf Basis der Java Persistence API (JPA) in der Version 1.0 zu versehen. GeneSEZ erzeugt aus diesen Informationen die entsprechenden Annotationen und fügt sie dem Quellcode hinzu. Die Generierung von XML-Konfigurationsdateien wird nicht unterstützt. Es wird ein grundlegendes Verständnis der JPA-Technologie vorausgesetzt.

Im nächsten Abschnitt wird das UML-Profil für die Java Plattform-Erweiterung JPA vorgestellt. Danach wird am Beispiel einer Persistent Entity gezeigt was ausgewählte Stereotypen bewirken und wie die automatische Quellcode-Ergänzung den Modellierer unterstützt. Die nachfolgenden Abschnitte beschreiben das Verhalten von Stereotypen, welche die automatische Quellcode-Ergänzung verwenden. Sie können unabhängig voneinander gelesen werden. Als Beispiel dient durchgängig das Bank-Projekt.

12.3.1. Das UML-Profil "jpa"

Figure 12-2. UML-Profil der Java Plattform-Erweiterung JPA

Figure 12-2 zeigt das UML-Profil für die Java Plattform-Erweiterung JPA. In dem Profil sind die verschiedenen Stereotypen mit ihren TaggedValues und den dazugehörigen Enumerations enthalten. Die Enumerations werden als Datentypen einiger TaggedValues verwendet, falls diesen fest definierte Werte zugewiesen werden müssen. Dadurch werden dem Modellierer direkt die möglichen Werte (am besten durch das Modellierungstool) vorgegeben und Tippfehler vermieden.

12.3.2. Eine Einführung - Die (Persistent) Entity

Eine normale UML-Klasse wird zu einer (Persistent) Entity, indem der Modellierer diese mit Hilfe des Stereotyps "jpaPersistentEntity" als solche charakterisiert. Jede Persistent Entity benötigt einen Primärschlüssel, der durch das Anhängen des Stereotyps jpaPrimaryKey an ein Attribut oder eine Methode (field oder property access, siehe auch Kapitel über field/property access-Umschaltung) festgelegt wird (siehe Figure 12-3).

Figure 12-3. Persistent Entity mit den Stereotypen "jpaPersistentEntity" und "jpaPrimaryKey"

GeneSEZ erzeugt aus dieser Klasse folgenden Quellcode (ohne die automatisch erzeugten getter und setter-Methoden):


			@Entity
			@Table(name = "tbl_Bank")
			public class Bank implements Serializable {
			
				@Id
				@GeneratedValue(strategy = GenerationType.AUTO)
				private int sortCode;
				
				private String name;
				
				@Version
				private int version;
				
				public Bank {
				}
				
				[...]		
						
			}	
		

Die Generierung der Annotationen @Entity sowie @Id lassen sich durch die beiden verwendeten Stereotypen erklären. Woher kommen aber die anderen Stereotypen, das Attribut version, der Standardkonstruktor und das Interface Serializable?

Die Antwort lautet automatische Quellcode-Ergänzung. Gehen wir die verschiedenen Punkte der Reihe nach durch:

Bei dieser Klasse gibt es bezüglich des Primärschlüssels zwei notwendige Anmerkungen. Da mit der Bankleitzahl (sortCode) nicht gerechnet werden soll, ist die Wahl des Datentyps String hier dem int vorzuziehen. Aus Performanzgründen empfiehlt die JPA-Spezifikation aber auf Primärschlüssel mit dem Datentyp String zu verzichten. Hinzu kommt noch, dass die Vermischung von fachlichen und technischen Merkmalen nicht besonders guter Programmierstil ist. Aus diesem Grund wird dem Attribut sortCode mit Hilfe des Stereotyps jpaColumn eine Unique-Beschränkung verpasst (fachlicher Primärschlüssel) und als technischer Primärschlüssel wird das Attribut id mit dem Datentyp int hinzugefügt. Für das nächste Beispiel (siehe Figure 12-4 und ) wird noch ein Attribut mit dem Namen index hinzugefügt, welches den Platz der Bank in einem fiktiven Bewertungsindex repräsentiert.

Figure 12-4. Persistent Entity mit unique-Attribut und ohne jpaPrimaryKey

GeneSEZ erzeugt aus dieser Klasse folgenden Quellcode (ohne die automatisch erzeugten getter und setter-Methoden):


			@Entity
			@Table(name = "tbl_Bank")
			public class Bank implements Serializable {
			
				@Id
				@GeneratedValue(strategy = GenerationType.AUTO)
				private int id;
				
				@Column(name = "sortCode", unique=true, nullable=false)
				private String sortCode;
				
				private String name;
				
				@Column(name = "bank_index")
				private String index;
				
				@Version
				private int version;
				
				public Bank {
				}
				
				[...]
								
			}	
		

Auch in diesem Beispiel war die automatische Quellcode-Ergänzung wieder am Werke. Wir schauen uns die Punkte genauer an:

Figure 12-5. Persistent Entity ohne technischen Primärschlüssel

Ein Ziel der Java Plattform-Erweiterung JPA ist das Modell möglichst frei von technologiespezifischen Elementen zu halten. Dies wird nicht immer gelingen, aber bei der Persistent Entity lässt sich noch etwas verbessern. Der technische Primärschlüssel ist ein technologiespezifisches Element und hält man sich an die Trennung von fachlichen und technischen Merkmalen, dann läuft es in den meisten Klassen auf ein zusätzliches Attribut hinaus. Um das Modell von technologiespezifischen Elementen freizuhalten und den Arbeitsaufwand des Modellierers zu verringern, sorgt die automatische Quellcode-Ergänzung dafür, dass jede Persistent Entity einen technischer Primärschlüssel bekommt (Name: id, Datentyp: int), sofern der Modellierer kein anderes Attribut als Primärschlüssel definiert hat. Figure 12-5 zeigt die Klasse Bank ohne technischen Primärschlüssel. Am generierten Quellcode ändert sich gegenüber dem letzten Beispiel nichts.