Muss bei der Migration auf Java 9 + / Java 11 zu Modulen gewechselt werden?


80

Wir migrieren derzeit von Java 8 auf Java 11. Das Upgrade unserer Dienste war jedoch weniger schmerzhaft als erwartet. Wir mussten im Grunde nur die Versionsnummer in unserer build.gradleDatei ändern und die Dienste waren zufriedenstellend. Wir haben Bibliotheken sowie (Mikro-) Dienste aktualisiert, die diese Bibliotheken verwenden. Bis jetzt keine Probleme.

Gibt es eine Notwendigkeit , um tatsächlich zu Modulen wechseln? Dies würde meiner Meinung nach unnötige Kosten verursachen. Jeder Vorschlag oder weiteres Lesematerial ist willkommen.

Gibt es Konsequenzen, wenn Java 9+ Code ohne Einführung von Modulen verwendet wird? Kann es zB mit anderem Code inkompatibel werden?


10
Es ist das gleiche Risiko, dem Sie bereits in Java 8 ausgesetzt waren: in "Classpath Hell" zu landen.

4
Die sotms / # Zusammenfassung würde bis zu einem gewissen Grad antworten. Sie können überprüfen, ob Ihre Projektziele auf das Projekt Jigsaw ausgerichtet sind . Abgesehen davon ist es meiner Meinung nach auch eine Frage der Aktualität, die für Bibliotheken / Dienste von Bedeutung ist, die ihre Verbraucher unterstützen.
Naman

4
@Taschi Ich glaube nicht, dass die Hölle des Klassenpfads allein eine Modularität rechtfertigt, da der gesamte Code vor Java 9 dieses Problem hatte und wir in den meisten Fällen damit einverstanden waren (persönlich hatten wir nie ein Problem damit).
Younes EO

1
@Naman, der die Ziele des Projektpuzzles anspricht, ist in der Tat ein sehr gutes Argument.
Younes EO

8
@Younes El Ouarti, das Entfernen von "Classpath Hell" ist eines der beiden erklärten Ziele von Project Jigsaw. Wenn Sie denken, dass dies kein ausreichender Grund für den Umgang mit Puzzle ist, dann stimme ich Ihnen zu und vermeide Puzzle, wann immer ich kann.

Antworten:


130

Nein.

Es ist nicht erforderlich, zu Modulen zu wechseln.

Es war nie notwendig, auf Module umzusteigen.

Java 9 und spätere Versionen unterstützen traditionelle JAR-Dateien auf dem traditionellen Klassenpfad über das Konzept des unbenannten Moduls und werden dies wahrscheinlich bis zum Hitzetod des Universums tun.

Ob Sie mit der Verwendung von Modulen beginnen, liegt ganz bei Ihnen.

Wenn Sie ein großes Legacy-Projekt pflegen, das sich nicht sehr ändert, ist es wahrscheinlich nicht die Mühe wert.

Wenn Sie an einem großen Projekt arbeiten, dessen Wartung im Laufe der Jahre schwierig geworden ist, kann die Klarheit und Disziplin, die die Modularisierung mit sich bringt, von Vorteil sein, aber es kann auch viel Arbeit bedeuten. Überlegen Sie also sorgfältig, bevor Sie beginnen.

Wenn Sie ein neues Projekt starten, empfehle ich dringend, mit Modulen zu beginnen, wenn Sie können. Viele beliebte Bibliotheken wurden inzwischen zu Modulen aufgerüstet , sodass die Wahrscheinlichkeit groß ist, dass alle benötigten Abhängigkeiten bereits in modularer Form verfügbar sind.

Wenn Sie eine Bibliothek verwalten, empfehle ich dringend, sie zu einem Modul zu aktualisieren, wenn Sie dies noch nicht getan haben und wenn alle Abhängigkeiten Ihrer Bibliothek konvertiert wurden.

All dies bedeutet nicht, dass Sie beim Überholen von Java 8 nicht auf einige Stolpersteine ​​stoßen werden. Diejenigen, auf die Sie stoßen, haben jedoch wahrscheinlich nichts mit Modulen an sich zu tun . Die häufigsten Migrationsprobleme , dass wir davon gehört haben , seit wir veröffentlicht Java 9 im Jahr 2017 zu tun haben mit Änderungen an der Syntax der Versionszeichenfolge und zum Entfernen oder Kapselung von internen APIs ( zB , sun.misc.Base64Decoder) , für die Öffentlichkeit, unterstützt Ersatz haben seit Jahren verfügbar.


25

Ich kann Ihnen nur meine Organisationsmeinung zu diesem Thema mitteilen. Wir sind dabei , für jedes einzelne Projekt, an dem wir arbeiten, auf Module umzusteigen. Was wir bauen, sind im Grunde genommen Mikrodienste + einige Client-Bibliotheken. Für Mikrodienste hat der Übergang zu modulesirgendwie eine niedrigere Priorität: Der Code dort ist bereits irgendwie im Docker-Container isoliert, so dass das "Hinzufügen" von Modulen dort (für uns) nicht sehr wichtig erscheint. Diese Arbeit wird langsam aufgenommen, hat aber eine niedrige Priorität.

