web-dev-qa-db-fra.com

NoClassDefFoundError: org / Apache / hadoop / fs / StreamCapabilities lors de la lecture des données s3 avec spark

Je voudrais exécuter un travail simple spark sur ma machine de développement locale (via Intellij)) en lisant les données d'Amazon s3.

mon build.sbt fichier:

scalaVersion := "2.11.12"

libraryDependencies ++= Seq(
  "org.Apache.spark" %% "spark-core" % "2.3.1",
  "org.Apache.spark" %% "spark-sql" % "2.3.1",
  "com.amazonaws" % "aws-Java-sdk" % "1.11.407",
  "org.Apache.hadoop" % "hadoop-aws" % "3.1.1"
)

mon extrait de code:

val spark = SparkSession
    .builder
    .appName("test")
    .master("local[2]")
    .getOrCreate()

  spark
    .sparkContext
    .hadoopConfiguration
    .set("fs.s3n.impl","org.Apache.hadoop.fs.s3native.NativeS3FileSystem")

  val schema_p = ...

  val df = spark
    .read
    .schema(schema_p)
    .parquet("s3a:///...")

Et je reçois l'exception suivante:

Exception in thread "main" Java.lang.NoClassDefFoundError: org/Apache/hadoop/fs/StreamCapabilities
    at Java.lang.ClassLoader.defineClass1(Native Method)
    at Java.lang.ClassLoader.defineClass(ClassLoader.Java:763)
    at Java.security.SecureClassLoader.defineClass(SecureClassLoader.Java:142)
    at Java.net.URLClassLoader.defineClass(URLClassLoader.Java:467)
    at Java.net.URLClassLoader.access$100(URLClassLoader.Java:73)
    at Java.net.URLClassLoader$1.run(URLClassLoader.Java:368)
    at Java.net.URLClassLoader$1.run(URLClassLoader.Java:362)
    at Java.security.AccessController.doPrivileged(Native Method)
    at Java.net.URLClassLoader.findClass(URLClassLoader.Java:361)
    at Java.lang.ClassLoader.loadClass(ClassLoader.Java:424)
    at Sun.misc.Launcher$AppClassLoader.loadClass(Launcher.Java:349)
    at Java.lang.ClassLoader.loadClass(ClassLoader.Java:357)
    at Java.lang.Class.forName0(Native Method)
    at Java.lang.Class.forName(Class.Java:348)
    at org.Apache.hadoop.conf.Configuration.getClassByNameOrNull(Configuration.Java:2093)
    at org.Apache.hadoop.conf.Configuration.getClassByName(Configuration.Java:2058)
    at org.Apache.hadoop.conf.Configuration.getClass(Configuration.Java:2152)
    at org.Apache.hadoop.fs.FileSystem.getFileSystemClass(FileSystem.Java:2580)
    at org.Apache.hadoop.fs.FileSystem.createFileSystem(FileSystem.Java:2593)
    at org.Apache.hadoop.fs.FileSystem.access$200(FileSystem.Java:91)
    at org.Apache.hadoop.fs.FileSystem$Cache.getInternal(FileSystem.Java:2632)
    at org.Apache.hadoop.fs.FileSystem$Cache.get(FileSystem.Java:2614)
    at org.Apache.hadoop.fs.FileSystem.get(FileSystem.Java:370)
    at org.Apache.hadoop.fs.Path.getFileSystem(Path.Java:296)
    at org.Apache.spark.sql.execution.streaming.FileStreamSink$.hasMetadata(FileStreamSink.scala:45)
    at org.Apache.spark.sql.execution.datasources.DataSource.resolveRelation(DataSource.scala:354)
    at org.Apache.spark.sql.DataFrameReader.loadV1Source(DataFrameReader.scala:239)
    at org.Apache.spark.sql.DataFrameReader.load(DataFrameReader.scala:227)
    at org.Apache.spark.sql.DataFrameReader.parquet(DataFrameReader.scala:622)
    at org.Apache.spark.sql.DataFrameReader.parquet(DataFrameReader.scala:606)
    at Test$.delayedEndpoint$Test$1(Test.scala:27)
    at Test$delayedInit$body.apply(Test.scala:4)
    at scala.Function0$class.apply$mcV$sp(Function0.scala:34)
    at scala.runtime.AbstractFunction0.apply$mcV$sp(AbstractFunction0.scala:12)
    at scala.App$$anonfun$main$1.apply(App.scala:76)
    at scala.App$$anonfun$main$1.apply(App.scala:76)
    at scala.collection.immutable.List.foreach(List.scala:392)
    at scala.collection.generic.TraversableForwarder$class.foreach(TraversableForwarder.scala:35)
    at scala.App$class.main(App.scala:76)
    at Test$.main(Test.scala:4)
    at Test.main(Test.scala)
Caused by: Java.lang.ClassNotFoundException: org.Apache.hadoop.fs.StreamCapabilities
    at Java.net.URLClassLoader.findClass(URLClassLoader.Java:381)
    at Java.lang.ClassLoader.loadClass(ClassLoader.Java:424)
    at Sun.misc.Launcher$AppClassLoader.loadClass(Launcher.Java:349)
    at Java.lang.ClassLoader.loadClass(ClassLoader.Java:357)
    ... 41 more

Lors du remplacement de s3a:/// à s3:/// J'obtiens une autre erreur: No FileSystem for scheme: s3

Comme je suis nouveau sur AWS, je ne sais pas si je dois utiliser s3:///, s3a:/// ou s3n:///. J'ai déjà configuré mes informations d'identification AWS avec aws-cli.

Je n'ai aucune installation Spark sur ma machine.

Merci d'avance pour votre aide

9
ogen

Je commencerais par regarder les documents de dépannage S3A

N'essayez pas de "déposer" une version plus récente du kit SDK AWS que celle avec laquelle la version Hadoop a été créée.

quelle que soit la version des hadoop-JAR que vous avez sur votre installation locale spark, vous devez avoir exactement la même version de hadoop-aws, et exactement la même version du kit de développement logiciel aws avec lequel hadoop-aws a été construit. Essayez mvnrepository pour les détails.

15
Steve Loughran

Pour moi, cela a été résolu en ajoutant la dépendance suivante dans pom.xml en plus de ce qui précède:

<dependency>
    <groupId>org.Apache.hadoop</groupId>
    <artifactId>hadoop-common</artifactId>
    <version>3.1.1</version>
</dependency>
4
Atihska