17 June 2015
因緣際會下,得稍微摸一下Apache Spark,
說實在,在粗淺地摸完Spark以後,我還是想不太出他的應用面。
Anyway,這篇主要分為3個section,

  • 如何安裝Spark
  • 如何使用
  • 如何寫個Spark application


1. Install JDK

首先要先講安裝,
安裝spark之前,要先安裝java+scala,
apt-add-repository ppa:webupd8team/java
apt-get update
apt-get install oracle-java7-installer

2. Install scala

接著要安裝scala,這裡安裝的版本是2.11.6。
wget http://www.scala-lang.org/files/archive/scala-2.11.6.tgz
mkdir /usr/local/src/scala
tar xvf scala-2.11.6.tgz -C /usr/local/src/scala/

安裝完以後,要把scala的路徑加入到PATH環境變數中
echo "export SCALA_HOME=/usr/local/src/scala/scala-2.11.6" >> .bashrc
echo "export PATH=\$SCALA_HOME/bin:\$PATH" >> .bashrc
. .bashrc

3. Install Spark

最後就安裝spark,安裝會需要一段時間。
wget http://www.apache.org/dist/spark/spark-1.4.0/spark-1.4.0.tgz
tar xvf spark-1.4.0.tgz
cd spark-1.4.0
sbt/sbt assembly

4. Spark Interactive Shell

安裝完以後,可以進入spark的interactive shell模式做個簡單的測試,
進入interactive mode,
./bin/spark-shell

大概會花個10秒做init,進入以後,
會看到scala的prompt字樣,這裏就可以對spark進行操作了。
下面有二個例子,都是對README.md去做操作,
分別為找出含"apache"的句子,
以及找出有幾個"apache"的字。
scala> val textFile = sc.textFile("README.md")
scala> textFile.count()
scala> val results = textFile.filter(line => line.contains("apache")) // search apache
scala> results.count()
scala> results.collect() // find out those lines contain apache

5. Start a Spark cluster

好了,剛剛都是自爽模式,
接著我們要啟動一個spark cluster,
這個cluster可以讓很多個worker(slave)加入,
讓他們去執行工作。

啟動cluster的指令如下:
./sbin/start-master.sh

啟動完以後,你可以用netstat -tnlp去看一下,
你會發現有3個java bind住的connection,
預設分別為7077、8080、6066
7077就是這個cluster的port,將來worker要加入就得指定這個port,
8080是這個spark的web management UI。
所以你就可以打開browser,然後去看看web UI.
這時候你的worker數量應該是0。
如果想要加入一個worker,得透過下面的指令,
./sbin/start-slave.sh spark://ubuntu:7077 # change ubuntu to your hostname

此時再去web UI看,應該就看到有一個worker存在。
上面是透過二個指令去分別啟動master and slave,
其實你也可以透過下面一個指令就去啟動master, slave,
./sbin/start-all.sh

6. Connecting an Application to the Cluster

有了一個spark cluster以後,
我們就可以把application掛上去,
我們可以透過前面使用的spark-shell,把這個shell run在cluster上。
只要加入--master這參數即可。
./bin/spark-shell --master spark://ubuntu:7077 # change ubuntu to your hostname

進去以後,你一樣可以執行上面的example玩玩看。
同時你也可以去web UI上看看,會在"Running Applications"裡面看到這個shell。

7. Writing an Application

上一步也算是自爽模式,
我想應該不可能透過shell mode去做你想做的事情,
應該還是要寫個application,
所以這一步驟就是要寫一個很簡單的classs,
然後build它,再把它掛到cluster上執行。

開始之前,先來設定一下spark的環境變數,
echo "export SK_HOME=/root/spark-1.4.0" >> .bashrc
. .bashrc

然後改這隻script,($SK_HOME/build/sbt-launch-lib.bash)
因為我在build的時候,有發生路徑的問題。
vim $SK_HOME/build/sbt-launch-lib.bash

打開這檔案以後,找到這幾行,
SBT_VERSION=`awk -F "=" '/sbt\.version/ {print $2}' ./project/build.properties`
...
JAR=build/sbt-launch-${SBT_VERSION}.jar
換成下面這幾行,其實也只是變成絕對路徑。
SBT_VERSION=`awk -F "=" '/sbt\.version/ {print $2}' $SK_HOME/project/build.properties`
...
JAR=$SK_HOME/build/sbt-launch-${SBT_VERSION}.jar

完成以後,先來create幾個資料夾,
mkdir -p ./spark-app/src/main/scala/

接著就可以寫一個簡單的class,
這class上面差不多,也是用來算count,
記得該class一定要放置在src/main/scala底下。
cd ./spark-app
vim src/main/scala/SimpleApp.scala

class內容如下,
/* SimpleApp.scala */
import org.apache.spark.SparkContext
import org.apache.spark.SparkContext._
import org.apache.spark.SparkConf

object SimpleApp {
def main(args: Array[String]) {
val logFile = "/root/spark-1.4.0/README.md"
val conf = new SparkConf().setAppName("Simple Application")
val sc = new SparkContext(conf)
val logData = sc.textFile(logFile, 2).cache()
val numApache = logData.filter(line => line.contains("apache")).count()
println("Line with apache: %s ".format(numApache))
}
}

而在開始build之前,要寫一下這個app的dependency,
放置在sparka-app底下就好。
vim simple.sbt

內容如下,
name := "Simple Project"

version := "1.0"

scalaVersion := "2.11.6"

libraryDependencies += "org.apache.spark" %% "spark-core" % "1.4.0"

接著就可以開始build,
$SPARK_HOME/build/sbt package


build完以後,
會發現spark-app底下多了二個folder(project, target),
而我們要的jar檔會放在target底下,
我們就可以把這jar交付給spark執行。
$SPARK_HOME/bin/spark-submit --class "SimpleApp" --master spark://ubuntu:7077 target/scala-2.11/simple-project_2.11-1.0.jar

應該會看到下面的字樣,
Line with apache: 9 15/06/17 02:55:34 INFO TaskSetManager: Finished task 1.0 in stage 2.0 (TID 5) in 32 ms on 172.16.131.140 (2/2)

最後在web UI裡面的"Completed Applications"會看到我們剛剛執行的那個item。
基本上這樣就完成了簡單的spark application。






blog comments powered by Disqus