Xây dựng một hũ chất béo bằng maven


118

Tôi có một cơ sở mã mà tôi muốn phân phối dưới dạng jar. Nó cũng có sự phụ thuộc vào các lọ bên ngoài, mà tôi muốn gói trong lọ cuối cùng.

Tôi nghe nói rằng điều này có thể được thực hiện bằng cách sử dụng maven-assembly-plug-in, nhưng tôi không hiểu làm thế nào. Ai đó có thể chỉ cho tôi một số ví dụ.

Hiện giờ, tôi đang sử dụng lọ mỡ để bó lọ cuối cùng. Tôi muốn đạt được điều tương tự bằng cách sử dụng maven.

Câu trả lời:


143

Lưu ý: Nếu bạn là ứng dụng khởi động vào mùa xuân, hãy đọc phần cuối của câu trả lời

Thêm plugin sau vào của bạn pom.xml Có thể tìm thấy phiên bản mới nhất tại

...
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-assembly-plugin</artifactId>
            <version>CHOOSE LATEST VERSION HERE</version>
            <configuration>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
            <executions>
                <execution>
                    <id>assemble-all</id>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>
...

Sau khi định cấu hình trình cắm thêm này, việc chạy mvn packagesẽ tạo ra hai lọ: một lọ chỉ chứa các lớp dự án và một lọ béo thứ hai chứa tất cả các phụ thuộc với hậu tố "-jar-with-dependencies".

nếu bạn muốn classpaththiết lập chính xác trong thời gian chạy thì hãy thêm plugin sau

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <configuration>
        <archive>
            <manifest>
                <addClasspath>true</addClasspath>
                <mainClass>fully.qualified.MainClass</mainClass>
            </manifest>
        </archive>
    </configuration>
</plugin>

Đối với ứng dụng khởi động mùa xuân, chỉ sử dụng plugin sau (chọn phiên bản thích hợp của nó)

<plugin>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-maven-plugin</artifactId>
    <configuration>
        <fork>true</fork>
        <mainClass>${start-class}</mainClass>
    </configuration>
    <executions>
        <execution>
            <goals>
                <goal>repackage</goal>
            </goals>
        </execution>
    </executions>
</plugin>

1
Phiên bản hiện tại của plugin này hiện là 2.4
touristda

13
Tính năng này hiện không được dùng nữa và nên sử dụng plugin maven-shadow-thay thế. Xem câu trả lời của @phlogratos: stackoverflow.com/a/16222965/274350 .
Richard Neish

2
Maven-assembly-plugin có thể giảm thiểu kích thước của fat jar không?
May12

1
@Richard Nơi nào bạn thấy nó không được dùng nữa? Tôi không thể tìm thấy bất cứ thứ gì xung quanh đây maven.apache.org/plugins/maven-assembly-plugin
user3833308 Ngày

3
@ user3833308 "không được dùng nữa" có thể là từ sai, nhưng tài liệu tại maven.apache.org/plugins/maven-assembly-plugin cho biết "Nếu dự án của bạn muốn đóng gói cấu phần của bạn trong uber-jar, thì plugin lắp ráp chỉ cung cấp cơ bản hỗ trợ. Để kiểm soát nhiều hơn, hãy sử dụng Plugin Maven Shade. "
Richard Neish

55

Bạn có thể sử dụng maven-shadow-plugin .

Sau khi định cấu hình plugin bóng râm trong bản dựng của bạn, lệnh mvn packagesẽ tạo một jar duy nhất với tất cả các phụ thuộc được hợp nhất vào nó.


9
Đây là cách chính xác để làm điều đó. Tài liệu maven-assembly-plugin nêu rõ: "Nếu dự án của bạn muốn gói phần mềm của bạn trong uber-jar, thì plugin lắp ráp chỉ cung cấp hỗ trợ cơ bản. Để kiểm soát nhiều hơn, hãy sử dụng Plugin Maven Shade."
Richard Neish

Nhưng làm cách nào để lấy .jar đơn đó và sử dụng nó để xuất bản?
DanGordon

42

