流计算是进行实时计算,作业启动后会一直运行,没有止境,除非手动停止
最有名的流计算产品:
storm:逐行或个批次(如100行)进行处理,批次指的是行
spark:即streaming模块,按时间片段批次处理,批次指的是时间段
sparkstreaming当数据量非常大的时候不建议小于30秒一个批次,负载会特别大,这点和storm是完全不同的。
开发难度上storm难一些,spark简单,因为spark更注重封装。
场景上spark离线计算实时计算都可以,storm就是实时计算
dstream是sparkstreaming里面数据的封装
storm里面是tuple
dstream也是一个rdd,sparkstreaming使用离散化流(discretized stream)作为抽象表示,dstream是随时间推移而收到的数据的序列
每个时间区间收到的数据都作为rdd存在,而dstream是由这些rdd所组成的序列。
每个粒度:微小时间片段的rdd
dstream:是这些rdd的序列
dstream支持两种操作,一种是转化操作,会生成一个新的dstream,另一种是输出操作,可以把数据写入外部系统中
dstream提供了很多与rdd作支持的相同操作相类似的操作支持,还增加了与时间相关的操作,比如滑动窗口
数据源的设计:
dstream可以从各种输入源创建,如kafka,flume,hdfs文件,socket等
架构设计中,如何做到最稳健:不丢数据,稳定性高
作业的维护:作业有需求变更优化,所以必须有重启维护,要做到不丢数据,而且不重复读数据,这个条件要能满足,文件源不行,socket也不行(你重启后,重启过程中产生的数据就丢失了),flume不行(它从它的数据实时拿数据,但你从flume里面实时拿数据,你记录不了它的数据,重启还是会数据丢失),而做的最好的是kafka。
kafka内部可以最小限度避免数据丢失,它内部会维护消费位置offset是一秒更新一次,所以无法避免一行不丢,但kafka可以尽可能避免!
所以企业里面最稳健的架构师kafka作数据源,消费端可以是sparkstreaming或者是storm。
如果公司的数据源是文件,或socket,乙方公司是控制不了数据源的,进行实时计算时,通常用flume来接受数据。
然而sparkstorm读flume是不稳键的,如何解决,一个好的方式是让flume写kafka,再接sparkstreaming/storm
如果是甲方公司,能控制数据源的架构设计的话,通常不用flume,因为没必要,而且flume稳定性也不好。
架构原理:
sparkstreaming使用“微批次”的架构,把流计算当作一系列连续的小规模批处理来对待,sparkstreaming从输入源中读数据,并把数据分组为小的批次。新的批次按均匀的时间间隔创建出来。每个批次里的数据行数是不相等的。
在每个时间区间开始的时候,一个新的批次就创建出来,在该区间内收到的数据都会被添加到这个批次中,在时间区间结束时,批次停止增长。
时间区间的大小是由批次间隔这个参数决定的。批次间隔一般设在500毫秒到几秒之间,有应用开发者配置。这个是数据量比较小的时候,数据量大的时候,比如一天1亿行级别,延迟建议不小于30秒。
sparkstreaming为每个输入源启动对应的接收器,接收器以任务的形式运行在应用的工作节点执行器进程中,把输入源手机数据并保存为rdd,它们收集到输入数据后会把数据复制到另一个执行器进程保障容错性(默认行为)
数据保存在执行器进程的内存中,和缓存rdd的方式一样,驱动器程序中的streamingcontext会周期性地运行spark作业来处理这些数据,把数据与之前时间区间的rdd进行整合
另外dstream还有“有状态”的转换操作,可以用来聚合不同时间片内的数据。