2014-11-30 1 views
4

Maven (서버 앱도 구현되어 실행 됨)으로 간단한 Jersey 2 클라이언트 앱을 만들고 싶습니다.저지 2 클라이언트 with maven

내 pom.xml 파일

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> 
    <modelVersion>4.0.0</modelVersion> 
    <groupId>com.client</groupId> 
    <artifactId>RestClient</artifactId> 
    <packaging>jar</packaging> 
    <version>1.0-SNAPSHOT</version> 
    <name>RestClient</name> 
    <url>http://maven.apache.org</url> 
    <dependencies> 
     <dependency> 
      <groupId>junit</groupId> 
      <artifactId>junit</artifactId> 
      <version>3.8.1</version> 
      <scope>test</scope> 
     </dependency> 
     <dependency> 
      <groupId>org.glassfish.jersey.core</groupId> 
      <artifactId>jersey-client</artifactId> 
      <version>2.13</version> 
      <scope>provided</scope> 
     </dependency> 
    </dependencies> 

    <build> 
     <plugins> 
      <plugin> 
       <groupId>org.apache.maven.plugins</groupId> 
       <artifactId>maven-compiler-plugin</artifactId> 
       <version>2.3.2</version> 
       <configuration> 
        <source>1.7</source> 
        <target>1.7</target> 
       </configuration> 
      </plugin> 
     </plugins> 
    </build> 
</project> 

자바 코드는

package com.client; 

import javax.ws.rs.client.Client; 
import javax.ws.rs.client.ClientBuilder; 
import javax.ws.rs.client.Entity; 
import javax.ws.rs.core.GenericType; 
import javax.ws.rs.core.MediaType; 
import javax.ws.rs.client.WebTarget; 
import javax.ws.rs.core.Response; 
import javax.ws.rs.client.Invocation.Builder;   

public class App 
{ 
    public static void main(String[] args) 
    { 

     Client client = ClientBuilder.newClient(); 
     WebTarget target = client.target("http://localhost:8080").path("simple-service-webapp/rest/myresource"); 

     Builder builder = target.request(); 
     //Response response = builder.get(); 
     String result = builder.get(String.class); 
     System.out.println(target.getUri().toString()); 
     System.out.println("Result=" + result); 

    } 
} 

나는 통과 명령 MVN 패키지 모든 것을하여 응용 프로그램을 구축 할 수 있습니다. 그럼, 자바 -cp 대상/위해 RESTClient-1.0-SNAPSHOT.jar com.client.App에 의해 응용 프로그램을 실행 한 후 오류가 발생,

Exception in thread "main" java.lang.NoClassDefFoundError: javax/ws/rs/client/ClientBuilder 
     at com.client.App.main(App.java:20) 
Caused by: java.lang.ClassNotFoundException: javax.ws.rs.client.ClientBuilder 
     at java.net.URLClassLoader$1.run(URLClassLoader.java:366) 
     at java.net.URLClassLoader$1.run(URLClassLoader.java:355) 
     at java.security.AccessController.doPrivileged(Native Method) 
     at java.net.URLClassLoader.findClass(URLClassLoader.java:354) 
     at java.lang.ClassLoader.loadClass(ClassLoader.java:425) 
     at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308) 
     at java.lang.ClassLoader.loadClass(ClassLoader.java:358) 
     ... 1 more 

라이브러리가 포함되지 않은 것으로 보인다 때문에 projeckt의 파일 트리 외모 :

. 
├── pom.xml 
├── src 
│   ├── main 
│   │   └── java 
│   │    └── com 
│   │     └── client 
│   │      └── App.java 
│   └── test 
│    └── java 
│     └── com 
│      └── client 
│       └── AppTest.java 
└── target 
    ├── classes 
    │   └── com 
    │    └── client 
    │     └── App.class 
    ├── generated-sources 
    │   ├── annotations 
    │   └── test-annotations 
    ├── maven-archiver 
    │   └── pom.properties 
    ├── RestClient-1.0-SNAPSHOT.jar 
    ├── surefire 
    ├── surefire-reports 
    │   ├── com.client.AppTest.txt 
    │   └── TEST-com.client.AppTest.xml 
    └── test-classes 
     └── com 
      └── client 
       └── AppTest.class 

나는 어디에서 실수 했습니까? 감사.

답변

3

로컬 저장소에서 프로젝트로 종속성을 복사해야합니다 (실제로는 -cp에 연결할 위치). 이를 위해 maven-dependency-plugin을 사용할 수 있습니다. 그냥 할 것입니다 위의 플러그인 구성 target/lib 모든 종속성을 복사 무엇인지 <plugins>

