Dienstag, 12. Februar 2013

K2.2.1 - Entwicklung im Team mit Apache Archiva, Maven, Git und Eclipse

Einleitung

In diesem Artikel werden wir zu aller erst Apache Archiva als zentralen Repository Management Server für ein Projekt konfigurieren, welches wir mit dem Magnolia CMS aufsetzen werden. Wir nutzen Git als Versionskontrollsystem und werden dafür auch ein zentrales Repository einrichten, ein s.g. Git bare repository.

Wir werden es uns nicht zu einfach machen und direkt ein Maven Projekt mit Untermodulen (Maven submodules) aufsetzen. Es gibt als Alternative noch die flache Projektstruktur, die ich persönlich nicht empfehle, da man für jedes Modul/Projekt ein eigenes Git Repository benötigen würde. Das kann dann etwas aufwendig werden in der Wartung und Verwaltung der Repositories. Ansonsten ist die flache Struktur nicht unbedingt schlechter, als die hierarchische. Man sollte sich die Vor- und Nachteile mal genauer ansehen, und dazu kann ich den Artikel von Torsten Horn empfehlen.

Außerdem zeige ich diverse Wege, wie man in Eclipse ein Maven Webapp Projekt auf einem Apache Tomcat deployen kann. Den Tomcat Server werden wir natürlich auch gemeinsam installieren und in Eclipse in der Servers View einrichten. Wir werden für das Deployment das Maven Cargo Plugin nutzen und dabei ist es übrigens egal, ob der Tomcat Server lokal oder entfernt (remote) läuft, da mit dem Plugin auf einen beliebigen Server deployed werden kann. Wir nutzen hier zwar Tomcat, aber das Plugin kann auch mit JBoss oder anderen Application Servern umgehen.

Am Ende dieses Artikels haben Sie dann ein Magnolia Webapp Projekt als Maven submodule in einem Maven parent Projekt unter Git Versionskontrolle. Mit den beiden zentralen Repository Servern für Maven und Git ist das eine solide Basis für die Entwicklung auch in einem größeren Team.

Motivation


Im Unternehmensumfeld macht es Sinn aus Gründen einer wartbaren und standardisierten Infrastuktur für die Softwareentwicklung einen zentralen Repository Server, sowohl für Maven als auch für Git aufzusetzen. Beide Technologien sind seit einiger Zeit dabei die etablierten Tools Apache Ant und Subversion abzulösen und das wohl zu recht. Aus eigener Erfahrung muss ich nach langjähriger Nutzung von SVN zugeben, dass Git als verteiltes Versionskontrollsystem einige Vorteile hat. Allerdings kenne ich keines der anderen Distributed Version Control Systems (DVCS), wie z.B. Mercurial. Wer etwas im Internet unterwegs ist und diverse Fachmagazine liest, der weiß, dass Git in diesen Medien eine enorme Präsenz hat und daher wohl einen größeren Bekanntheitsgrad genießt.

Auch Apache Maven kann einen ähnlichen Erfolg vorweisen. Der Umstieg von Ant auf Maven ist zwar etwas aufwendig, da die Workflows und die Projektstruktur komplett unterschiedlich sind, aber wer in die Zukunft investieren möchte, sollte die Migration auf jeden Fall angehen. Die Ant Experten und auch die SVN Gurus werden über die nächsten Jahre weniger werden, so dass Unternehmen es schwer haben werden fähiges Personal für ihre Projekte zu finden, wenn diese auf veralteten Technologien basieren. Und andersherum erhöht man natürlich als Entwickler seinen eigenen Markwert, wenn man moderne Technologien beherrscht.

Apropos "moderne Technologie", wie bereits erwähnt werden wir als erstes Maven Projekt eine Java Web Applikation mit dem Magnolia CMS aufsetzen. Magnolia gehört zweifellos zu den modernsten Content Management Systemen im Java Umfeld. Leider ist in diesem Artikel kein Platz mehr für eine Einführung in Magnolia, wer aber Interesse hat kann im Anschluss mit der sehr guten Dokumentation weiter arbeiten und das Projekt ausbauen. Ich empfehle zuerst mit der Webapp und Modul Dokumentation anzufangen.

