In meinem letzen Blog ging es um Lizenzreports und Lizenzüberwachung von Fremdbibliotheken sowie Open Source mittels Gradle License Report. Dies funktioniert gut für alle betroffenen Teile des Codes. Aber es führte auch zu doppeltem Code und weniger Transparenz in der Konfiguration. Der Wunsch ist nun, diese spezifischen Umsetzungen für wenige Module zentral abzubilden. Wie dies sehr strukturiert und einfach in Gradle realisiert werden kann, möchte ich in diesem Blog kurz anhand von Convention-Plugins Konzept beschreiben.

Mein Beispiel orientiert sich wieder an dem Lizenz-Report. Allerdings ist der Report hier nur als Beispiel anzusehen. Daher werde ich fachlich nicht weiter auf das Lizenz-Plugin eingehen.

Was für die Softwareentwicklung generell gilt, gilt natürlich auch für die Nutzung von Plugins:

  • keine unerwünschte Code-Duplizierung
  • Gleichartigkeit von Konfigurationen für bestimmte Module, in Gradle Subprojects genannt, im Gradle-Buildprozess
  • fachlich zentrale Konfiguration zur besseren Wartbarkeit bei der eigentlichen Lizenzkontrolle

Dies soll in einem zu schreibenden Conventions-Plugin realisiert werden. Konkret soll das Plugin auf vier Subprojekte angewendet werden, die über 500 anderen Subprojekte benötigen die geforderte Funktionalität nicht.

The Gradle-way

Gradle bietet hierfür das Konzept der sogenannten Convention-Plugins an. Diese selbst zu schreibenden Plugins wirken auf alle Subprojekte, die dieses Plugin anwenden. Abweichungen von der Konvention sind gut zu erkennen und gehen nicht in Code-Duplizierungen unter, d.h. der Code wird schlanker und deutlich übersichtlicher.

Nun wurde im vorherigen Blog der Gradle License Report, ebenfalls ein Plugin, angesprochen und dessen gute Möglichkeiten aufgezeigt. D.h. die Aufgabe ist, das Lizenz-Plugin in ein Convention-Plugin zu integrieren und buildspezifische sowie fachliche Konfigurationen im Conventions-Plugin zu implementieren. D.h. das gewünschte Plugin wird zweckmäßig mit einem Convention-Plugin ummantelt und einmalig mit Standardwerten zentral konfiguriert.

Um es gleich einmal plakativ darzustellen:

Vorher, ohne Convention-Plugin

Vorher, ohne Convention-Plugin

nachher, mit Convention-Plugin

nachher, mit Convention-Plugin

Da diese Blöcke bei vier Subprojekten Anwendung finden, lässt sich erahnen, wie groß das Potential ist, Code einzusparen!

Die zentrale Konfiguration für das Convention-Plugin ist dagegen einmalig im Root-Project unter buildSrc abzulegen und sieht wie folgt aus:

LicenseConvention.groovy

LicenseConvention.groovy

Dazu gehört noch das Bekanntmachen des neuen Plugins über eine Property-Datei. Das war’s dann aber auch schon.

licenseConvention.properties

licenseConvention.properties

In diesem Fall wurde Groovy als Implementierungssprache für das Convention-Plugin verwendet. Natürlich lässt sich dies mit jeder von Gradle unterstützten Programmiersprache realisieren.

Fazit

Wie zu erkennen war, lassen sich beliebige Gradle-Plugins als Convention-Plugin abbilden und gewüschte Konfigurationen als Konvention zentral ablegen, s.d. eigentliche Unterschiede in z.B. Konfigurationen leichter erkennbar sind und Code-Duplizierungen in Subprojekten unnötig werden. Das lässt sich auf alle Gradle-Plugins anwenden, wie jib, asciidoc, OWASP Dependency Check u.a.. Wer sich also schon immer über solche Dubletten an Code für Gradle-Plugins geärgert hat, sollte einen Blick auf das Konzept der Convention-Plugins werfen. Einfach mal ausprobieren und den Code entschlacken.

Viel Spaß, Frank