Hadoop 在Apache Spark中尝试持久化到数据库时,RDD不起作用

Hadoop 在Apache Spark中尝试持久化到数据库时,RDD不起作用,hadoop,apache-spark,apache-spark-sql,rdd,Hadoop,Apache Spark,Apache Spark Sql,Rdd,我想将我的rdd持久化到mysql数据库表中。我使用了一个map函数来迭代RDD,并将每个元组传递到我的函数中,在这里我进行持久化。在这里,我想将我的作业并行化为主节点和从节点 但是它不能正常工作,也不能调用使数据库持久化的函数 如果我使用collect(),例如courseSet.collect().map(m=>sendCourseInfo(m))而不是courseSet.map(m=>sendCourseInfo(m)),这将很好地工作 我不想在这里使用collect() 我在很多文章中都

我想将我的rdd持久化到mysql数据库表中。我使用了一个map函数来迭代RDD,并将每个元组传递到我的函数中,在这里我进行持久化。在这里,我想将我的作业并行化为主节点和从节点

但是它不能正常工作,也不能调用使数据库持久化的函数

如果我使用collect(),例如
courseSet.collect().map(m=>sendCourseInfo(m))
而不是
courseSet.map(m=>sendCourseInfo(m))
,这将很好地工作

我不想在这里使用collect()

我在很多文章中都搜索过这个,但都没有找到答案。谁能帮我解决这个问题

下面是我的代码

 .....
  x.toString().split(",")(1),
  x.toString().split(",")(2),
  x.toString().split(",")(3)))

 courseSet.map(m => sendCourseInfo(m))
}

def sendCourseInfo(courseData: (Int, String, String, String)): Unit = {
    try {
      DatabaseUtil.setJDBCConfiguration()

      val jdbcConnection: java.sql.Connection = DatabaseUtil.getConnection

      val statement = "{call insert_course (?,?,?,?)}"
      val callableStatement = jdbcConnection.prepareCall(statement)
      callableStatement.setInt(1, courseData._1)
      callableStatement.setString(2, courseData._2)
      callableStatement.setString(3, courseData._3)
      callableStatement.setString(4, courseData._4)

      callableStatement.executeUpdate
    } catch {
      case e: SQLException => println(e.getStackTrace)
    }
}
您正在RDD上调用map(),这是一种转换,而不是一种操作。所以,为了让它执行,你需要调用一些动作,比如

courseSet.foreach(sendCourseInfo)
对你所做工作的额外建议

无论
x
是什么,您都要将它转换为字符串,拆分它并从拆分中提取一些内容。对于RDD/集合中的每个元素,您将执行三次此操作。所以你可以用这样的方法来优化它

x.map(_.toString.split(",")).map(x=>(x(1),x(2),x(3)))
接下来,在这种情况下,您必须将这些数据持久化到DB、MySql中。您正在为此使用java常用的jdbc连接,为每个元素创建一个新的连接和操作。相反,使用Spark 2.x做类似的事情

import org.apache.spark.sql.SparkSession
import java.util.Properties

...

case class TableSchema(col1:Int,col2:String,col3:String,col4:String)
val props = new Properties()

def main(args: Array[String]): Unit = {

val ss = SparkSession.builder.appName("Test").master("local[*]").getOrCreate()

import ss.implicits._

...

props.setProperty("username", "username")
props.setProperty("password", "password")    

val df = rdd.map(_.toString.split(",")).map(x=>TableSchema(x(0),x(1),x(2),x(3))).toDF()

df.write.jdbc(s"jdbc:mysql://${mysqlHost}/${mysqlDBName}", "tablename", props)

}
让我知道这是否有用,干杯。

尝试
courseSet.map(m=>sendCourseInfo(m)).count
,否则map语句永远不会执行(RDD转换是惰性的),或者
courseSet.foreach(m=>sendCourseInfo(m))
这不是惰性的