Auf der anderen Seite ist Client-Bibliotheken eine ganz andere Geschichte. Ich kann dir das Chaos nicht sagen, das wir manchmal haben. Ich werde einen Punkt erklären, den ich vorher gehasst habe jigsaw. Sie stellen Clients eine Schnittstelle zur Verfügung, die jeder verwenden kann. Automatisch interfaceist das public- der Welt ausgesetzt. Normalerweise habe ich dann einige package-privateKlassen, die nicht den Clients ausgesetzt sind, die diese Schnittstelle verwenden. Ich möchte nicht, dass Kunden das verwenden, es ist intern. Hört sich gut an? Falsch.

Das erste Problem ist, dass wenn diese package-privateKlassen wachsen und Sie mehr Klassen möchten, die einzige Möglichkeit, alles verborgen zu halten, darin besteht, Klassen im selben Paket zu erstellen :

  package abc:
        -- /* non-public */ Usage.java
        -- /* non-public */ HelperUsage.java
        -- /* non-public */ FactoryUsage.java
        ....

Wenn es wächst (in unseren Fällen), sind diese Pakete viel zu groß. Wechseln Sie zu einem separaten Paket, sagen Sie? Sicher, aber dann das HelperUsageund FactoryUsagewird es sein publicund wir haben versucht, das von Anfang an zu vermeiden.

Problem Nummer zwei: Jeder Benutzer / Aufrufer unserer Kunden kann denselben Paketnamen erstellen und diese versteckten Klassen erweitern. Es ist uns schon ein paar Mal passiert, lustige Zeiten.

moduleslöst dieses Problem auf schöne Weise: publicist nicht mehr wirklich public ; Ich kann friendüber exports toDirektive Zugang haben . Dies erleichtert unseren Code-Lebenszyklus und unsere Verwaltung erheblich. Und wir entkommen der Hölle des Klassenpfades. Natürlich maven/gradlekümmern wir uns hauptsächlich darum, aber wenn es ein Problem gibt, werden die Schmerzen sehr real sein. Es könnte auch viele andere Beispiele geben.

Der Übergang ist jedoch (noch) nicht einfach. Zunächst muss jeder im Team ausgerichtet werden. Zweitens gibt es Hürden. Die größten zwei, die ich noch sehe, sind: Wie trennt man jedes Modul, basierend auf was speziell? Ich habe noch keine definitive Antwort. Die zweite ist split-packages, oh die schöne "gleiche Klasse wird von verschiedenen Modulen exportiert". Wenn dies bei Ihren Bibliotheken der Fall ist, gibt es Möglichkeiten, dies zu verringern. aber wenn dies externe Bibliotheken sind ... nicht so einfach.

Wenn Sie auf jarAund jarB(separate Module) angewiesen sind , beide jedoch exportieren abc.def.Util, werden Sie überrascht sein. Es gibt jedoch Möglichkeiten, dies zu lösen. Irgendwie schmerzhaft, aber lösbar.

Insgesamt ist unser Code seit der Migration auf Module (und dies immer noch) viel sauberer geworden. Und wenn Ihr Unternehmen ein "Code-First" -Unternehmen ist, ist dies wichtig. Andererseits war ich an Unternehmen beteiligt, bei denen dies von leitenden Architekten als "zu teuer" und "kein wirklicher Vorteil" angesehen wurde.


4
Danke für die Anstiftungen! Was ich also bekomme, ist, dass die Modularisierung mit den dringend benötigten Zugriffsbeschränkungen einhergeht, die wir in früheren Versionen vermisst haben. Ich kann definitiv sehen, wie nützlich dies für Bibliotheken ist. Falls ein Dienst über REST / AMQP / etc. Kommuniziert wird. Dies ist wieder nicht so sehr ein Problem, oder eher gibt es keine Vorteile? Vielleicht können wir nicht willkürlich sagen, dass der gesamte Java 9+ Code modular sein sollte? Also sollten wir es als "Werkzeug" selbst betrachten? Trotzdem interessant.
Younes EO

Was Sie nützlich finden könnten, ist ein "Accessor" -API-Muster (beachten Sie jedoch, dass anstelle eines öffentlichen statischen Felds ein privates Feld mit Methoden bevorzugt wird, um Deadlocks beim Laden von Klassen zu vermeiden). Siehe hier: wiki.netbeans.org/…
Tomáš Myšík

Vielen Dank für Ihre Erfahrungen! Es wäre gut, wenn Sie mehr Details oder Links zu den von Ihnen erwähnten Problemen teilen würden, die schmerzhaft, aber immer noch lösbar sind.
Botismarius

3
"Problem Nummer zwei: Jeder Benutzer / Anrufer unserer Kunden kann denselben Paketnamen erstellen und diese versteckten Klassen erweitern." Lange vor Java 9 konnten Pakete versiegelt werden , um dies zu verhindern. (Ich denke, Module sind eine hervorragende Idee und ich verwende sie in allen meinen Projekten. Ich wollte nur darauf hinweisen, dass dieser spezielle Anwendungsfall sie nicht erfordert.)
VGR
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.