1、1、重定向方式读入 scala 文件(执行 scala 脚本)/usr/local/spark-1.2.0-bin-hadoop2.4/bin/spark-shell ./spark-classorg.apache.spark.deploy.yarn.Client -jar -class -args -num-workers -master-class -master-memory -worker-memory -worker-cores -name -queue -addJars -files -archives 例 1 计算 PI,可以看出程序运行时是先将运行文件上传到 Hadoop 集群
2、的,所以客户端最好是和 Hadoop 集群在一个局域网里。SPARK_JAR=./assembly/target/scala-2.9.3/spark-assembly-0.8.1-incubating-hadoop2.2.0.jar ./spark-class org.apache.spark.deploy.yarn.Client -jar examples/target/scala-2.9.3/spark-examples-assembly-0.8.1-incubating.jar -class org.apache.spark.examples.SparkPi -args yarn-sta
3、ndalone -num-workers 3 -master-memory 2g -worker-memory 2g -worker-cores 1 例 2 计算 TCSPARK_JAR=./assembly/target/scala-2.9.3/spark-assembly-0.8.1-incubating-hadoop2.2.0.jar ./spark-class org.apache.spark.deploy.yarn.Client -jar examples/target/scala-2.9.3/spark-examples-assembly-0.8.1-incubating.jar
4、-class org.apache.spark.examples.SparkTC -args yarn-standalone -num-workers 3 -master-memory 2g -worker-memory 2g -worker-cores 1 点击 Tracking UI 中的相应链接可以查看 Spark 的运行信息:Spark on YARN 客户端模式作业运行全过程分析http:/ http:/ Spark on YARN 客户端模式作业运行全过程分析本文链接: http:/ 、Hbase、Flume 等 QQ 交流群:138615359 (已满),请加入新群:149892
5、483Spark on YARN 集群模式作业运行全过程分析Spark on YARN 客户端模式作业运行全过程分析SparkStandalone 模式作业运行全过程分析(未发布)在前篇文章中我介绍了 Spark on YARN 集群模式(yarn-cluster)作业从提交到运行整个过程的情况(详情见 Spark on YARN 集群模式作业运行全过程分析 ),我们知道Sparkon yarn 有两种模式:yarn-cluster 和 yarn-client。这两种模式作业虽然都是在 yarn 上面运行,但是其中的运行方式很不一样,今天我就来谈谈 Spark on YARN yarn-cli
6、ent 模式作业从提交到运行的过程剖析。和 yarn-cluster 模式一样,整个程序也是通过 spark-submit 脚本提交的。但是yarn-client 作业程序的运行不需要通过 Client 类来封装启动,而是直接通过反射机制调用作业的 main 函数。下面就来分析:1、通过 SparkSubmit 类的 launch 的函数直接调用作业的 main 函数(通过反射机制实现),如果是集群模式就会调用 Client 的 main 函数。2、而应用程序的 main 函数一定都有个 SparkContent,并对其进行初始化;3、在 SparkContent 初始化中将会依次做如下的事情
7、:设置相关的配置、注册MapOutputTracker、BlockManagerMaster、BlockManager,创建 taskScheduler和 dagScheduler;其中比较重要的是创建 taskScheduler 和 dagScheduler。在创建taskScheduler 的时候会根据我们传进来的 master 来选择 Scheduler 和SchedulerBackend。由于我们选择的是 yarn-client 模式,程序会选择YarnClientClusterScheduler 和YarnClientSchedulerBackend,并将 YarnClientSch
8、edulerBackend 的实例初始化YarnClientClusterScheduler,上面两个实例的获取都是通过反射机制实现的,YarnClientSchedulerBackend 类是 CoarseGrainedSchedulerBackend 类的子类,YarnClientClusterScheduler 是 TaskSchedulerImpl 的子类,仅仅重写了TaskSchedulerImpl 中的 getRackForHost 方法。4、初始化完 taskScheduler 后,将创建 dagScheduler,然后通过taskScheduler.start()启动 task
9、Scheduler,而在 taskScheduler 启动的过程中也会调用SchedulerBackend 的 start 方法。在 SchedulerBackend 启动的过程中将会初始化一些参数,封装在 ClientArguments 中,并将封装好的 ClientArguments 传进 Client 类中,并 client.runApp()方法获取 Application ID。5、client.runApp 里面的做是和前面 客户端进行操作 那节类似,不同的是在里面启动是 ExecutorLauncher(yarn-cluster 模式启动的是 ApplicationMaster)。
10、6、在 ExecutorLauncher 里面会初始化并启动 amClient,然后向ApplicationMaster 注册该 Application。注册完之后将会等待 driver 的启动,当 driver启动完之后,会创建一个 MonitorActor 对象用于和 CoarseGrainedSchedulerBackend进行通信(只有事件 AddWebUIFilter 他们之间才通信,Task 的运行状况不是通过它和CoarseGrainedSchedulerBackend 通信的)。然后就是设置 addAmIpFilter,当作业完成的时候,ExecutorLauncher 将通过
11、 amClient 设置 Application 的状态为FinalApplicationStatus.SUCCEEDED。7、分配 Executors,这里面的分配逻辑和 yarn-cluster 里面类似,就不再说了。8、最后,Task 将在 CoarseGrainedExecutorBackend 里面运行,然后运行状况会通过 Akka 通知 CoarseGrainedScheduler,直到作业运行完成。9、在作业运行的时候,YarnClientSchedulerBackend 会每隔 1 秒通过 client 获取到作业的运行状况,并打印出相应的运行信息,当 Application
12、的状态是FINISHED、FAILED 和 KILLED 中的一种,那么程序将退出等待。10、最后有个线程会再次确认 Application 的状态,当 Application 的状态是FINISHED、FAILED 和 KILLED 中的一种,程序就运行完成,并停止 SparkContext。整个过程就结束了。本博客文章除特别声明,全部都是原创!尊重原创,转载请注明: 转载自 过往记忆(http:/ Spark on YARN 客户端模式作业运行全过程分析 (http:/ Spark On Yarn 程序http:/ 2.2.0 + Scala 2.10.3 + Spark 0.9 + Id
13、ea 13单机伪分布式的 YarnIdea SBT 插件使用:建立 SBT 项目,然后在 Setting 中设置 SBT autoimport 和 auto 创建目录结构,ok 后 refreshbuild.sbtplain view plaincopyprint?1. name := “WordCount“ 2. 3. version := “1.0“ 4. 5. scalaVersion := “2.10.3“ 6. 7. libraryDependencies += “org.apache.spark“ % “spark-core“ % “0.9.0-incubating“ 8. 9.
14、resolvers += “Akka Repository“ at “http:/repo.akka.io/releases/“ 10. 11. libraryDependencies += “org.apache.spark“ % “spark-bagel_2.10“ % “0.9.0-incubating“ 12. 13. libraryDependencies += “org.apache.spark“ % “spark-mllib_2.10“ % “0.9.0-incubating“ 14. 15. libraryDependencies += “org.apache.spark“ %
15、 “spark-graphx_2.10“ % “0.9.0-incubating“ 16. 17. libraryDependencies += “org.apache.spark“ % “spark-streaming_2.10“ % “0.9.0-incubating“ 后面的那些依赖可以不要,Spark 自带的其他的 exapmle 中会用到CODEhtml view plaincopyprint?1. package myclass 2. 3. import org.apache.spark._ 4. import SparkContext._ 5. /* 6. * Created b
16、y jack on 2/22/14. 7. */ 8. object MyWordCount 9. def main(args: ArrayString) 10. /* 本地版本 11. val spark = new SparkContext(“local“,“my word count“,System.getenv(“SPARK_HOME“),SparkContext.jarOfClass(this.getClass) 12. 13. val file = spark.textFile(“src/main/resources/abc“) 14. val counts = file.flat
17、Map(line = line.split(“ “) 15. .map(word = (word, 1) 16. .reduceByKey(_ + _) 17. counts.saveAsTextFile(“src/main/resources/out“) 18. spark.stop()*/ 19. 20. / HDFS 版本 21. val spark = new SparkContext(“yarn-standalone“,“my word count“,System.getenv(“SPARK_HOME“),SparkContext.jarOfClass(this.getClass)
18、22. 23. val file = spark.textFile(“hdfs:/127.0.0.1:9000/user/jack/input“) 24. val wordcounts = file.flatMap(line = line.split(“ “).map(word = (word,1).reduceByKey(_+_) 25. wordcounts.saveAsTextFile(“hdfs:/127.0.0.1:9000/user/jack/myWordCountOutput“) 26. spark.stop() 27. 28. 第二个 import 至关重要,不然会出现 red
19、uceByKey 方法无法使用的情况单机版本可以直接在 Idea 下跑和调试,HDFS 版要打包为 jar 后在命令行执行run_spark_shell.sh执行脚本 跑起1. #!/bin/sh 2. SPARK_JAR=$SPARK_HOME/assembly/target/scala-2.10/spark-assembly_2.10-0.9.0-incubating-hadoop2.2.0.jar 3. $SPARK_HOME/bin/spark-class org.apache.spark.deploy.yarn.Client 4. -jar /home/jack/IdeaProjec
20、ts/Spark/WordCount/out/artifacts/mywordcount/mywordcount.jar 5. -class myclass.MyWordCount 6. -num-workers 1 7. -master-memory 512m 8. -worker-memory 1g 9. -worker-cores 1 KMeans on Sparkhttp:/ K 个聚类中心3.计算每个点所属的类别4.计算新的聚类中心5.比较聚类中心的变化情况,大于阈值跳转至 3;小于阈值停止。plain view plaincopyprint?1. package myclass 2
21、. 3. import java.util.Random 4. import org.apache.spark.SparkContext 5. import SparkContext._ 6. import org.apache.spark.util.Vector 7. /* 8. * Created by jack on 2/26/14. 9. */ 10. object MyKMeans 11. val N = 1000 12. val R = 1000 /随机数范围 0-1 * R 13. val D = 10 /点空间纬度 14. val K = 10 /聚类中心个数 15. val
22、rand = new Random(42) /随机种子 16. val convergeDist = 0.01 /迭代收敛条件 17. 18. /* 19. * 将 p 分配到当前所有聚类中心的最短距离的 类中 20. * */ 21. def closestPoint(p:Vector,centers: ArrayVector): Int = 22. var bestIndex = 0 23. var closest = Double.PositiveInfinity 24. 25. for (i rand.nextDouble * R) 42. 43. Array.tabulate(N)(
23、generatePoint) 44. 45. 46. def main(args: ArrayString) 47. val sc = new SparkContext(“local“,“My KMeans“,System.getenv(“SPARK_HOME“),SparkContext.jarOfClass(this.getClass) 48. val data = sc.parallelize(generateData).cache() 49. 50. /随机初始化 K 个聚类中心 51. val kPoints = data.takeSample(false,K,42).toArray
24、 52. var tempDist = 1.0 53. 54. while(tempDist convergeDist) 55. /closest为(类别,(点,1),1 是用来后续统计各个类中点的数量count 56. val closest = data.map(p = (closestPoint(p,kPoints),(p,1) 57. /按类别,计算点的坐标和,以及该类别中节点总数 (类别,(点向量和,点数) 58. val pointStats = closest.reduceByKey 59. case (x1,y1),(x2,y2) = (x1+x2,y1+y2) 60. 61.
25、 /生成新的聚类中心的 Map(类别,新聚类中心) 62. val newPoints = pointStats.map 63. pair = (pair._1, pair._2._1 / pair._2._2) 64. .collectAsMap() 65. 66. tempDist = 0.0 67. for (i val file = sc.textFile(“hdfs:/namenode1:9000/user/root/README.md“)scala val count = file.flatMap(line = line.split(“ “).map(word = (word, 1
26、).reduceByKey(_+_)scala count.collect()scala :quitSpark1.0.x 入门指南 (spark on yarn, standalone)http:/ 节点说明IP Role192.168.1.111 ActiveNameNode192.168.1.112 StandbyNameNode,Master,Worker192.168.1.113 DataNode,Master,Worker192.168.1.114 DataNode,WorkerHDFS 集群和 Spark 集群之间节点共用。2 安装 HDFS见 HDFS2.X 和 Hive 的安装
27、部署文档:http:/ Spark 部署Spark 常用的安装部署模式有 Spark On Yarn 和 Standalone,可以同时使用。3.1 Spark on Yarn这种模式,借助 Yarn 资源分配的功能,使用 Spark 客户端来向 Yarn 提交任务运行。只需将 Spark 的部署包放置到 Yarn 集群的某个节点上即可(或者是 Yarn 的客户端,能读取到 Yarn 集群的配置文件即可)。Spark 本身的 Worker 节点、Master 节点不需要启动。但是, Spark 的部署包须是基于对应的 Yarn 版本正确编译后的,否则会出现 Spark和 Yarn 的兼容性问题
28、。on Yarn 的两种运行方式,其运行结束后的日志不能在 Yarn 的 Application 管理界面看到,目前只能在客户端通过:yarn logs -applicationId 命令查看每个 Application 的日志。3.1.1 配置部署这种模式,需要修改 conf 目录下的 spark-env.sh 文件。在其中新增如下配置选项:export HADOOP_HOME= /home/hadoop/hadoop-2.0.0-cdh4.5.0export HADOOP_CONF_DIR= $HADOOP_HOME/etc/hadoopSPARK_EXECUTOR_INSTANCES=2
29、SPARK_EXECUTOR_CORES=1SPARK_EXECUTOR_MEMORY=400MSPARK_DRIVER_MEMORY=400MSPARK_YARN_APP_NAME=“Spark 1.0.0“其中:(1) HADOOP_HOME:当前节点中 HDFS 的部署路径,因为 Spark 需要和 HDFS 中的节点在一起;(2) HADOOP_CONF_DIR:HDFS 节点中的 conf 配置文件路径,正常情况下此目录为$HADOOP_HOME/etc/hadoop;(3) SPARK_EXECUTOR_INSTANCES:在 Yarn 集群中启动的 Worker 的数目,默认为2
30、 个;(4) SPARK_EXECUTOR_CORES:每个 Worker 所占用的 CPU 核的数目;(5) SPARK_EXECUTOR_MEMORY:每个 Worker 所占用的内存大小;(6) SPARK_DRIVER_MEMORY:Spark 应用程序 Application 所占的内存大小,这里的Driver 对应 Yarn 中的 ApplicationMaster;(7) SPARK_YARN_APP_NAME:Spark Application 在 Yarn 中的名字;配置完成后,将 Spark 部署文件放置到 Yarn 的节点中即可。这里,将 spark-1.0.0整个目录放
31、到 Yarn 集群的一个节点 192.168.1.112 的/home/hadoop(设为spark 的安装路径的父目录)路径下。3.1.2 测试在 Spark 的部署路径的 bin 路径下,执行 spark-submit 脚本来运行 spark-examples 包中的例子。执行如下:./bin/spark-submit -master yarn -class org.apache.spark.examples.JavaWordCount -executor-memory 400M -driver-memory 400M /home/hadoop/spark-1.0.0/examples/t
32、arget/scala-2.10/spark-examples-1.0.0-hadoop2.0.0-cdh4.5.0.jar ./hdfs-site.xml这个例子是计算 WordCount 的,例子被打包在/home/hadoop/spark-1.0.0/examples/target/scala-2.10/spark-examples-1.0.0-hadoop2.0.0-cdh4.5.0.jar 包中,对应的 Class 为org.apache.spark.examples.JavaWordCount,./hdfs-site.xml 是 HDFS 中指定路径下的一个文件,WordCount
33、 就是针对它来做的。而-master yarn 就是指定运行在Yarn 集群中,以 yarn 模式运行。Spark On Yarn 有两种运行模式,一种是 Yarn Cluster 方式,一种是 Yarn Client方式。(1) Yarn Cluster: Spark Driver 程序将作为一个 ApplicationMaster 在 YARN 集群中先启动,然后再由 ApplicationMaster 向 RM 申请资源启动 executor 以运行 Task。因为 Driver 程序在 Yarn 中运行,所以程序的运行结果不能在客户端显示,所以最好将结果保存在 HDFS 上,客户端的终
34、端显示的是作为 Yarn 的 job 的运行情况。(2) Yarn Client: Spark Driver 程序在客户端上运行,然后向 Yarn 申请运行 exeutor以运行 Task,本地程序负责最后的结果汇总等。客户端的 Driver 将应用提交给 Yarn 后,Yarn 会先后启动 ApplicationMaster 和 executor,另外 ApplicationMaster 和executor 都是装载在 container 里运行,container 默认的内存是1G, ApplicationMaster 分配的内存是 driver-memory,executor 分配的内存
35、是executor-memory。同时,因为 Driver 在客户端,所以程序的运行结果可以在客户端显示,Driver 以进程名为 SparkSubmit 的形式存在。上面命令中的提交方式“yarn”就是默认按照“Yarn Client”方式运行。用户可自定义运行方式,通过“-master”指定程序以 yarn、yarn-cluster 或者 yarn-client 中的一种方式运行。需要重点说明的是最后文件的路径,是相当于 HDFS 中的/user/hadoop 而言,hadoop 是当前命令的用户。“./hdfs-site.xml”在 HDFS 中的全路径为“hdfs:/namespace
36、/user/hadoop/hdfs-site.xml”,其中 hadoop 是当前的用户,namespace 是 HDFS 的命名空间;如果写成“/hdfs-site.xml”则在 HDFS 中指的是“hdfs:/namespace/hdfs-site.xml”;当然也可以直接传入“hdfs:/namespace/user/hadoop/hdfs-site.xml”用于指定在 HDFS 中的要进行 WordCount 计算的文件。另外, Spark 应用程序需要的 CPU Core 数目和内存,需要根据当前 Yarn 的NodeManager 的硬件条件相应设置,不能超过 NodeManage
37、r 的硬件条件。./bin/spark-submit -master yarn -class org.apache.spark.examples.JavaWordCount -executor-memory 400M -driver-memory 400M /home/hadoop/spark-1.0.0/examples/target/scala-2.10/spark-examples-1.0.0-hadoop2.0.0-cdh4.5.0.jar hdfs:/namespace/user/hadoop/hdfs-site.xml在 Yarn 的 ResourceManager 对应的 Web
38、 界面中查看启动的 Application。Running:Success:同时可以在启动脚本的客户端看到 WordCount 的运行结果:3.2 Spark Standalone这种模式,就是把 Spark 单独作为一个集群来进行部署。集群中有两种节点,一种是Master,另一种是 Worker 节点。Master 负责分配任务给 Worker 节点来执行,并负责最后的结果合并,Worker 节点负责具体的任务执行。3.2.1 配置所需修改的配置文件除了 spark-env.sh 文件以外,还有 slave 文件,都位于 conf 目录中。slave 文件中保存的是 worker 节点 ho
39、st 或者 IP,此处的配置为:192.168.1.112192.168.1.113192.168.1.114至于 spark-env.sh 文件,可以配置如下属性:(1) SPARK_MASTER_PORT:Master 服务端口,默认为 7077;(2) SPARK_WORKER_CORES:每个 Worker 进程所需要的 CPU 核的数目;(3) SPARK_WORKER_MEMORY:每个 Worker 进程所需要的内存大小;(4) SPARK_WORKER_INSTANCES:每个 Worker 节点上运行 Worker 进程的数目;(5) SPARK_MASTER_WEBUI_P
40、ORT:Master 节点对应 Web 服务的端口;(6)export SPARK_DAEMON_JAVA_OPTS=“-Dspark.deploy.recoveryMode=ZOOKEEPER -Dspark.deploy.zookeeper.url=192.168.1.117:2181,192.168.1.118:2181,192.168.1.119:2181 -Dspark.deploy.zookeeper.dir=/spark“:用于指定 Master 的HA,依赖于 zookeeper 集群;(7) export SPARK_JAVA_OPTS=“-Dspark.cores.max=
41、4“:用于限定每个提交的Spark Application 的使用的 CPU 核的数目,因为缺省情况下提交的 Application 会使用所有集群中剩余的 CPU Core。注意在 Worker 进程的 CPU 个数和内存大小的时候,要结合机器的实际硬件条件,如果一个 Worker 节点上的所有 Worker 进程需要的 CPU 总数目或者内存大小超过当前Worker 节点的硬件条件,则 Worker 进程会启动失败。将配置好的 Spark 文件拷贝至每个 Spark 集群的节点上的相同路径中。为方便使用spark-shell,可以在环境变量中配置上 SPARK_HOME。3.2.2 启动配
42、置结束后,就该启动集群了。这里使用 Master 的 HA 方式,选取192.168.1.112、192.168.1.113 节点作为Master,192.168.1.112 、192.168.1.113、192.168.1.114 节点上运行两个Worker 进程。首先在 192.168.1.113 节点上做此操作:启动之后,可以查看当前节点的进程:另外,为了保证 Master 的 HA,在 192.168.1.112 节点上只启动 Master:192.168.1.112 节点的进程为:启动过后,通过 Web 页面查看集群的情况,这里访问的是:http:/192.168.1.113:8090/再看 standby 节点 192.168.1.112 的 web 界面 http:/192.168.1.112:8090/