Have fun!

Voraussetzungen

So wie es die Kapitelnummer im Titel dieses Artikels vermuten lässt, sollte man den vorherigen Artikel K2.2 - Professionelle Entwicklung mit Git und Maven unter Eclipse und mit Apache Archiva durchgearbeitet haben, um alle notwendigen Installationen bereit zu haben, z.B. eine lokal laufende virtuelle Maschine mit VirtualBox, um die Server Repositories für Maven und Git möglichst praxisnah betreiben zu können. Vorallem aber wird von Apache Archiva eine Installation  aufgesetzt, die in diesem Tutorial weiter konfiguriert wird und auch Eclipse mit den notwendigen Plugins m2eclipse und EGit werden installiert.

Server-Side (Linux Debian)


Workstation PC (Windows 7)


Umsetzung

Kurzübersicht aller Schritte

  1. Apache Archiva konfigurieren (Magnolia Remote Repository hinzufügen) (~5min)
  2. In Eclipse ein Maven Basis Projekt erstellen (ein s.g. parent module einer multi-module Struktur) (~5min)
  3. Magnolia Webapp als Projekt erstellen (als s.g. Maven submodule im Basis Projekt) (~5min)
  4. Apache Tomcat in Eclipse integrieren (~10min)
  5. Magnolia Webapp Maven Projekt auf Tomcat deployen (~15min)
  6. Ein zentrales Git bare repository erstellen (~3min)
  7. In Eclipse unser Maven Projekt unter Git Versionskontrolle stellen (~5min)

1. Apache Archiva konfigurieren

Rufen Sie Apache Archiva im Browser auf und loggen Sie sich mit Ihrem Administrator Benutzer ein, z.B.

Klicken Sie auf Repositories und wenn Sie parallel Eclipse geöffnet haben, sollten Sie in der Eclipse View "Maven Repositories" unter Global Repositories das eingerichtete Archiva als "internal-blogger" sehen, wenn Sie den vorherigen Artikel durchgearbeitet habe:
Sie sehen, dass aktuell 2 remote repositories konfiguriert sind. Diese sind in Apache Archiva bereits vorkonfiguriert gewesen. Wir benötigen nun ein weiteres remote repository, worüber wir das Magnolia CMS beziehen können.
Klicken Sie dazu auf "Add" und füllen Sie die Felder mit folgenden Werden aus:
  • URL: http://nexus.magnolia-cms.com/content/repositories/magnolia.public.releases/
  • Sonstige Feldwerte sehen Sie im Screenshot
Speichern Sie das Repository mit "Add Repository":
Jetzt fehlt noch die Proxy Konfiguration damit das neue Repository auch verwendet werden kann. Klicken Sie dazu auf "Proxy Connectors" und anschließend direkt auf "Add":

Sie haben nun das Magnolia Repository hinzugefügt und können nun in einem Maven Projekt Magnolia dependencies benutzen, die von diesem Repository heruntergeladen werden.

2. Maven multi-module Projekt erstellen

Starten Sie Eclipse und klicken Sie auf "File" -> "New" -> "Other":
Achten Sie darauf, dass Sie als Packaging Typ "pom" ausgewählt haben. Dies macht ein Maven Projekt zu einem Basis Projekt einer Maven multi-module Projektstruktur.


3. Maven submodule als Projekt erstellen

Ein parent Projekt hat die Aufgabe mehrere Unterprojekte zu verwalten, d.h. man kann Maven Goals auf das parent Projekt ausführen und es wird auch auf alle Unterprojekte ausgeführt.

Um ein submodule zu erstellen sind nur 3 Dinge notwendig:
  1. Ein Unterverzeichnis im parent Projekt als Modulverzeichnis
  2. Ein <module> Eintrag in der parent pom.xml
  3. Eine eigene pom.xml im neuen Unterprojekt/Modulverzeichnis
