【问题标题】:Adding java classes to sbt assembly将 java 类添加到 sbt 程序集
【发布时间】:2016-01-20 13:05:46
【问题描述】:

我在使用 scala 构建火花罐时遇到问题。这是一件非常简单的事情,我想通过 JDBC 以编程方式访问 mysql 服务器并将其加载到 spark 数据框中。我可以让它在 spark shell 中工作,但我不能打包一个与 spark 提交一起工作的 jar。它会打包,但在运行时会失败,并显示

Exception in thread "main" java.sql.SQLException: No suitable driver found for jdbc:mysql://localhost:3310/100million

我的 spark-submit 命令是

./bin/spark-submit ~/path/to/scala/project/target/scala-2.10/complete.jar --driver-class-path ~/path/to/mysql-connector-java-5.1.37-bin.jar

我的 build.sbt 看起来像

name := "sql_querier"

version := "1.0"

scalaVersion := "2.10.4"

sbtVersion := "0.13.7"

libraryDependencies += "org.apache.spark" %% "spark-core" % "1.5.1" % "provided"

libraryDependencies += "org.apache.spark" %% "spark-sql" % "1.5.1" % "provided"

libraryDependencies += "mysql" % "mysql-connector-java" % "5.1.37"

assemblyJarName in assembly := "complete.jar"

mainClass in assembly := Some("sql_querier")

offline := true

我非常简单的代码是

import org.apache.spark.SparkContext
import org.apache.spark.SparkConf
import org.apache.spark.sql.SQLContext

object sql_querier{

        def main(args: Array[String]) {

                val sc = new org.apache.spark.SparkContext()
                val sqlContext = new org.apache.spark.sql.SQLContext(sc)
                val url="jdbc:mysql://databaseurl:portno/database"

                val prop = new java.util.Properties
                prop.setProperty("user","myuser")
                prop.setProperty("password","mydatabase")
                val cats=sqlContext.read.jdbc(url, "categories", prop)
                cats.show
         }
 }

我隐藏了用户密码和数据库 URL 的真实值。 我在项目中也有一个文件,它添加了 sbt 程序集插件,但这并没有错。当使用指向 mysql jar 的 --driver-class-path 选项启动 spark shell 时,我可以运行命令并从 mysql 数据库中提取数据。

任何线索我在构建中做错了什么将不胜感激。

院长

编辑:尝试了很多东西,包括不同版本的 jdbc 驱动程序和添加行

sc.addJar("/Users/dean.wood/data_science/scala/sqlconn/mysql-connector-java-5.0.8-bin.jar")
Class.forName("com.mysql.jdbc.Driver")

到 scala 文件和行

assemblyMergeStrategy in assembly := {
  case PathList("META-INF", xs@_*) =>
    xs.map(_.toLowerCase) match {
      case ("manifest.mf" :: Nil) |
           ("index.list" :: Nil) |
           ("dependencies" :: Nil) |
           ("license" :: Nil) |
           ("notice" :: Nil) => MergeStrategy.discard
      case _ => MergeStrategy.first // was 'discard' previousely
    }
  case "reference.conf" => MergeStrategy.concat
  case _ => MergeStrategy.first
}

到构建文件。

似乎没有任何帮助。

【问题讨论】:

  • 看起来 mysql 驱动程序不在 fat jar 中。你运行了哪个任务?组装?
  • 你可以试试spark-submit ... --packages="mysql:mysql-connector-java:5.1.37"
  • @FatihDonmez 他没有使用组装任务,否则他的构建文件会有所不同。但是对于 Dean,这个错误就像 Fatih 所说的,因为您的应用程序 jar 中没有 mysql 连接器 jar,您需要使用 sbt 程序集插件来创建一个包含所有需要依赖项的 uber jar。另一种解决方案是按照 Victor 所说的那样做,但如果您正在构建更大的项目,最终您将需要大量依赖项,这不是您拥有的最佳解决方案。
  • 我认为你不需要这个:--driver-class-path ~/path/to/mysql-connector-java-5.1.37-bin.jar。我认为您可能缺少加载驱动程序Class.forName("com.mysql.jdbc.Driver").newInstance 的部分?
  • 我正在使用 sbt 程序集构建。就像我在问题中所说的那样,我有一个包含插件内容的插件文件,并且我之前使用过这个文件来构建一个胖 jar。我完全同意它看起来不像 jar 中的 mysql 驱动程序,但为什么不呢?它应该是。如果我尝试 marios 建议,我会得到同样的错误。无论如何,这不应该是必要的,因为它在 repl 中没有必要。我会尝试 Victors 的建议。

标签: mysql scala jdbc apache-spark


【解决方案1】:

解决了。我在构建文件或 scala 文件中没有做错任何事情。

结果 spark-submit 只查看 --driver-class-path 如果它位于可执行文件的路径之前。所以为了让它工作,而不是上面我使用的 spark-submit 命令:

./bin/spark-submit --driver-class-path ~/path/to/mysql-connector-java-5.1.37-bin.jar ~/path/to/scala/project/target/scala-2.10/complete.jar 

我怀疑要将其扩展到集群,我必须将 mysql 连接器添加到每个工作人员,但那是另一天。

【讨论】:

    猜你喜欢
    • 2014-11-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-13
    • 2015-12-28
    • 2021-07-21
    • 1970-01-01
    • 1970-01-01
    • 2022-08-04
    相关资源
    最近更新 更多