Làm cách nào để yêu cầu jaxb / Maven tạo nhiều gói lược đồ?


80

Thí dụ:

</plugin>       
       <plugin>
           <groupId>org.jvnet.jaxb2.maven2</groupId>
           <artifactId>maven-jaxb2-plugin</artifactId>
           <version>0.7.1</version>
           <executions>
             <execution>
               <goals>
                 <goal>generate</goal>
               </goals>
             </execution>
           </executions>
            <configuration>
             <schemaDirectory>src/main/resources/dir1</schemaDirectory>
              <schemaIncludes>
                  <include>schema1.xsd</include>
              </schemaIncludes>
              <generatePackage>schema1.package</generatePackage>
           </configuration>
         </plugin>
          <plugin>
           <groupId>org.jvnet.jaxb2.maven2</groupId>
           <artifactId>maven-jaxb2-plugin</artifactId>
           <version>0.7.1</version>
           <executions>
             <execution>
               <goals>
                 <goal>generate</goal>
               </goals>
             </execution>
           </executions>
            <configuration>
             <schemaDirectory>src/main/resources/dir2</schemaDirectory>
              <schemaIncludes>
                  <include>schema2.xsd</include>
              </schemaIncludes>
              <generatePackage>schema2.package</generatePackage>
           </configuration>
         </plugin>
       </plugins>

Điều gì đã xảy ra: Maven thực thi plugin đầu tiên. Sau đó, xóa thư mục đích và tạo gói thứ hai, gói này sẽ hiển thị.

Tôi đã cố gắng đặt target / somedir1 cho cấu hình đầu tiên và target / somedir2 cho cấu hình thứ hai. Nhưng hành vi không thay đổi? Có ý kiến ​​gì không? Tôi không muốn tạo các gói trực tiếp trong thư mục src / main / java, vì các gói này được tạo ra và không được trộn lẫn với các lớp được tạo thủ công.


vâng, gặp vấn đề tương tự ở đây, mặc dù giải pháp của Pascal hoạt động gần như hoàn hảo. Tất cả những gì tôi cần bây giờ là có được IDE để chơi tốt với mã đã tạo, nếu không thì đó chỉ là những gì tôi muốn.
Newtopian

Câu trả lời:


119

Tôi phải chỉ định khác generateDirectory(không có điều này, plugin đang xem xét rằng các tệp đã được cập nhật và không tạo ra bất kỳ thứ gì trong lần thực thi thứ hai). Và tôi khuyên bạn nên tuân theo target/generated-sources/<tool>quy ước cho các nguồn được tạo để chúng sẽ được nhập tự động trong IDE yêu thích của bạn. Tôi cũng khuyên bạn nên khai báo một số executionthay vì khai báo plugin hai lần (và di chuyển configurationbên trong mỗi executionphần tử):

<plugin>
  <groupId>org.jvnet.jaxb2.maven2</groupId>
  <artifactId>maven-jaxb2-plugin</artifactId>
  <version>0.7.1</version>
  <executions>
    <execution>
      <id>schema1-generate</id>
      <goals>
        <goal>generate</goal>
      </goals>
      <configuration>
        <schemaDirectory>src/main/resources/dir1</schemaDirectory>
        <schemaIncludes>
          <include>shiporder.xsd</include>
        </schemaIncludes>
        <generatePackage>com.stackoverflow.package1</generatePackage>
        <generateDirectory>${project.build.directory}/generated-sources/xjc1</generateDirectory>
      </configuration>
    </execution>
    <execution>
      <id>schema2-generate</id>
      <goals>
        <goal>generate</goal>
      </goals>
      <configuration>
        <schemaDirectory>src/main/resources/dir2</schemaDirectory>
        <schemaIncludes>
          <include>books.xsd</include>
        </schemaIncludes>
        <generatePackage>com.stackoverflow.package2</generatePackage>
        <generateDirectory>${project.build.directory}/generated-sources/xjc2</generateDirectory>
      </configuration>
    </execution>
  </executions>
</plugin>

Với thiết lập này, tôi nhận được kết quả sau mvn clean compile