In folgendem Screenshot sehen Sie das Ergebnis nach 1. und 2.
Jedes Maven Projekt hat eine eigene pom.xml Datei. Für das neue Unterprojekt wollen wir Magnolia als Webapp Projekt einrichten. Dazu starten wir mit folgender pom.xml (3.):
Wir können nun das Untermodul als separates Eclipse Projekt importieren. Dies ändert nichts an der Verzeichnisstruktur, lediglich in Eclipse wird sich die Anzeige anpassen.
Klicken Sie auf "File" -> "Import...":
Anschließend wählen Sie das Maven submodule aus. Der Eclipse Wizard wird es erkennen, da im Modulverzeichnis eine pom.xml existiert:

Nun sehen Sie zwei Projekte in Eclipse, das Maven submodule ist als eigenständiges Projekt importiert worden. Das Dateisystem hat sich aber nicht verändert.

Als nächstes können Sie einfach mal das Projekt bauen und zwar mit dem Maven Goal "install". Gehen Sie dazu per Rechtsklick auf das Projekt auf Run As und anschließend auf Maven install:
Es wird ein WAR Archiv im target Verzeichnis erzeugt. Dies können Sie nun auf einem Tomcat Server deployen.
Für alle die an dieser Stelle keinen Tomcat Server zur Verfügung haben, wir werden direkt im Anschluss einen lokalen Tomcat installieren und in Eclipse integrieren, sodass Tomcat direkt aus Eclipse heraus gestartet und gestoppt werden kann.

4. Apache Tomcat in Eclipse integrieren

Wir benötigen zur Integration in Eclipse die Web Tools Platform (WTP), die wir über Help -> Install New Software installieren können:
Nach der erfolgreichen Installation hat man die Servers View in Eclipse zur Verfügung.

Laden Sie nun ein Tomcat Binary zip Paket herunter und entpacken Sie es in ein Verzeichnis Ihrer Wahl. Das Ergebnis sollte ungefähr so aussehen:
Jetzt ist es an der Zeit die Eclipse Servers View anzuzeigen. Gehen Sie zu Window -> Show View -> Other und wählen Sie Servers aus:
Anschließend sehen Sie das Servers Window:
Klicken Sie in diesem Fenster auf den Link "new server wizard" und wählen Sie unter Apache den Tomcat Eintrag mit der passenden Version aus:
Klicken Sie auf Next und wählen Sie Ihr Tomcat Verzeichnis aus:
Im nächsten Schritt bietet Eclipse Ihnen an sofort ein Projekt dem Server hinzuzufügen. Falls Sie bis hierher das Tutorial durchgearbeitet haben, dann wird hier nichts zur Auswahl stehen:
Wir werden auch später diese Hot-Deployment Möglichkeit nicht nutzen, sondern unser Webapp Projekt über das Maven Cargo Plugin per "Knopfdruck" deployen. Das ist zwar kein hot-deploy, aber ich persönlich finde es auch gar nicht schlecht, wenn man zuerst mehrere Dateien bearbeiten kann bevor das Projekt veröffentlicht (deployt? deployed?) wird.
Nach einem Klick auf Finish sollte unser Tomcat in der Servers View integriert sein:
Starten Sie den Tomcat Server nun per Rechtsklick auf den Server und dann auf Start:
Unser Tomcat Server ist nun gestartet, allerdings wird die Tomcat Administrationsoberfläche noch nicht aufrufbar sein:
Stoppen Sie den Server und machen dann einen Doppelklick auf den Tomcat Server Eintrag. Eclipse öffnet anschließend die Konfigurationsübersicht. Wählen Sie unter Server Locations den Radio Button "Use Tomcat installation" aus:
Danach nutzt unser Tomcat das webapps Verzeichnis im lokalen Dateisystem:
Hier landen alle veröffentlichten (deployten?) Webapp Projekte. Bevor wir aber den Server erneut starten müssen wir noch einen Benutzer anlegen. Öffnen Sie mit einem Texteditor folgende tomcat-users.xml Datei:
Konfigurieren Sie einen Benutzer mit Passwort und den folgenden Rollen:
<role rolename="manager-gui"/>
<role rolename="manager-script"/>
<user password="tomcat" roles="manager-gui,manager-script" username="tomcat"/>


