zoukankan      html  css  js  c++  java
  • 面试总结(1)

    项目中flume的source用的什么?为什么?

    大数据实时处理项目中用taildir作为source,因为Taildir Source可实时监控一批文件,并记录每个文件最新消费位置,agent进程重启后不会有重复消费的问题。flume1.7出来后,将flume进行了升级,升级了主要原因是TailDirSouce,KafkaChannel,但是TailDirSource不能递归发现文件,从github参考了一些代码,对TailDirSouce进行了升级。可以监控递归文件。

    Spooling Directory Source可监听一个目录,同步目录中的新文件到sink,被同步完的文件可被立即删除或被打上标记。适合用于同步新文件,但不适合对实时追加日志的文件进行监听并同步。如果需要实时监听追加内容的文件,可对SpoolDirectorySource进行改进。

    Exec Source可通过tail -f命令去tail住一个文件,然后实时同步日志到sink。但存在的问题是,当agent进程挂掉重启后,会有重复消费的问题。可以通过增加UUID来解决,或通过改进ExecSource来解决。

    项目中flume的channel用的什么?为什么?

    项目中用kafka channel。 原因: File Channel是一个持久化的隧道(channel),他持久化所有的事件,并将其存储到磁盘中。因此,即使Java 虚拟机当掉,或者操作系统崩溃或重启,再或者事件没有在管道中成功地传递到下一个代理(agent),这一切都不会造成数据丢失。Memory Channel是一个不稳定的隧道,其原因是由于它在内存中存储所有事件。如果java进程死掉,任何存储在内存的事件将会丢失。另外,内存的空间收到RAM大小的限制,而File Channel这方面是它的优势,只要磁盘空间足够,它就可以将所有事件数据存储到磁盘上,但是比较慢。

    kafka channel总和了以上两者的优点,events存储在Kafka集群中。Kafka提供高可用性和高可靠性,所以当agent或者kafka broker 崩溃时,events能马上被其他sinks可用。

    如何解决实时系统中flume存储到hdfs时产生的小文件?

    hdfs sink需要注意其roll的时机,目前影响roll时机的几个参数“minBlockReplicas”、“rollInterval”(根据时间间隔)、“rollSize”(根据文件尺寸)、“rollCount”(根据event条数);此外“round”相关的选项也可以干预滚动生成新文件的时机。 flume每次flush都将生成一个新的hdfs文件,最终导致生成很多小文件,我希望一个tail的文件最终在hdfs中也是一个文件;后来经过考虑,使用基于rollSize来滚动生成文件,通常本人的nginx日志文件不超过1G,那么我就让rollSize设置为1G,这样就可以确保不会roll。此外,hdfs每个文件都会有一个“数字”后缀,这个数字是一个内部的counter,目前没有办法通过配置的方式来“消除”。

    使用sparkstreaming时,如果实时计算结果要写入到HDFS,那么不可避免的会遇到一个问题,那就是在默认情况下会产生非常多的小文件,这是由sparkstreaming的微批处理模式和DStream(RDD)的分布式(partition)特性导致的,sparkstreaming为每个partition启动一个独立的线程来处理数据,一旦文件输出到HDFS,那么这个文件流就关闭了,再来一个batch的parttition任务,就再使用一个新的文件流,那么假设,一个batch为10s,每个输出的DStream有32个partition,那么一个小时产生的文件数将会达到(3600/10)*32=11520个之多。众多小文件带来的结果是有大量的文件元信息,比如文件的location、文件大小、block number等需要NameNode来维护,NameNode会因此鸭梨山大。不管是什么格式的文件,parquet、text,、JSON或者 Avro,都会遇到这种小文件问题,这里讨论几种处理Sparkstreaming小文件的典型方法。

    增加batch大小 这种方法很容易理解,batch越大,从外部接收的event就越多,内存积累的数据也就越多,那么输出的文件数也就回变少,比如上边的时间从10s增加为100s,那么一个小时的文件数量就会减少到1152个。但别高兴太早,实时业务能等那么久吗,本来人家10s看到结果更新一次,现在要等快两分钟,是人都会骂娘。所以这种方法适用的场景是消息实时到达,但不想挤压在一起处理,因为挤压在一起处理的话,批处理任务在干等,这时就可以采用这种方法(是不是很像spark内部的pipeline模式,但是要注意区别哦)。

    Coalesce大法好? 文章开头讲了,小文件的基数是:batchnumber*partitionnumber,而第一种方法是减少batchnumber,那么这种方法就是减少partitionnumber了,这个api不细说,就是减少初始的分区个数。看过spark源码的童鞋都知道,对于窄依赖,一个子RDD的partition规则继承父RDD,对于宽依赖(就是那些个叉叉叉ByKey操作),如果没有特殊指定分区个数,也继承自父rdd。那么初始的SourceDstream是几个partiion,最终的输出就是几个partition。所以Coalesce大法的好处就是,可以在最终要输出的时候,来减少一把partition个数。但是这个方法的缺点也很明显,本来是32个线程在写256M数据,现在可能变成了4个线程在写256M数据,而没有写完成这256M数据,这个batch是不算做结束的。那么一个batch的处理时延必定增长,batch挤压会逐渐增大。这种方法也要慎用,切鸡切鸡啊!

    SparkStreaming外部来处理 我们既然把数据输出到hdfs,那么说明肯定是要用hive或者sparksql这样的“sql on hadoop”系统类进一步进行数据分析,而这些表一般都是按照半小时或者一小时、一天,这样来分区的(注意不要和sparkStreaming的分区混淆,这里的分区,是用来做分区裁剪优化的),那么我们可以考虑在SparkStreaming外再启动定时的批处理任务来合并SparkStreaming产生的小文件。这种方法不是很直接,但是却比较有用,“性价比”较高,唯一要注意的是,批处理的合并任务在时间切割上要把握好,搞不好就可能回去合并一个还在写入的SparkStreaming小文件。

    自己调用foreach去append SparkStreaming提供的foreach这个outout类api,可以让我们自定义输出计算结果的方法。那么我们其实也可以利用这个特性,那就是每个batch在要写文件时,并不是去生成一个新的文件流,而是把之前的文件打开。考虑这种方法的可行性,首先,HDFS上的文件不支持修改,但是很多都支持追加,那么每个batch的每个partition就对应一个输出文件,每次都去追加这个partition对应的输出文件,这样也可以实现减少文件数量的目的。这种方法要注意的就是不能无限制的追加,当判断一个文件已经达到某一个阈值时,就要产生一个新的文件进行追加了。

    spark集群的管理是什么模式?

    yarn模式 如果你只是测试Spark Application,你可以选择local模式。而如果你数据量不是很多,Standalone 是个不错的选择。当你需要统一管理集群资源(Hadoop、Spark等),那么你可以选择Yarn或者mesos,但是这样维护成本就会变高。 如果你同时运行hadoop和Spark,从兼容性上考虑,Yarn是更好的选择。

    spark默认的存储文件格式?

    parquet。 可以跳过不符合条件的数据,只读取需要的数据,降低IO数据量。 压缩编码可以降低磁盘存储空间。由于同一列的数据类型是一样的,可以使用更高效的压缩编码(例如RunLength Encoding和Delta Encoding)进一步节约存储空间。 只读取需要的列,支持向量运算,能够获取更好的扫描性能。 spark天然支持parquet,并为其推荐的存储格式(默认存储为parquet)。 hive 支持parquet格式存储,如果以后使用hiveql 进行查询,也完全兼容。

    加入:原始日志大小为214G左右,120+字段

    采用csv(非压缩模式)几乎没有压缩。

    采用parquet 非压缩模式、gzip、snappy格式压缩后分别为17.4G、8.0G、11G,达到的压缩比分别是:12、27、19。

    若我们在hdfs上存储3份,压缩比仍达到4、9、6倍

    parquet的gzip的压缩比率最高,若不考虑备份可以达到27倍。 分区过滤和列修剪可以帮助我们大幅节省磁盘IO。以减轻对服务器的压力。 如果你的数据字段非常多,但实际应用中,每个业务仅读取其中少量字段,parquet将是一个非常好的选择。 spark在这里选择了用snappy的压缩方式压缩成parquet文件作为默认策略。

    spark.sql.parquet.compression.codec:默认snappy。 Acceptable values include: none, uncompressed, snappy, gzip, lzo.

    使用背压机制,设置的背压条数是多少?

    Direct模式需要结合控量功能使用,比如可以设置控量值是“最优量”(计算批次内数据所用时间尽可能的接近但又一直低于批次调度间隔时间)的1到2倍,这样第一批次摄入的数据量是saprk.streaming.kafka.maxRatePerPartition的值,紧接着几批会因为第一批次处理延迟而依旧采用控量值为摄入量,直到第一个批次运算完,后续批次才会触发背压机制自动优化摄入量,但最大上限还是saprk.streaming.kafka.maxRatePerPartition的值。

    spark的结构化流?

    结构化流(Structured Streaming),是一种基于Spark-SQL引擎构建的,可容错的,可扩展的流处理引擎.

    它以微批量计算的形式来表达流式计算,随着流式数据持续到达,它能持续的进行处理并更新最终计算结果.

    它使用Spark-SQL带来的丰富的API,来表示流聚合(streaming aggregations),事件时间窗口( event-time windows),流到批处理连接(stream-to-batch joins)等,最终在同一个引擎(优化的Spark-SQL引擎)执行.

    并且,系统能以检查点(CheckPoint)和预写日志(Write Ahead Logs),来确保端到端的(end-to-end)有且仅有一次(exactly-once)的容错保证.

    它的微批处理机制,可以将端到端的延迟降低到100毫秒以下,而在2.3版本中,新提供了一种连续处理(Continuous Processing)机制,将这种端到端的延迟进一步降低到1毫秒以内

    简单来说,结构化流提供一种快速的,可容错的,可扩展的,端到端有且仅有一次保证的流式处理方案。

    结构化流是Spark2.X时代提出的新一代流式计算框架.

    它相当于Streaming的增强版,从就旧的来说,它可以完全覆盖Streaming的功能,从新的来说,它还具有以下的演进:

    Streaming是按时间分片为DStream,这导致Streaming很难基于event-time,来处理数据延时,甚至数据乱序的情况.而结果化流是视为一个无界DataFrame,输出结果映射为另一张表.天然支持乱序情况.

    流式(使用RDD)和批处理(使用Spark-SQL)API不能保持完全兼容,程序代码需要做一些转换才行

    端到端的保障机制由用户维护,难以处理增量更新和持久化存储一致的问题。

    结构化流的核心思想是时间分片,是将实时数据流,视为一个不断增加(append)的表.这让它与普通的批处理非常类似

    但是,结构化流不实现整个表.它读取最新的可用数据流数据来源,处理结果逐步更新,然后丢弃的源数据.只保持在所需的最少的中间状态的数据更新结果。

    基于事件时间处理数据延迟:

    因为时间分片的机制,时间属性就是一个非常重要的属性.结构化流支持基于事件时间(Event-time)来处理.

    事件时间是嵌入在数据本身中.很多的时候,都需要基于事件时间而不是结构化流接受时间来处理.比如某些情况下,一部分数据到达出现延迟

    容错机制:

    端到端的有且仅有一次保证,是结构化流设计的关键目标之一.

    结构化流设计了 Structured Streaming sources,sinks等等,来跟踪确切的处理进度,并让其重启或重运行来处理任何故障

    streaming source是类似kafka的偏移量(offsets)来跟踪流的读取位置.执行引擎使用检查点(checkpoint)和预写日志(write ahead logs)来记录每个执行其的偏移范围值

    streaming sinks 是设计用来保证处理的幂等性

    这样,依靠可回放的数据源(streaming source)和处理幂等(streaming sinks),结构流来做到任何故障下的端到端的有且仅有一次保证   

  • 相关阅读:
    tiny4412 串口驱动分析八 --- log打印的几个阶段之内核启动阶段(printk tiny4412串口驱动的注册)
    tiny4412 串口驱动分析七 --- log打印的几个阶段之内核启动阶段(earlyprintk)
    tiny4412 串口驱动分析六 --- TTY驱动架构
    Android简单的利用SoundPool进行播放铃声的实例代码
    Android简单的利用MediaRecorder进行录音的实例代码
    tiny4412 串口驱动分析五 --- LDD3上TTY驱动程序源码
    tiny4412 串口驱动分析四 --- 修改默认的串口输出
    tiny4412 串口驱动分析三 --- log打印的几个阶段之内核自解压
    tiny4412 串口驱动分析二 --- printk的实现
    tiny4412 串口驱动分析一 --- u-boot中的串口驱动
  • 原文地址:https://www.cnblogs.com/fredkeke/p/9502803.html
Copyright © 2011-2022 走看看