mục tiêu $ cây /
Mục tiêu/
├── lớp học
│ ├── com
│ │ └── stackoverflow
│ │ ├── Lớp ứng dụng
│ │ ├── gói1
│ │ │ ├── ObjectFactory.class
│ │ │ ├── Shiporder.class
│ │ │ ├── Shiporder $ Item.class
│ │ │ └── Đặt hàng $ Shipto.class
│ │ └── gói2
│ │ ├── BookForm.class
│ │ ├── BooksForm.class
│ │ ├── ObjectFactory.class
│ │ └── package-info.class
│ ├── dir1
│ │ └── shiporder.xsd
│ └── dir2
│ └── books.xsd
└── nguồn tạo
    ├── xjc
    │ └── META-INF
    │ └── sun-jaxb.ep Chap
    ├── xjc1
    │ └── com
    │ └── stackoverflow
    │ └── gói1
    │ ├── ObjectFactory.java
    │ └── Shiporder.java
    └── xjc2
        └── com
            └── stackoverflow
                └── gói2
                    ├── BookForm.java
                    ├── BooksForm.java
                    ├── ObjectFactory.java
                    └── package-info.java

Đó dường như là kết quả mong đợi.


cảm ơn, tôi thực sự đã gặp vấn đề tương tự ngày hôm qua nhưng đã tạm thời chấp nhận nó. Giải pháp của bạn hoạt động gần như hoàn hảo, vấn đề duy nhất của tôi bây giờ là tôi không thể biên dịch Eclipse mà không gặp lỗi. Tất cả đều tốt trên dòng lệnh. Cách giải quyết hiện tại của tôi là tôi khai báo các thư mục này trong đích là thư mục nguồn và tất cả đều tốt .. mặc dù tôi không chắc mình thích nó lắm, tôi muốn tạo một jar với mã đã tạo và chỉ sử dụng trực tiếp
Newtopian

1
Plugin eclipse m2eclipse cập nhật đường dẫn xây dựng. Sau khi tạo bean với mvc clean assembly: assembly, tôi chỉ chạy [nhấp chuột phải vào dự án]> [Maven]> [Cập nhật cấu hình dự án] và nó cập nhật đường dẫn xây dựng.
MR

@Newtopian Xem bình luận của @ MR, m2eclipse sẽ làm điều đó cho bạn nếu bạn tuân theo quy ước mà tôi đã đề cập.
Pascal Thivent

hmm ok sau đó, hóa ra để làm điều tương tự như tôi đã làm theo cách thủ công, bây giờ chỉ cần một hoặc hai cú nhấp chuột. Vẫn còn lạ khi thấy mục tiêu trong các thư mục nguồn nhưng bây giờ gần như miễn phí để thực hiện nên tôi sẽ giữ nó :-)
Newtopian

1
Tôi biết nó là câu hỏi cũ nhưng tôi hy vọng một cái gì đó trả lời cho tôi. Tôi sử dụng mã đó và nó hoạt động. Nhưng khi tôi muốn thiết lập cùng một gói, nó luôn chỉ tạo ra một lược đồ. Ví dụ: trong lần thực thi đầu tiên, tôi đặt com.myproject.answer và trong lần thực thi thứ hai com.myproject.request .. và sau khi tạo nguồn, tôi chỉ có gói * câu trả lời và yêu cầu bị thiếu ... bất kỳ ý tưởng nào để khắc phục nó? Tạo thư mục tôi cũng đặt như vậy.
Denis Stephanov

14

Bạn cũng có thể sử dụng các ràng buộc JAXB để chỉ định gói khác nhau cho mỗi lược đồ, ví dụ:

<jaxb:bindings xmlns:jaxb="http://java.sun.com/xml/ns/jaxb" xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
    xmlns:xs="http://www.w3.org/2001/XMLSchema" version="2.0" schemaLocation="book.xsd">

    <jaxb:globalBindings>
        <xjc:serializable uid="1" />
    </jaxb:globalBindings>

    <jaxb:schemaBindings>
        <jaxb:package name="com.stackoverflow.book" />
    </jaxb:schemaBindings>

</jaxb:bindings>

Sau đó, chỉ cần sử dụng maven-jaxb2-plugin 0.8.0 mới <schemas><bindings>các phần tử trong pom.xml. Hoặc chỉ định thư mục đầu nhất <schemaDirectory><bindingDirectory>và bằng <include>lược đồ và các ràng buộc của bạn:

<schemaDirectory>src/main/resources/xsd</schemaDirectory>
<schemaIncludes>
    <include>book/*.xsd</include>
    <include>person/*.xsd</include>
</schemaIncludes>
<bindingDirectory>src/main/resources</bindingDirectory>
<bindingIncludes>
    <include>book/*.xjb</include>
    <include>person/*.xjb</include>
</bindingIncludes>

Tôi nghĩ đây là giải pháp tiện lợi hơn , vì khi bạn thêm XSD mới, bạn không cần phải thay đổi Maven pom.xml, chỉ cần thêm tệp ràng buộc XJB mới vào cùng một thư mục.


Trong khi tầm thường soạn thảo để cung cấp một gợi ý cú pháp nổi bật không cải thiện mức độ dễ đọc của bài
Kev

OK, cảm ơn vì lời giải thích. Tôi không hiểu rằng chỉnh sửa đã thêm đánh dấu cú pháp.
xmedeko

2
Đây là câu trả lời tốt nhất cho tôi vì tôi sẽ không muốn tiếp tục thay đổi pom mỗi khi một lược đồ mới được thêm vào.
Ben Thurley

Một vấn đề ở đây là nếu cuốn sách và người ở trong cùng một không gian tên đích trong xsd. Giả sử thay vào đó, họ có sách, tạp chí, báo, v.v., tất cả đều bao gồm cả publisherhable.xsd. Chúng phải ở trong cùng một không gian tên như có thể xuất bản, và do đó lẫn nhau, và bây giờ điều này bị phá vỡ vì bạn chỉ có thể có một schemaBindings trên mỗi không gian tên. Tôi đồng ý rằng nó lý tưởng và tôi ước nó hoạt động với ví dụ trên, nhưng JAXB không đủ linh hoạt.
TurnipEntropy

8

bạn nên thay đổi điều đó để xác định plugin chỉ một lần và thực hiện hai lần các vùng thực thi ... như sau ... và createDirectory phải được đặt (dựa trên tài liệu) ..

<plugin>
  <groupId>org.jvnet.jaxb2.maven2</groupId>
  <artifactId>maven-jaxb2-plugin</artifactId>
  <version>0.7.1</version>
  <executions>
    <execution>
      <id>firstrun</id>
      <goals>
        <goal>generate</goal>
      </goals>
      <configuration>
        <generateDirectory>target/gen1</generateDirectory>
        <schemaDirectory>src/main/resources/dir1</schemaDirectory>
        <schemaIncludes>
          <include>schema1.xsd</include>
        </schemaIncludes>
        <generatePackage>schema1.package</generatePackage>
      </configuration>
    </execution>
    <execution>
      <id>secondrun</id>
      <goals>
        <goal>generate</goal>
      </goals>
      <configuration>
        <generateDirectory>target/gen2</generateDirectory>
        <schemaDirectory>src/main/resources/dir2</schemaDirectory>
        <schemaIncludes>
          <include>schema2.xsd</include>
        </schemaIncludes>
        <generatePackage>schema2.package</generatePackage>
      </configuration>
    </execution>
  </executions>
</plugin>

Đối với tôi, dường như bạn đang chiến đấu chống lại quy tắc tạo tác duy nhất của maven ... có lẽ bạn nên nghĩ về điều này.


Quy tắc một tạo tác cho mỗi mô-đun là đúng nhưng ... OP không tạo ra hai tạo tác.
Pascal Thivent

5

Điều này cũng có thể đạt được bằng cách chỉ định tên tệp cũ cho các lược đồ và không xóa thư mục đầu ra. Thư mục out put mặc định được tự động đưa vào classpath, điều này hơi thuận tiện. Nếu chúng ta chỉ định thư mục đầu ra khác nhau, người ta phải quan tâm đến classpath để sử dụng mã này trong IDE. Ví dụ -

<plugins>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>jaxb2-maven-plugin</artifactId>
            <version>1.3.1</version>
            <configuration>
                <quiet>true</quiet>
                <verbose>false</verbose>
                <clearOutputDir>false</clearOutputDir>
                <readOnly>true</readOnly>
                <arguments>-mark-generated</arguments>
            </configuration>
            <executions>
                <execution>
                    <id>reportingSchema</id>
                    <goals>
                        <goal>xjc</goal>
                    </goals>
                    <configuration>
                        <schemaDirectory>src/main/resources/schema/r17/schemaReporting</schemaDirectory>
                        <schemaIncludes>
                            <include>OCISchemaReporting.xsd</include>
                        </schemaIncludes>
                        <packageName>com.broadsoft.oci.r17.reporting</packageName>
                        <staleFile>${build.directory}/generated-sources/.jaxb-staleFlag-reporting</staleFile>
                    </configuration>
                </execution>
                <execution>
                    <id>schemaAS</id>
                    <goals>
                        <goal>xjc</goal>
                    </goals>
                    <configuration>
                        <schemaDirectory>src/main/resources/schema/r17/schemaAS</schemaDirectory>
                        <schemaIncludes>
                            <include>OCISchemaAS.xsd</include>
                        </schemaIncludes>
                        <packageName>com.broadsoft.oci.r17.as</packageName>
                        <staleFile>${build.directory}/generated-sources/.jaxb-staleFlag-as</staleFile>
                    </configuration>
                </execution>
            </executions>
        </plugin>
</plugins>

Nguồn: Tạo mã bằng JAXB Plugin


5

tôi đã giải quyết bằng:

                        <removeOldOutput>false</removeOldOutput>
                        <clearOutputDir>false</clearOutputDir>
                        <forceRegenerate>true</forceRegenerate>

thêm cái này vào mỗi cấu hình;)


2
Bạn cũng có thể chỉ thêm nó vào <executions>thẻ. Đủ rồi. <removeOldOutput>được đặt thành false theo mặc định. Nhưng tôi không thể tìm thấy <clearOutputDir>tại static.highsource.org/mjiip/maven-jaxb2-plugin/...

Đối với tôi, giải pháp thực tế, gây ra bạn có thể tạo everythong trong cùng một thư mục
MilacH

<clearOutputDir>false</clearOutputDir>là đủ cho tôi trong trường hợp của tôi.
Ruwanka Madhushan

3

Điều này đã được khắc phục trong phiên bản 1.6 của plugin .

            <groupId>org.codehaus.mojo</groupId>
            <artifactId>jaxb2-maven-plugin</artifactId>
            <version>1.6</version>

Tuy nhiên, lưu ý nhanh, tôi nhận thấy rằng đầu ra lặp lại đầu tiên đã bị xóa. Tôi đã sửa nó bằng cách thêm phần sau vào mỗi lần thực thi.

                        <removeOldOutput>false</removeOldOutput>
                        <clearOutputDir>false</clearOutputDir>

Đây là ví dụ làm việc đầy đủ của tôi với mỗi lần lặp lại xuất ra một cách chính xác. BTW Tôi đã phải làm điều này do sự cố không gian tên trùng lặp với xsd mà tôi đã được cung cấp. Điều này dường như giải quyết vấn đề của tôi.

        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>jaxb2-maven-plugin</artifactId>
            <version>1.6</version>
            <executions>
                <execution>
                    <id>submitOrderRequest</id>
                    <goals>
                        <goal>xjc</goal>
                    </goals>
                    <configuration>
                        <extension>true</extension>
                        <schemaDirectory>src/main/resources/xsd/</schemaDirectory>
                        <!-- <schemaFiles>getOrderStatusResponse.xsd,quoteShippingRequest.xsd,quoteShippingResponse.xsd,submitOrderRequest.xsd,submitOrderResponse.xsd</schemaFiles> -->
                        <schemaFiles>submitOrderRequest.xsd</schemaFiles>
                        <bindingDirectory>${project.basedir}/src/main/resources/xjb</bindingDirectory>
                        <bindingFiles>submitOrderRequest.xjb</bindingFiles>
                        <removeOldOutput>false</removeOldOutput>
                        <clearOutputDir>false</clearOutputDir>
                    </configuration>
                </execution>
                <execution>
                    <id>submitOrderResponse</id>
                    <goals>
                        <goal>xjc</goal>
                    </goals>
                    <configuration>
                        <extension>true</extension>
                        <schemaDirectory>src/main/resources/xsd/</schemaDirectory>
                        <!-- <schemaFiles>getOrderStatusResponse.xsd,quoteShippingRequest.xsd,quoteShippingResponse.xsd,submitOrderRequest.xsd,submitOrderResponse.xsd</schemaFiles> -->
                        <schemaFiles>submitOrderResponse.xsd</schemaFiles>
                        <bindingDirectory>${project.basedir}/src/main/resources/xjb</bindingDirectory>
                        <bindingFiles>submitOrderResponse.xjb</bindingFiles>
                        <removeOldOutput>false</removeOldOutput>
                        <clearOutputDir>false</clearOutputDir>
                    </configuration>
                </execution>
            </executions>

        </plugin>

2

Những điều sau đây phù hợp với tôi, sau nhiều thử nghiệm

<plugin>
         <groupId>org.codehaus.mojo</groupId>
         <artifactId>jaxb2-maven-plugin</artifactId>
         <version>2.1</version>
         <executions>
            <execution>
              <id>xjc1</id>
              <goals>
                  <goal>xjc</goal>
              </goals>
             <configuration>
                <packageName>com.mycompany.clientSummary</packageName>
               <sourceType>wsdl</sourceType>
                <sources>
                <source>src/main/resources/wsdl/GetClientSummary.wsdl</source>
                </sources>
                <outputDirectory>target/generated-sources/xjb</outputDirectory>
                 <clearOutputDir>false</clearOutputDir>
            </configuration>
          </execution>

          <execution>
             <id>xjc2</id>
             <goals>
                 <goal>xjc</goal>
             </goals>
             <configuration>
                <packageName>com.mycompany.wsclient.employerProfile</packageName>
                <sourceType>wsdl</sourceType>
                <sources>
                <source>src/main/resources/wsdl/GetEmployerProfile.wsdl</source>
                </sources>
                <outputDirectory>target/generated-sources/xjb</outputDirectory>
                <clearOutputDir>false</clearOutputDir>
         </configuration>
         </execution>

         <execution>
            <id>xjc3</id>
            <goals>
                <goal>xjc</goal>
            </goals>
            <configuration>
                <packageName>com.mycompany.wsclient.producersLicenseData</packageName>
                <sourceType>wsdl</sourceType>
                <sources>
                <source>src/main/resources/wsdl/GetProducersLicenseData.wsdl</source>
                </sources>
                <outputDirectory>target/generated-sources/xjb</outputDirectory>
                <clearOutputDir>false</clearOutputDir>
            </configuration>
        </execution>


     </executions>
  </plugin>

2

Tôi đã gặp rất nhiều sự cố khi sử dụng jaxb trong Maven nhưng tôi đã giải quyết được vấn đề của bạn bằng cách làm như sau

Đầu tiên hãy tạo một tệp schema.xjc

<?xml version="1.0" encoding="UTF-8"?>
<jaxb:bindings xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
               xmlns:xsd="http://www.w3.org/2001/XMLSchema"
               jaxb:version="2.0">
    <jaxb:bindings schemaLocation="YOUR_URL?wsdl#types?schema1">
        <jaxb:schemaBindings>
            <jaxb:package name="your.package.name.schema1"/>
        </jaxb:schemaBindings>
    </jaxb:bindings>
    <jaxb:bindings schemaLocation="YOUR_URL??wsdl#types?schema2">
        <jaxb:schemaBindings>
            <jaxb:package name="your.package.name.schema2"/>
        </jaxb:schemaBindings>
    </jaxb:bindings>
</jaxb:bindings>

Tên gói có thể là bất cứ thứ gì bạn muốn, miễn là nó không chứa bất kỳ từ khóa dành riêng nào trong Java

Tiếp theo, bạn phải tạo tập lệnh wsimport.bat để tạo mã và mã được đóng gói tại vị trí ưa thích.

cd C:\YOUR\PATH\TO\PLACE\THE\PACKAGES
wsimport -keep -verbose -b "C:\YOUR\PATH\TO\schema.xjb" YOUR_URL?wsdl
pause

Nếu bạn không muốn sử dụng cd, bạn có thể đặt wsimport.bat trong "C: \ YOUR \ PATH \ TO \ PLACE \ THE \ PACKAGES"

Nếu bạn chạy nó mà không có -keep -verbose, nó sẽ chỉ tạo ra các gói chứ không phải các tệp .java.

-B sẽ đảm bảo rằng schema.xjc được sử dụng khi tạo


0

Có một giải pháp khác, một giải pháp rõ ràng (IMO) cho vấn đề này Có một tham số gọi là "staleFile" được sử dụng như một cờ để không tạo lại nội dung. Chỉ cần thay đổi nó trong mỗi lần thực hiện.

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.