Speichern Sie die Datei und starten den Tomcat Server erneut.

Rufen Sie nochmal die Tomcat URL im Browser auf, diesmal sollte ein HTTP Basic Auth Fenster öffnen. Geben Sie Ihre gerade angelegten Benutzerdaten ein:
Anschließend sollte nun die Tomcat Administrationsoberfläche angezeigt werden:
Wir nutzen nun die Gelegenheit, um unser WAR Projekt, welches wir am Ende von Schritt 3 erzeugt haben, auf diesem Tomcat Server zu veröffentlichen. Dieser manuelle Weg dient in erster Linie nur zum Testen von WAR Dateien, während der Entwicklung ist das natürlich ein zu aufwändiger Weg.

Klicken Sie unter "WAR file to deploy" auf den Button "Datei auswählen". Im anschließend geöffneten Dialog wählen Sie die WAR Datei aus dem Projektverzeichnis (rechts):
Klicken Sie im Anschluss auf den Button "Deploy". Sie sollten dann die Webapp in der Liste "Applications" sehen:
Die Webapp sollte gestartet sein und wenn Sie auf den Path Link klicken, wird sich in unserem Fall die Magnolia Installation öffnen, da es der erste Aufruf ist:
Sie sollten nun auch im Tomcat webapps Verzeichnis diese Applikation sehen:
Nach diesem ersten Teilerfolg, werden wir jetzt Maven nutzen, um das Projekt auf unserem Tomcat zu veröffentlichen.

5. Webapp mit Maven auf Server veröffentlichen

Wir benötigen das Maven Cargo Plugin, dazu müssen wir lediglich die pom.xml Datei unseres Webapp Projekts erweitern:
Hier die pom.xml als Text zwecks Copy&Paste:
 
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
 <modelVersion>4.0.0</modelVersion>
 <groupId>de.blogspot.sw-technik</groupId>
 <artifactId>myMagnoliaCmsProject</artifactId>
 <version>4.5.7</version>
 <packaging>war</packaging>

 <properties>
  <magnolia.version>${project.version}</magnolia.version>
  <cargo.version>1.2.4</cargo.version>
 </properties>
 
 <build>
  <plugins>
   <plugin>
    <groupId>org.codehaus.cargo</groupId>
    <artifactId>cargo-maven2-plugin</artifactId>
    <version>${cargo.version}</version>
    <!-- Cargo Tomcat --> 
    <configuration>
     <container>
      <containerId>tomcat7x</containerId>
      <type>remote</type>
     </container>
     <configuration>
      <type>runtime</type>
      <properties>
       <!-- /text requires the tomcat-users.xml user/role config with manager-script -->
       <cargo.tomcat.manager.url>http://localhost:8080/manager/text</cargo.tomcat.manager.url>
       <cargo.remote.username>tomcat</cargo.remote.username>
       <cargo.remote.password>tomcat</cargo.remote.password>
      </properties>
     </configuration>
    </configuration>
    <dependencies>
     <dependency>
        <groupId>org.codehaus.cargo</groupId>
        <artifactId>cargo-core-container-tomcat</artifactId>
        <version>${cargo.version}</version>
     </dependency>
    </dependencies>
   </plugin>
  </plugins>
 </build>
 
 <dependencies>
  <dependency>
   <groupId>info.magnolia</groupId>
   <artifactId>magnolia-empty-webapp</artifactId>
   <version>${magnolia.version}</version>
   <type>war</type>
  </dependency>
 </dependencies>
</project>