Có thể bạn muốn maven-shade-plugin, gói phần phụ thuộc, giảm thiểu mã không sử dụng và ẩn phần phụ thuộc bên ngoài để tránh xung đột.

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>3.1.1</version>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                    <configuration>
                        <minimizeJar>true</minimizeJar>
                        <createDependencyReducedPom>true</createDependencyReducedPom>
                        <dependencyReducedPomLocation>
                            ${java.io.tmpdir}/dependency-reduced-pom.xml
                        </dependencyReducedPomLocation>
                        <relocations>
                            <relocation>
                                <pattern>com.acme.coyote</pattern>
                                <shadedPattern>hidden.coyote</shadedPattern>
                            </relocation>
                        </relocations>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

Người giới thiệu:


Nếu một người gặp phải Provider org.apache.xerces.jaxp.SAXParserFactoryImpl not found, chỉ cần loại bỏ <minimizeJar>true</minimizeJar>.
koppor

Nếu bạn nhận được ngoại lệ "java.lang.SecurityException: Thông báo tệp chữ ký không hợp lệ cho các thuộc tính chính của Tệp kê khai", thì việc bổ sung này vào phần cấu hình ở trên sẽ giúp: stackoverflow.com/a/6743609/38368
Danny Varod

12

trên thực tế, thêm

<archive>
   <manifest>
    <addClasspath>true</addClasspath>
    <packageName>com.some.pkg</packageName>                     
    <mainClass>com.MainClass</mainClass>
  </manifest>
</archive>

khai báo cho maven-jar-plugin không thêm mục nhập lớp chính vào tệp kê khai cho tôi. Tôi đã phải thêm nó vào maven-assembly-plugin để có được điều đó trong tệp kê khai


5

Bạn có thể sử dụng plugin onejar-maven để đóng gói. Về cơ bản, nó tập hợp dự án của bạn và các phụ thuộc của nó trong một jar, không chỉ bao gồm tệp jar dự án của bạn, mà còn tất cả các phụ thuộc bên ngoài dưới dạng "jar of jar", ví dụ:

<build>
    <plugins>
        <plugin>
            <groupId>com.jolira</groupId>
            <artifactId>onejar-maven-plugin</artifactId>
                <version>1.4.4</version>
                <executions>
                    <execution>
                        <goals>
                            <goal>one-jar</goal>
                        </goals>
                    </execution>
                </executions>
        </plugin>
    </plugins>
</build>

Lưu ý 1: Các tùy chọn cấu hình có sẵn tại trang chủ của dự án .

Lưu ý 2: Vì lý do này hay lý do khác, dự án onejar-maven-plugin không được xuất bản tại Maven Central. Tuy nhiên, jolira.com theo dõi dự án ban đầu và xuất bản nó với groupId com.jolira.


Có thể chọn các phụ thuộc mà bạn muốn đóng gói không? Ví dụ: nếu a.jar và b.jar là các bình bên ngoài và tôi muốn chỉ gói a.jar vào trong bình cuối cùng, thì nó có thể / cấu hình được không?
bianca

Tôi cũng thấy những thứ một lọ cũng được đóng gói trong lọ cuối cùng. Điều này làm tăng kích thước của lọ cuối cùng lên rất nhiều. Có thể chọn lọ bên ngoài mà bạn định cho vào lọ cuối cùng không? Dưới đây là các bản ghi một jar: pastebin.com/UwniQJ2X
bianca

Tôi không biết liệu bạn có thể cấu hình những gì được bao gồm hay không. Về cơ bản, một-jar bao gồm tất cả các phụ thuộc được chỉ định bởi dự án của bạn, bao gồm cả các phụ thuộc bắc cầu, vì vậy có, jar cuối cùng có thể trở nên lớn nếu bạn có nhiều phụ thuộc. Một số chi phí sẽ được thêm vào bởi one-jar, để Java làm việc với cấu trúc "jar of jar".
matsev

2

Một giải pháp thay thế là sử dụng plugin bóng maven để tạo uber-jar.

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-shade-plugin</artifactId>
    <version> Your Version Here </version>
    <configuration>
            <!-- put your configurations here -->
    </configuration>
    <executions>
            <execution>
                    <phase>package</phase>
                    <goals>
                            <goal>shade</goal>
                    </goals>
            </execution>
    </executions>
</plugin>
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.