Maven2 doprowadza mnie do szału podczas fazy eksperymentowania / szybkiej i brudnej makiety.
Mam pom.xml
plik, który definiuje zależności dla frameworka aplikacji sieci web, którego chcę używać, i mogę szybko wygenerować projekty początkowe z tego pliku. Czasami jednak chcę połączyć się z biblioteką innej firmy, która nie ma jeszcze pom.xml
zdefiniowanego pliku, więc zamiast pom.xml
ręcznie utworzyć plik dla biblioteki innej firmy i zainstalować go i dodać zależność do mojej pom.xml
, chciałbym tylko powiedzieć Mavenowi: „Oprócz moich zdefiniowanych zależności, uwzględnij również wszystkie słoiki, które są w /lib
środku”.
Wydaje się, że to powinno być proste, ale jeśli tak, coś mi brakuje.
Wszelkie wskazówki dotyczące tego, jak to zrobić, są bardzo mile widziane. Krótko mówiąc, jeśli istnieje prosty sposób, aby wskazać maven na /lib
katalog i łatwo utworzyć pom.xml
z wszystkimi dołączonymi słojami zamapowanymi na jedną zależność, którą mógłbym następnie nazwać / zainstalować i połączyć za jednym zamachem.
Odpowiedzi:
Problemy popularnych podejść
Większość odpowiedzi, które znajdziesz w Internecie, sugeruje zainstalowanie zależności w lokalnym repozytorium lub określenie zakresu „systemowego” w
pom
i dystrybucję zależności ze źródłem projektu. Ale oba te rozwiązania są w rzeczywistości wadliwe.Dlaczego nie powinieneś stosować podejścia „Zainstaluj w lokalnym repozytorium”
Po zainstalowaniu zależności w lokalnym repozytorium pozostaje ona tam. Twój artefakt dystrybucji będzie działał dobrze, o ile będzie miał dostęp do tego repozytorium. Problem polega na tym, że w większości przypadków to repozytorium będzie znajdować się na twoim komputerze lokalnym, więc nie będzie sposobu na rozwiązanie tej zależności na żadnym innym komputerze. Wyraźne uzależnienie artefaktu od konkretnej maszyny nie jest sposobem na radzenie sobie z różnymi rzeczami. W przeciwnym razie ta zależność będzie musiała zostać zainstalowana lokalnie na każdej maszynie pracującej z tym projektem, co nie jest lepsze.
Dlaczego nie powinieneś stosować podejścia „Zakres systemu”
Słoje, na których polegasz przy zastosowaniu podejścia „Zakres systemu”, nie są instalowane w żadnym repozytorium ani dołączane do pakietów docelowych. Dlatego twój pakiet dystrybucyjny nie będzie w stanie rozwiązać tej zależności, gdy zostanie użyty. Wierzę, że był to powód, dla którego użycie zakresu systemowego nawet się przestało. W każdym razie nie chcesz polegać na przestarzałej funkcji.
Statyczne rozwiązanie repozytorium w projekcie
Po umieszczeniu tego w
pom
:dla każdego artefaktu o identyfikatorze grupy
x.y.z
Maven w poszukiwaniu artefaktów uwzględni następującą lokalizację w katalogu projektu:Aby rozwinąć więcej na ten temat, możesz przeczytać ten post na blogu .
Użyj Maven, aby zainstalować repozytorium projektu
Zamiast ręcznie tworzyć tę strukturę, zalecamy użycie wtyczki Maven do zainstalowania słoików jako artefaktów. Aby zainstalować artefakt w repozytorium w projekcie w
repo
folderze wykonaj:Jeśli wybierzesz to podejście, będziesz mógł uprościć deklarację repozytorium w
pom
:Skrypt pomocnika
Ponieważ wykonywanie komend instalacyjnych dla każdej biblioteki jest trochę denerwujące i zdecydowanie podatne na błędy, stworzyłem skrypt narzędziowy, który automatycznie instaluje wszystkie słoiki z
lib
folderu do repozytorium projektu, jednocześnie automatycznie tłumacząc wszystkie metadane (groupId, artefactId itp.) Z nazwy plików. Skrypt wypisuje również xml zależności, które możesz skopiować i wkleić w swoim plikupom
.Uwzględnij zależności w pakiecie docelowym
Po utworzeniu repozytorium wewnątrz projektu rozwiązałeś problem dystrybucji zależności projektu z jego źródłem, ale od tego czasu artefakt docelowy projektu będzie zależał od niepublikowanych słoików, więc kiedy będziesz instalował to do repozytorium będzie miało nierozwiązywalne zależności.
Aby rozwiązać ten problem, sugeruję włączenie tych zależności do pakietu docelowego. Można to zrobić za pomocą wtyczki asemblera lub lepiej za pomocą wtyczki OneJar . Oficjalna dokumentacja OneJar jest łatwa do zrozumienia.
źródło
Tylko do wyrzucenia kodu
ustaw zakres == system i po prostu utwórz identyfikator grupy, identyfikator artefaktu i wersję
Uwaga: zależności systemowe nie są kopiowane do wynikowego pliku jar / war
(zobacz Jak uwzględnić zależności systemowe w wojnie zbudowanej przy użyciu maven )
źródło
system
lunety jest okropną praktyką, która jest zdecydowanie odradzana . Zobacz Zależność + zakresy .Możesz utworzyć lokalne repozytorium w swoim projekcie
Na przykład, jeśli masz
libs
folder w strukturze projektuW
libs
folderze należy utworzyć strukturę katalogów, taką jak:/groupId/artifactId/version/artifactId-version.jar
W swoim pom.xml powinieneś zarejestrować repozytorium
i dodaj zależność jak zwykle
To wszystko.
Aby uzyskać szczegółowe informacje: Jak dodać biblioteki zewnętrzne w Maven
źródło
Uwaga: Podczas korzystania z zakresu Systemu ( jak wspomniano na tej stronie ), Maven potrzebuje ścieżek bezwzględnych.
Jeśli słoiki znajdują się w katalogu głównym projektu, warto poprzedzić wartości systemPath wartością $ {basedir}.
źródło
To właśnie zrobiłem, działa również w przypadku problemu z pakietem i działa z wypisanym kodem.
Utworzyłem nowy folder w projekcie w moim przypadku, którego użyłem
repo
, ale możesz go używaćsrc/repo
W mojej POM miałem zależność, której nie ma w publicznych repozytoriach maven
Następnie utworzyłem następujące katalogi
repo/com/dovetail/zoslog4j/1.0.1
i skopiowałem plik JAR do tego folderu.Utworzyłem następujący plik POM, który reprezentuje pobrany plik (ten krok jest opcjonalny, ale usuwa OSTRZEŻENIE) i pomaga następnemu facetowi dowiedzieć się, skąd mam ten plik na początek.
Dwa opcjonalne pliki, które tworzę, to sumy kontrolne SHA1 dla POM i JAR, aby usunąć brakujące ostrzeżenia o sumach kontrolnych.
Na koniec dodaję następujący fragment do mojego pom.xml, który pozwala mi odwoływać się do lokalnego repozytorium
źródło
Naprawdę powinieneś wdrożyć platformę poprzez repozytorium i z góry zidentyfikować swoje zależności. Korzystanie z zakresu systemowego jest częstym błędem, z którego korzystają ludzie, ponieważ „nie dbają o zarządzanie zależnościami”. Problem polega na tym, że robiąc to, otrzymujesz zboczoną kompozycję maven, która nie pokaże maven w normalnych warunkach. Użytkownik będzie lepiej następujące podejście jak ten .
źródło
W ten sposób dodajemy lub instalujemy lokalny słoik
Dałem trochę domyślnego groupId i artefactId, ponieważ są one obowiązkowe :)
źródło
Wtyczka instalacyjna Maven ma użycie wiersza polecenia do zainstalowania słoika w lokalnym repozytorium, POM jest opcjonalny, ale będziesz musiał określić GroupId, ArtifactId, Version i Packaging (wszystkie rzeczy POM).
źródło
Używanie
<scope>system</scope>
jest okropnym pomysłem z powodów wyjaśnionych przez innych, ręczne zainstalowanie pliku w lokalnym repozytorium powoduje, że kompilacja jest niemożliwa do odtworzenia, a używanie<url>file://${project.basedir}/repo</url>
nie jest dobrym pomysłem, ponieważ (1) może nie być dobrze sformułowanymfile
adresem URL (np. Jeśli projekt jest wyewidencjonowany w katalogu z nietypowymi znakami), (2) wynik jest bezużyteczny, jeśli POM tego projektu jest używany jako zależność od projektu innego użytkownika.Zakładając, że nie chcesz wgrać artefaktu do publicznego repozytorium, sugestia Simeona dotycząca modułu pomocniczego spełnia swoje zadanie. Ale jest teraz łatwiejszy sposób…
Zalecenie
Użyj wtyczki innej niż maven-jar-maven-plug-in . Robi dokładnie to, o co prosiłeś, bez żadnych wad innych podejść.
źródło
Znalazłem inny sposób, aby to zrobić, patrz tutaj z postu Heroku
Podsumowując (przepraszamy za kopiowanie i wklejanie)
repo
katalog w folderze głównym:pom.xml
:źródło
Po bardzo długiej dyskusji z chłopakami z CloudBees na temat właściwego pakowania takich plików JAR, zaproponowali interesującą dobrą propozycję rozwiązania:
Stworzenie fałszywego projektu Maven, który dołącza istniejący plik JAR jako główny artefakt, działający w ramach należącej do niego instalacji POM: wykonanie pliku instalacyjnego. Oto przykład takiego kinfa POM:
Ale w celu jego wdrożenia należy zmienić istniejącą strukturę projektu. Po pierwsze, należy pamiętać, że dla każdego takiego rodzaju JAR należy utworzyć inny fałszywy projekt (moduł) Maven. I powinien zostać utworzony nadrzędny projekt Maven zawierający wszystkie podmoduły, które są: wszystkie opakowania JAR i istniejący projekt główny. Struktura może być:
Gdy rodzic działa za pośrednictwem mvn: install lub mvn: pakowanie jest wymuszone, a podmoduły zostaną wykonane. Może to być traktowane jako minus, ponieważ struktura projektu powinna zostać zmieniona, ale na końcu oferuje rozwiązanie niestatyczne
źródło
To, co wydaje mi się najprostsze, to po prostu skonfiguruj wtyczkę kompilatora maven, aby zawierała niestandardowe słoiki. W tym przykładzie załadowane zostaną wszystkie pliki jar w katalogu lib.
źródło
says nothing to complile
!all classes are up to date
nothing to compile
ponieważ nie będzie już szukał*.java
. Możesz je dodać ponownie za pomocą<include>**/*.java</include>
. Jednak nie ma dla mnie sukcesu dla słoikówProblem
systemPath
polega na tym, że słoiki zależności nie będą rozprowadzane wzdłuż twoich artefaktów jako zależności przechodnie. Spróbuj tego, co tu napisałem: czy najlepiej jest zdenerwować pliki jar projektu lub umieścić je w WEB-INF / lib?Następnie zadeklaruj zależności jak zwykle.
I proszę przeczytać notatkę w stopce.
źródło
Dziwne rozwiązanie, które znalazłem:
za pomocą Eclipse
na zdrowie, Balint
źródło
Jeśli chcesz szybkiego i brudnego rozwiązania, możesz wykonać następujące czynności (chociaż nie polecam tego do niczego poza projektami testowymi, maven narzeka, że nie jest to właściwe).
Dodaj pozycję zależności dla każdego potrzebnego pliku jar, najlepiej za pomocą skryptu perla lub czegoś podobnego i skopiuj / wklej to do pliku pom.
źródło
Szybkie i zabrudzony rozwiązanie partii (na podstawie odpowiedzi Alexa):
libs.bat
Wykonać to tak:
libs.bat > libs.txt
. Następnie otwórzlibs.txt
i skopiuj jego zawartość jako zależności.W moim przypadku potrzebowałem tylko bibliotek do skompilowania mojego kodu i to rozwiązanie było najlepsze do tego celu.
źródło
Chociaż nie pasuje to do twojego problemu, upuszczę to tutaj. Moje wymagania to:
Porozmawiajmy najpierw o (3): Samo umieszczenie słoików w folderze i jakoś scalenie ich w końcowy słoik nie będzie tutaj działać, ponieważ IDE tego nie zrozumie. Oznacza to, że wszystkie biblioteki muszą być poprawnie zainstalowane. Nie chcę jednak, aby wszyscy instalowali go za pomocą „pliku instalacyjnego mvn”.
W moim projekcie potrzebowałem metawidget. No to ruszamy:
Za każdym razem, gdy masz nową bibliotekę, po prostu dodaj nowe wykonanie i powiedz wszystkim, aby ponownie zbudowali projekt (możesz ulepszyć ten proces za pomocą hierarchii projektu).
źródło
Aby zainstalować słoik innej firmy, który nie znajduje się w repozytorium maven, użyj wtyczki maven-install-plugin.
Poniżej znajdują się kroki:
Poniżej znajduje się np. Ten, którego użyłem dla simonsite log4j
W pliku pom.xml uwzględnij zależność jak poniżej
Uruchom polecenie mvn clean install, aby utworzyć opakowanie
Poniżej znajduje się link referencyjny:
https://maven.apache.org/guides/mini/guide-3rd-party-jars-local.html
źródło
Dla tych, którzy nie znaleźli tutaj dobrej odpowiedzi, robimy to, aby uzyskać słoik ze wszystkimi niezbędnymi zależnościami. Ta odpowiedź ( https://stackoverflow.com/a/7623805/1084306 ) wspomina o użyciu wtyczki Maven Assembly, ale tak naprawdę nie podaje przykładu w odpowiedzi. A jeśli nie przeczytasz do końca odpowiedzi (jest dość długa), możesz ją przegapić. Dodanie poniżej do pliku pom.xml wygeneruje
target/${PROJECT_NAME}-${VERSION}-jar-with-dependencies.jar
źródło
Nawiązałem do jakiegoś kodu python w komentarzu do odpowiedzi @alex Lehmann, więc zamieszczam go tutaj.
źródło
To nie wyjaśnia, jak dodać je do POM, i może nie jest to kłopotliwe, ale po prostu doda lib katalog do twojej ścieżki klas? Wiem, że to właśnie robię, gdy potrzebuję zewnętrznego słoika, którego nie chcę dodawać do moich repozytoriów Maven.
Mam nadzieję że to pomoże.
źródło
W naszym projekcie działa Archimedes Trajano, ale w pliku .m2 / settings.xml mieliśmy coś takiego:
i * należy zmienić na centralny. Więc jeśli jego odpowiedź nie zadziała, powinieneś sprawdzić plik settings.xml
źródło
Chciałem tylko szybkiego i brudnego obejścia ... Nie mogłem uruchomić skryptu z Nikity Volkov: błąd składni + wymaga ścisłego formatu nazw jarów.
Zrobiłem ten skrypt Perla, który działa z dowolnym formatem dla nazw plików jar, i generuje zależności w pliku xml, dzięki czemu można go skopiować wkleić bezpośrednio w pom.
Jeśli chcesz go używać, upewnij się, że rozumiesz, co skrypt robi, być może trzeba zmienić
lib
folder i wartość dlagroupId
lubartifactId
...źródło
Rozwiązanie dla zakresu = podejście systemowe w Javie:
źródło