Jetzt benötigen wir nur noch eine Run Konfiguration, um auch wirklich per "Knopfdruck" das Projekt veröffentlichen zu können.
Gehen Sie im Hauptmenü von Eclipse auf Run -> Run Configurations... und erstellen Sie eine neue Maven Build Konfiguration:
Klicken Sie nun auf Run und sehen Sie in der Console View, wie die Webapp gebaut und deployed wird.

6. Git bare repository erstellen

Ein Git bare repository ist ein spezielles Repository, welches üblicherweise auf einem zentralen Server eingerichtet wird. Ein Git bare repository kann man nicht als Working Copy nutzen, also nicht als Entwicklungsprojekt einrichten. Der Sinn eines bare repository ist, dass man ein zentrales Repository für alle Entwickler hat. Jeder Entwickler klont dieses bare repository und pusht die Änderungen wieder zurück. Somit hält das bare repository den aktuellen Projektstand und kann für Deployments verwendet werden.

In zentralen Versionskontrollsystemen wie Subversion ist der Workflow sehr ähnlich. Der Vorteil von verteilten Versionskontrollsystemen wie Git oder Mercurial ist, dass so ein zentrales Repository optional und sehr leicht einzurichten ist. Und das machen wir jetzt!

Melden Sie sich per SSH auf Ihrem Linux Server an und öffnen Sie die Kommandozeile. Installieren Sie erstmal Git:
apt-get install git

Nach erfolgreicher Installation geben Sie folgende Befehle ein:
mkdir /var/www/parentproject
cd /var/www/parentproject
git --bare init

Prüfen Sie, ob das Repository erstellt wurde. Es sollte folgende Struktur haben:
root@debianVM:/var/www/repository/parentproject# ls
branches  config  description  HEAD  hooks  info  objects  refs

Als Vorbereitung für die Nutzung von Gitweb müssen wir noch einen URL Alias in den VHost von Apache eintragen:
Alias /parentproject "/var/www/repository/parentproject"

Anschließend einfach noch folgende Befehle auf der Konsole nacheinander ausführen:
git update-server-info
cd hooks
mv post-update.sample post-update
/etc/init.d/apache2 restart

Somit ist auf der Server-Side alles für ein zentrales Git bare repository eingerichtet. Jetzt werden wir dieses parentproject Repositoryper Eclipse EGit klonen, um damit arbeiten zu können.

Klicken Sie in der Git Repositories View auf den Link "Clone a Git repository":
Füllen Sie die Felder mit den passenden Daten aus:
Sie sehen, dass das Repository noch keinen master Branch hat und dementsprechend auch noch keinen HEAD hat. Dies werden wir nun ändern.

7. Eclipse Projekt unter Git Versionskontrolle stellen

Wir fügen nun das Eclipse parentproject dem Git Repository parentproject hinzu und damit unter Versionskontrolle.
Gehen Sie folgendermaßen vor: Rechtsklick auf das Projekt -> Team -> Share Project...
Nach einem Klick auf Finish sollte das parentproject mit gelben Säulen markiert sein:
Nun machen wir unseren ersten Git commit. Klicken Sie wieder per Rechtsklick auf das Projekt -> Team -> Commit:
Sobald der Commit durchgeführt wurde können wir die Änderungen auch pushen, d.h. in unser zentrales Git bare repository einspielen.
Dazu gehen wir wie folgt vor: Rechtsklick Projekt -> Team -> Push to Upstream
Jetzt sehen wir auch, dass wir den master Branch "ausgecheckt" (checkout) haben. Das Häkchen markiert den aktuell ausgecheckten Branch.

Wir sollten nun der besseren Entwicklung wegen auch das Webapp Projekt unter Versionskontrolle stellen. Das machen wie wie zuvor mit dem parentproject:
Diesmal müssen wir keinen Commit mehr durchführen, da die Dateien des Webapp Projekts im parentproject Verzeichnis liegen und dies ist ja bereits versioniert.

Leider haben wir einen kleinen Fehler gemacht...

