2016-12-16 3 views
0

Cloudera CDH 5.8.0 가상 상자를 실행하기 위해 작업을 제출하려고하고 json 라이브러리를 사용하고 있으며 또한 maven-shade 플러그인을 사용합니다.Cloudera CDH 5.8.0 가상 상자와 스파크 라이브러리 충돌을 해결하는 방법

spark-submit --class com.example.spark.SparkParser --master local[*] uber-spark-0.0.1-SNAPSHOT.jar 

그리고 나는 다음과 같은 예외가 점점 계속 :

<project> 
    <modelVersion>4.0.0</modelVersion> 

    <groupId>com.example</groupId> 
    <artifactId>spark</artifactId> 
    <version>0.0.1-SNAPSHOT</version> 
    <packaging>jar</packaging> 

    <dependencies> 

     <dependency> 
      <groupId>org.apache.spark</groupId> 
      <artifactId>spark-core_2.11</artifactId> 
      <version>1.5.1</version> 
      <scope>provided</scope> 
     </dependency> 

     <dependency> 
      <groupId>org.json</groupId> 
      <artifactId>json</artifactId> 
      <version>20160810</version> 
     </dependency> 

    </dependencies> 

    <build> 
     <plugins> 
      <plugin> 
       <groupId>org.apache.maven.plugins</groupId> 
       <artifactId>maven-compiler-plugin</artifactId> 
       <version>2.3.2</version> 
       <configuration> 
        <source>1.8</source> 
        <target>1.8</target> 
       </configuration> 
      </plugin> 
      <plugin> 
       <groupId>org.apache.maven.plugins</groupId> 
       <artifactId>maven-shade-plugin</artifactId> 
       <version>2.3</version> 
       <executions> 
        <execution> 
         <phase>package</phase> 
         <goals> 
          <goal>shade</goal> 
         </goals> 
        </execution> 
       </executions> 
       <configuration> 
        <filters> 
         <filter> 
          <artifact>*:*</artifact> 
          <excludes> 
           <exclude>META-INF/*.SF</exclude> 
           <exclude>META-INF/*.DSA</exclude> 
           <exclude>META-INF/*.RSA</exclude> 
          </excludes> 
         </filter> 
        </filters> 
        <finalName>uber-${project.artifactId}-${project.version}</finalName> 
       </configuration> 
      </plugin> 
     </plugins> 
    </build> 


</project> 

제출 명령은 다음과 같습니다

Exception in thread "main" java.lang.NoSuchMethodError: 
org.json.JSONTokener.<init>(Ljava/io/InputStream;) 
0123을 jar 파일에 대한 종속성을 포함, 다음은 내 치어입니다

나는 클래스가로드되는 라이브러리에서 알 수있는 작은 다음 코드 발견 :

ClassLoader classloader = org.json.JSONTokener.class.getClassLoader(); 
URL res = classloader.getResource("org/json/JSONTokener.class"); 
String path = res.getPath(); 
System.out.println("Core JSONTokener came from " + path); 

을 그리고 출력은 다음과 같습니다 : 나는 가상에 로컬 파일을 찾을 수 있습니다

Core JSONTokener came from file:/usr/lib/hive/lib/hive-exec-1.1.0-cdh5.8.0.jar!/org/json/JSONTokener.class 

여전히 같은 잘못을 나는 심지어 내 jar 파일에서 제외하는 '제공'으로 JSON 라이브러리를 만들려고

[[email protected] ~]$ ls -l /usr/lib/hive/lib/hive-exec-1.1.0-cdh5.8.0.jar 
-rw-r--r-- 1 root root 19306194 Jun 16 2016 /usr/lib/hive/lib/hive-exec-1.1.0-cdh5.8.0.jar 

:하지만, 다음과 같이 CDH의 상자 또는.

나는라는 이름의 로컬 jar 파일 제거하려고 : /usr/lib/hive/lib/hive-exec-1.1.0-cdh5.8.0.jar 을 그리고 내 코드는 제대로 작동하지만이 확실하지 않다 올바른 해결책이고,이 라이브러리를 제거하면 cloudera가 어떻게 든 상처를 입을 수 있습니다.

그렇다면 어떻게 spark에이 로컬 jar 파일을 사용하지 말고 내 'uber-spark-0.0.1-SNAPSHOT.jar'파일에 포함 된 것을 사용 할 수 있습니까?

답변

0

아무도 전에 대답없는 이유 확실하지 ...

문제는 런타임 클래스 경로에 같은 라이브러리의 서로 다른 두 가지 버전을 가지고있다. 하나는 항아리에 포함되어 있고 다른 하나는 Cloudera가 추가했습니다. JSONTokener에는 두 버전간에 다른 메소드가 있습니다 (한 버전에는 존재하지 않거나 서명이 변경되었을 수 있습니다), 코드에서 하나의 버전을 사용하므로 (코드가 컴파일되는 이유이기도하지만) 런타임 중에 ClassLoader 다른 하나를 사용 중입니다.

귀하의 질문에 대한 간단한 대답은 할 수 없다는 것입니다. Java ClassLoader는 경로에있는 모든 라이브러리를로드하고 클래스를로드하면 찾은 첫 번째 클래스를로드합니다. 이 경우 Hive 런타임에서 제공하는 것입니다.

길게 대답 : 앱에 포함 된 jar를 강제로 사용하는 유일한 방법은 스파이크 기본값을 편집하여 하이브가 포함되지 않도록하는 것입니다. 지금, 나는 당신의 경우에 그것을하는 방법에 대해 완전히 확신하지는 않지만, 아마도 /etc/spark/spark-defaults.conf를보고, 하이브를 비활성화 시키거나, Cloudera Manager 내부의 무언가가 갈 방법입니다 .

프로젝트에서 jar 파일을 제거하고 Cloudera Maven 저장소를 pom에 추가하고 제공된 종속 파일로 hive-exec-1.1.0-cdh5.8.0을 포함하는 것이 더 좋은 옵션입니다. 자세한 내용은 Using the CDH 5 Maven repository을 참조하십시오. 이것을하기 위해.

희망이 도움이됩니다.