<plugin> 
    <groupId>org.apache.maven.plugins</groupId> 
    <artifactId>maven-dependency-plugin</artifactId> 
    <version>2.9</version> 
    <executions> 
     <execution> 
      <id>copy-dependencies</id> 
      <phase>package</phase> 
      <goals> 
       <goal>copy-dependencies</goal> 
      </goals> 
      <configuration> 
       <outputDirectory>${project.build.directory}/lib</outputDirectory> 
       <overWriteReleases>false</overWriteReleases> 
       <overWriteSnapshots>false</overWriteSnapshots> 
       <overWriteIfNewer>true</overWriteIfNewer> 
      </configuration> 
     </execution> 
    </executions> 
</plugin> 

이를 추가 할 수 있습니다.

jar을 실행 파일로 실행하는 가장 쉬운 방법은 Maven을 통해 MANIFEST.MFClass-Path을 설정하는 것입니다. 이를 위해 maven-jar-plugin을 사용할 수 있습니다. 그래서 <plugins>

<plugin> 
    <groupId>org.apache.maven.plugins</groupId> 
    <artifactId>maven-jar-plugin</artifactId> 
    <version>2.5</version> 
    <configuration> 
     <archive> 
      <index>true</index> 
      <manifest> 
       <addClasspath>true</addClasspath> 
       <classpathPrefix>lib/</classpathPrefix> 
       <mainClass>com.client.App</mainClass> 
      </manifest> 
     </archive> 
    </configuration> 
</plugin> 

이 추가 또한 당신은 뉴저지 클라이언트 종속성에 대한 <scope>provided</scope> 제거해야합니다. 이 스코프를 사용하면 Maven은 classpath에 항아리를 추가하지 않는다.

그런 다음, 모든 항아리가 매니페스트에 지정되어 있으므로 -cp 옵션을 사용하지 않고 java -jar your-jar.jar을 실행하면됩니다. 모양이 비슷해야합니다.

Manifest-Version: 1.0 
Archiver-Version: Plexus Archiver 
Built-By: XxxxXxxxx 
Class-Path: lib/jersey-client-2.13.jar lib/jersey-common-2.13.jar lib/ 
javax.annotation-api-1.2.jar lib/jersey-guava-2.13.jar lib/osgi-resou 
rce-locator-1.0.1.jar lib/javax.ws.rs-api-2.0.1.jar lib/hk2-api-2.3.0 
-b10.jar lib/hk2-utils-2.3.0-b10.jar lib/aopalliance-repackaged-2.3.0 
-b10.jar lib/javax.inject-2.3.0-b10.jar lib/hk2-locator-2.3.0-b10.jar 
    lib/javassist-3.18.1-GA.jar 
Created-By: Apache Maven 3.0.5 
Build-Jdk: 1.8.0_20 
Main-Class: com.client.App 
+0

감사합니다. 작동합니다. 나는 Maven으로 시작하고있다. 마지막 질문이 있어도 될까요? 필자는 서버 응용 프로그램의 pom.xml에 플러그인/매개 변수가 없지만 특수 설정 없이도 응용 프로그램의 lib 디렉토리에 libs를 복사합니다. 그것은 응용 프로그램 서버와 협력 할 것으로 간주되는 서버 응용 프로그램이기 때문에 기본적으로 lib 디렉토리를 만들고 필요한 lib를 복사하도록 설정되어 있기 때문입니까? 아니면 다른 목적이 있습니까? 감사 – jiri463

0

제공된대로 저지 종속성을 표시 했으므로 출력에 포함되지 않습니다. 종속성이 제공되면 환경 (예 : 응용 프로그램 서버)에서 사용할 수 있다고 가정하기 때문입니다.

Maven 종속성에서 <scope>provided</scope>을 제거하거나 프로그램을 실행할 때 -cp 매개 변수를 사용하여 classpath에 jersey jar를 포함 해보십시오.

0

다른 방법으로는 종속성을 뚱뚱한 항아리에 패키지하는 것입니다. maven-assembly-plugin이 자동으로이 작업을 수행합니다.

<plugin> 
    <artifactId>maven-assembly-plugin</artifactId> 
    <configuration> 
    <archive> 
     <manifest> 
     <mainClass>YOUR MAIN CLASS HERE</mainClass> 
     </manifest> 
    </archive> 
    <descriptorRefs> 
     <descriptorRef>jar-with-dependencies</descriptorRef> 
    </descriptorRefs> 
    </configuration> 
    <executions> 
    <execution> 
     <id>make-assembly</id> 
     <phase>package</phase> 
     <goals> 
     <goal>single</goal> 
     </goals> 
    </execution> 
    </executions> 
</plugin> 

모든 종속성이 jar에 포함되는 기본 모드보다 정교한 것이 필요한 경우 사용자 지정 어셈블리 사양을 만들 수 있습니다.

더 많은 설정이 가능한 maven-shade-plugin도 있습니다.

또 다른 유용한 도구입니다 :

mvn dependency:tree -Dverbose 

는 의존성이 정확하게 볼 수 있습니다.