Das kommt hin und wieder auch mal vor, das sollte Sie nicht beunruhigen. Unser Fehler war, dass das target Verzeichnis unter Versionskontrolle von Git steht. Das target Verzeichnis enthält ausschließlich temporär generierte Dateien und Verzeichnisse und diese werden bei jedem Build geändert.

Als kleine Übung im Umgang mit Git überlasse ich die Behebung dieses Fehlers ihnen. Als Hinweis: Sie müssen das target Verzeichnis aus dem Git Index entfernen und anschließend per .gitignore Datei aus der Versionierung ausschließen.

Zusammenfassung

Herzlichen Glückwunsch an dieser Stelle, wenn Sie das Tutorial erfolgreich durchgearbeitet haben. Sie haben nun eine sehr gute Infrastruktur zur Entwicklung unter produktiven Bedingungen durch die Hilfe einer virtuellen Maschine für die Server-Side Installationen.

Sie haben mit Apache Archiva einen Repository Manager mit dem Sie zentral die notwendigen remote Repositories verwalten können und auch JAR Artefakte direkt hochladen können, z.B. wenn es in keinem öffentlichen remote Repository existiert.

Mit dem Maven Cargo Plugin können Sie nicht nur auf einem lokalen Tomcat (oder auch anderen Servern) Ihr Projekt auf einfache Weise veröffentlichen, sondern auch auf einem beliebigen entfernten Server. Sie müssen dazu lediglich die Server Daten in der pom.xml anpassen und natürlich sicherstellen, dass der Server auch entsprechend konfiguriert ist.

Und zu guter letzt haben wir mit Git sowohl auf Client Seite mit Eclipse und EGit, als auch auf der Server-Side mit einem Git bare repository eine solide Versionskontrolle aufgesetzt.

Diese Infrastruktur hat aus meiner Sicht in dieser Form nur einen einzigen Nachteil. Man hat noch kein Berechtigungssystem für die Git Repositories. Jeder der das Repository klonen kann hat auch alle Rechte auf dem Projekt. Das kann manchmal nicht gewünscht sein.

Weitere Schritte


Git hat von Haus aus keine Zugriffskontrolle. In einem Unternehmen kann es aber notwendig werden bestimmten Entwicklern, z.B. Freelancer, eingeschränkten Zugriff auf bestimmte Projekte zu geben. Für diesen Fall gibt es Gitolite oder noch besser Gerrit. Letzteres ist eigentlich kein reines ACL System für Git, sondern ein komplettes Review System. Allerdings bringt Gerrit ein ACL System von Haus aus mit und lässt sich über eine Web GUI auch recht nutzerfreundlich konfigurieren. Ich würde jedem sofort zu Gerrit statt Gitolite raten, auch wenn man erstmal kein Review System benötigt. Gerrit kann man auch an ein Active Directory anbinden, somit steht einer sauberen Integration in eine Enterprise Infrastruktur nichts mehr im Weg.


3 Kommentare:

  1. Hallo,

    RhodeCode ist eine wohl etwas einfachere Lösung zum Verwalten von Git und Mercurial Repos in Unternehmen. Es ist Open Source, kann auf eigenen Servern installiert werden und dedizierter Support ist zubuchbar.

    Und wer es ganz schnell und einfach haben will: ein gehosteter Dienst existiert auch, der einem einen dedizierten RhodeCode Enterprise Server in Deutschland gehostet zur Verfügung stellt.

    Schaut einfach mal hier: https://rhodecode.com

    Viele Grüße

    Sebastian Kreutzberger, CEO
    RhodeCode GmbH


    AntwortenLöschen
    Antworten
    1. Hallo,

      werde mich mal mit RhodeCode etwas näher beschäftigen, danke für den Hinweis.

      Es sieht auf jedenfall hübscher aus als Gerrit. Mal sehen, wie es mit der Integration, Administration und Benutzbarkeit aussieht.

      Löschen
  2. du hast mir sprachlos gemacht, das hilft sehr . danke

    AntwortenLöschen