sparkStreaming

目录

核心概念

DStream

Receiver

Transformation

Output Operation

IDEA搭建SparkStreaming环境的pom文件

带状态的算子:UpdateStateByKey

基于window的统计


核心概念

SparkStreaming可以简单的理解为 StreamingContext将数据按照时间分为很多小的RDD,然后再交给Spark处理这一个个的RDD。

DStream

对DStream做操作,其实质就是对一系列的RDD做相同的操作。 

Receiver

每一个inputDStream【除了文件流】 关联一个 Receiver对象【负责接受源头的数据并存储在spark的内存中】

注意:Receiver启动会占用一个线程,所以这时候不能使用master("local[1]")

Transformation

    map(func)、filter(func)、flatMap(func)、reductByKey(func, [numTasks])

    注意:流式计算中,reduce(func)、count()都是Transformation,统计出source DStream中的每个微批RDD的聚合结果和个数。

Output Operation

 

IDEA搭建SparkStreaming环境的pom文件



  4.0.0

  com.kylin.sparkstreaming
  sparkstreaming
  1.0-SNAPSHOT
  
    UTF-8
    2.2.3
    2.11
    2.7.6
    1.4.8
    1.1.1
  
  
    
      org.scala-lang
      scala-library
      2.11.12
    
    
      org.apache.spark
      spark-core_${scala.version}
      ${spark.version}
    
    
      org.apache.spark
      spark-sql_${scala.version}
      ${spark.version}
    
    
      org.apache.spark
      spark-hive_${scala.version}
      ${spark.version}
    
    
      org.apache.spark
      spark-streaming_${scala.version}
      ${spark.version}
    
    
      org.apache.hadoop
      hadoop-client
      2.7.6
    
    
      org.apache.hbase
      hbase-client
      ${hbase.version}
    
    
      org.apache.hbase
      hbase-server
      ${hbase.version}
    
    
    
      org.apache.spark
      spark-streaming-kafka-0-8_${scala.version}
      ${spark.version}
    
    
      
      
      
    
    
      org.apache.kafka
      kafka_2.11
      ${kafka.version}
    
    
      mysql
      mysql-connector-java
      5.1.41
    
    
      junit
      junit
      4.12
    
  

  
  
    
      central
      Maven Repository Switchboard
      default
      http://repo2.maven.org/maven2
      
        false
      
    
  

  
    src/main/scala
    src/test/scala

    
      
        
        org.scala-tools
        maven-scala-plugin
        2.15.2
        
          
            
              compile
              testCompile
            
          
        
      

      
        
        org.apache.maven.plugins
        maven-compiler-plugin
        3.3
        
          1.8
          1.8
          UTF-8
        
      
    
  

测试代码如下:

object FileWordCount {
  def main(args: Array[String]): Unit = {
    // 必须使用流的形式,才能读取到文件内容,如果windows下直接拷贝粘贴是不行的
    // cp 123.txt data/   而且对同一个文件修改也是不会再次被读取到的
    val sparkConf = new SparkConf().setMaster("local[2]").setAppName("file_word_count")
    val ssc = new StreamingContext(sparkConf, Seconds(5))
    val lines = ssc.textFileStream("file:///G:\\data\\")
    val result = lines.flatMap(_.split(" ")).map((_, 1)).reduceByKey(_ + _)
    result.print()

    ssc.start()
    ssc.awaitTermination()
  }
}

带状态的算子:UpdateStateByKey

需求:统计到目前为止累计出现的单词数量。

注意:

  1. updateStateByKey算子需要传入一个函数【输入:当前值、以前值 】
  2. 以前的状态必须存放在checkpoint指定的路径。
object StatefulFileWordCount {
  def main(args: Array[String]): Unit = {
    val sparkConf = new SparkConf().setMaster("local[2]").setAppName("file_word_count")
    val ssc = new StreamingContext(sparkConf, Seconds(5))
    // 如果使用了带状态的算子,必须设置checkpoint存放以前的状态
    ssc.checkpoint(".")

    val lines = ssc.textFileStream("file:///G:/data")
    val result = lines.flatMap(_.split(" ")).map((_, 1))
    val state = result.updateStateByKey(updateFunction _) // 隐式转换
    state.print()

    ssc.start()
    ssc.awaitTermination()
  }

  def updateFunction(currentValues: Seq[Int], preValues: Option[Int]):Option[Int] = {
    val current = currentValues.sum
    val pre = preValues.getOrElse(0)
    Some(current + pre)
  }
}

进阶:将单词数量统计写入MySQL中

思路:使用 foreachRDD算子,

 

基于window的统计

window:进行一个时间段内的数据处理。   与 window length和sliding interval2个参数有关。

举例:每个10秒计算前10分钟的wordcount,此处sliding interval是10秒,window length是10分钟。

 

RDD和DStream进行join

通过 DStream的transform(rdd=>{  rdd.leftjoin(RDD) })

举例:黑名单过滤,一般黑名单存在数据库中,通过外部数据源可以得到一个静态的RDD,此处我们直接存到内存中,方便试验。blacksRDD通过map将里面的每个记录后面添加一个true,每次通过DStream中的rdd和blacksRDD进行左外连接,通过过滤出是false,即可过滤掉黑名单,只显示除了黑名单之外的人。

import org.apache.spark.SparkConf
import org.apache.spark.streaming.{Seconds, StreamingContext}

object TransformApp {
  // 测试是必须通过cp命令或mv命令才可以,往文件中追加内容是不行的
  def main(args: Array[String]): Unit = {
    val sparkConf = new SparkConf().setMaster("local[2]").setAppName("transform")
    val ssc = new StreamingContext(sparkConf, Seconds(5))
    // 构建黑名单 一般是从数据库得到 此处简化为存在内存中
    // blacksRDD : [<"zs" :true>, <"ls" :true>]
    val blacks = List("zs", "ls")
    val blacksRDD = ssc.sparkContext.parallelize(blacks).map(x => (x, true))

    val lines = ssc.textFileStream("file:///G:/data/test")
    // 每一行数据格式:20180502,zs,20 --> 
    val clicklog = lines.map(x => (x.split(",")(1), x))
      .transform(rdd => {
        rdd.leftOuterJoin(blacksRDD)
          .filter(x => x._2._2.getOrElse(false) != true)
          .map(x => x._2._1)
      })
    clicklog.print()

    ssc.start()
    ssc.awaitTermination()
  }
}

Sparkstreaming整合SparkSQL

foreachRDD算子中func的入参是一个一个小的rdd,每个rdd即可转换为DataFrame

 sparkStreaming_第1张图片

 

你可能感兴趣的:(数据仓库)