Kako riješiti koliziju verzija u Mavenu
1. Pregled
Višemodulni Maven projekti mogu imati složene grafikone ovisnosti. To mogu imati neobične rezultate, što više moduli uvoze jedni od drugih.
U ovom uputstvu vidjet ćemo kako razriješiti verziju sudara artefakata u Mavenu.
Započet ćemo s projektom s više modula gdje smo namjerno koristili različite verzije istog artefakta. Zatim ćemo vidjeti kako spriječiti dobivanje pogrešne verzije artefakta s izuzećem ili upravljanjem ovisnošću.
Napokon ćemo pokušati koristiti maven-prisilnik-dodatak kako bi stvari bilo lakše kontrolirati, zabranom upotrebe prijelaznih ovisnosti.
2. Sukob inačica artefakata
Svaka ovisnost koju uključimo u naš projekt može se povezati s drugim artefaktima. Maven može automatski unijeti ove artefakte, koji se nazivaju i tranzitivne ovisnosti. Sukob verzije događa se kada se više ovisnosti povezuje na isti artefakt, ali koriste različite verzije.
Kao rezultat, u našim aplikacijama mogu postojati pogreške kako u fazi kompilacije tako i tijekom izvođenja.
2.1. Struktura projekta
Definirajmo strukturu projekta s više modula za eksperimentiranje. Naš projekt sastoji se od a verzija-sudar moduli za roditelje i troje djece:
verzija-sudar projekt-projekt-b projekt-sudar
The pom.xml za projekt-a i projekt-b su gotovo identični. Jedina je razlika u verziji com.google.guava artefakt o kojem ovise. Posebno, projekt-a koristi verziju 22.0:
com.google.guava guava 22.0
Ali, projekt-b koristi noviju verziju, 29,0-jre:
com.google.guava guava 29,0-jre
Treći modul, projekt-sudar, ovisi o druge dvije:
com.baeldung projekt-a 0.0.1-SNAPSHOT com.baeldung projekt-b 0.0.1-SNAPSHOT
Dakle, koja verzija guava bit će dostupan projekt-sudar?
2.2. Korištenje značajki iz verzije određene ovisnosti
Koju se ovisnost koristi možemo saznati stvaranjem jednostavnog testa u projekt-sudar modul koji koristi Futures.immediateVoidFuture metoda iz guava:
@Test javna void whenVersionCollisionDoesNotExist_thenShouldCompile () {assertThat (Futures.immediateVoidFuture (), notNullValue ()); }
Ova je metoda dostupna samo u 29,0-jre verzija. Naslijedili smo to iz jednog od ostalih modula, ali svoj kod možemo kompajlirati samo ako smo tranzitivnu ovisnost dobili iz projekt-b.
2.3. Pogreška pri kompilaciji uzrokovana kolizijom verzije
Ovisno o redoslijedu ovisnosti u projekt-sudar modul, u određenim kombinacijama Maven vraća pogrešku kompilacije:
[POGREŠKA] Nije uspjelo izvršiti cilj org.apache.maven.plugins: maven-compiler-plugin: 3.8.1: testCompile (default-testCompile) na projektnom sudaru projekta: Neuspjeh kompilacije [GREŠKA] / tutorials / maven-all / version -collision / project-collision / src / test / java / com / baeldung / version / collision / VersionCollisionUnitTest.java: [12,27] ne može pronaći simbol [POGREŠKA] simbol: metoda neposrednaVoidFuture () [GREŠKA] lokacija: klasa com. google.common.util.concurrent.Futures
To je rezultat sudara verzije com.google.guava artefakt. Prema zadanim postavkama, za ovisnosti na istoj razini u stablu ovisnosti, Maven bira prvu knjižnicu koju pronađe. U našem slučaju oboje com.google.guava ovisnosti su na istoj visini i odabire se starija verzija.
2.4. Koristeći dodatak za maven-dependency
The dodatak za maven-dependency je vrlo koristan alat za predstavljanje svih ovisnosti i njihovih verzija:
% mvn ovisnost: stablo -Dverbose [INFO] --- dodatak za ovisnost maven: 2.8: stablo (default-cli) @ project-collision --- [INFO] com.baeldung: project-collision: jar: 0.0.1 -SNAPSHOT [INFO] + - com.baeldung: project-a: jar: 0.0.1-SNAPSHOT: compile [INFO] | \ - com.google.guava: guava: jar: 22.0: compile [INFO] \ - com.baeldung: project-b: jar: 0.0.1-SNAPSHOT: compile [INFO] \ - (com.google.guava: guava : jar: 29.0-jre: compile - izostavljen zbog sukoba s 22.0)
The -Dverbozno zastava prikazuje sukobljene artefakte. Zapravo imamo com.google.guava ovisnost u dvije verzije: 22.0 i 29.0-jre. Ovo potonje bismo željeli koristiti u projekt-sudar modul.
3. Izuzimanje prijelazne ovisnosti iz artefakta
Jedan od načina za rješavanje sudara verzija je uklanjanje sukobljene prijelazne ovisnosti s određenih artefakata. U našem primjeru ne želimo imati com.google.guava knjižnica tranzitivno dodana iz projekt-a artefakt.
Stoga ga možemo isključiti u projekt-sudar pom:
com.baeldung projekt-a 0.0.1-SNAPSHOT com.google.guava guava com.baeldung projekt-b 0.0.1-SNAPSHOT
Sada, kad pokrenemo ovisnost: stablo naredbe, možemo vidjeti da je više nema:
% mvn ovisnost: stablo -Dverbose [INFO] --- dodatak za ovisnost maven: 2.8: stablo (default-cli) @ project-collision --- [INFO] com.baeldung: project-collision: jar: 0.0.1 -SNAPSHOT [INFO] \ - com.baeldung: project-b: jar: 0.0.1-SNAPSHOT: compile [INFO] \ - com.google.guava: guava: jar: 29.0-jre: compile
Kao rezultat, faza kompilacije završava bez greške i možemo koristiti klase i metode iz verzije 29,0-jre.
4. Korištenje ovisnostUpravljanje Odjeljak
Mavenova ovisnostUpravljanje odjeljak je a mehanizam za centraliziranje informacija o ovisnosti. Jedna od njegovih najkorisnijih značajki je upravljanje verzijama artefakata koji se koriste kao prijelazne ovisnosti.
Imajući to na umu, stvorimo a ovisnostUpravljanje konfiguracija u našem roditelju pom:
com.google.guava guava 29,0-jre
Kao rezultat toga, Maven će se pobrinuti za upotrebu verzije 29,0-jre od com.google.guava artefakt u svim podređenim modulima:
% mvn ovisnost: stablo -Dverbose [INFO] --- dodatak za ovisnost maven: 2.8: stablo (default-cli) @ project-collision --- [INFO] com.baeldung: project-collision: jar: 0.0.1 -SNAPSHOT [INFO] + - com.baeldung: project-a: jar: 0.0.1-SNAPSHOT: compile [INFO] | \ - com.google.guava: guava: jar: 29.0-jre: compile (verzija upravljana od 22.0) [INFO] \ - com.baeldung: project-b: jar: 0.0.1-SNAPSHOT: compile [INFO] \ - (com.google.guava: guava: jar: 29.0-jre: compile - verzija upravljana od 22.0; izostavljena za duplikat)
5. Spriječiti slučajne prijelazne ovisnosti
The maven-prisilnik-dodatak pruža mnoga ugrađena pravila koja pojednostaviti upravljanje projektom s više modula. Jedan od njih zabranjuje upotrebu klasa i metoda iz prijelaznih ovisnosti.
Izričita deklaracija ovisnosti uklanja mogućnost sudara verzije artefakata. Dodajmo i maven-prisilnik-dodatak s tim pravilom našem roditelju pom:
org.apache.maven.plugins maven-prisilnik-dodatak 3.0.0-M3 prisiliti-zabraniti-ovisnosti provesti
Kao posljedicu, sada moramo izričito proglasiti com.google.guava artefakt u našem projekt-sudar modul ako ga sami želimo koristiti. Moramo odrediti verziju koju ćemo koristiti ili postaviti ovisnostUpravljanje u roditelju pom.xml. To naš projekt čini više dokazima pogrešaka, ali zahtijeva da budemo eksplicitniji u svom pom.xml datoteke.
6. Zaključak
U ovom smo članku vidjeli kako riješiti koliziju verzije artefakata u Mavenu.
Prvo smo istražili primjer sudara verzije u projektu s više modula.
Zatim smo pokazali kako isključiti prijelazne ovisnosti u pom.xml. Pogledali smo kako kontrolirati verzije ovisnosti pomoću ovisnostUpravljanje odjeljak u roditelju pom.xml.
Napokon smo isprobali maven-prisilnik-dodatak zabraniti upotrebu prijelaznih ovisnosti kako bi se prisilio svaki modul da preuzme kontrolu nad sobom.
Kao i uvijek, kod prikazan u ovom članku dostupan je na GitHub-u.