flume--03-flume读取web应用某个文件夹下日志到hdfs
2017-09-07 13:14
591 查看
简介
这里主要是做这个实验遇到的问题以及解决方法问题:java.lang.OutOfMemoryError: GC overhead limit exceeded
1.准备工作
我本来想用已经写过的一个项目,那个项目是springboot写的,里面有log4j轮转日志,把日志写到一个文件夹里,我想的是flume把这些日志读取到hdfs上和hbase中,但是部署错误,因此我想个方法,本地建立一个文件夹,手动往里面放一些有格式的数据文件。文件内容如下
字段 | hotel | | | | h_id | id | | | h_region | 旅馆行政区划 | | | h_hname | 旅馆名称 | | | h_address | 旅馆地址 | | | h_uname | 姓名 | | | h_code | 证件号码 | | | h_start | 开房时间 | | | h_end | 退房时间 | | | h_start | 开房时间时间戳 | | | h_end | 退房时间时间戳 | | | h_homecode | 入住房号 | 数据样式 1,2,宾馆642,杭州市下城区xx484路373号,姓名65,U104,2006/06/23 00:00:00,2006/06/23 00:03:00,1150992000000,1150992180000,495 2,8,宾馆29,杭州市余杭区xx866路927号,姓名64,U193,2006/06/24 00:00:00,2006/06/24 00:16:00,1151078400000,1151079360000,376 3,8,宾馆190,杭州市余杭区xx81路801号,姓名56,U149,2006/06/24 00:00:00,2006/06/24 00:10:00,1151078400000,1151079000000,67 4,8,宾馆771,杭州市余杭区xx570路341号,姓名60,U870,2006/06/25 00:00:00,2006/06/25 00:06:00,1151164800000,1151165160000,761 5,1,宾馆584,杭州市上城区xx177路847号,姓名13,U552,2006/06/26 00:00:00,2006/06/26 00:09:00,1151251200000,1151251740000,583 6,5,宾馆375,杭州市西湖区xx532路372号,姓名93,U362,2006/06/27 00:00:00,2006/06/27 00:01:00,1151337600000,1151337660000,470 7,0,宾馆853,杭州市其他区xx390路777号,姓名65,U818,2006/06/28 00:00:00,2006/06/28 00:13:00,1151424000000,1151424780000,687 8,6,宾馆181,杭州市滨江区xx861路709号,姓名59,U625,2006/06/29 00:00:00,2006/06/29 00:00:00,1151510400000,1151510400000,573 9,2,宾馆813,杭州市下城区xx959路867号,姓名74,U431,2006/06/29 00:00:00,2006/06/29 00:07:00,1151510400000,1151510820000,58 10,2,宾馆771,杭州市下城区xx371路967号,姓名47,U410,2006/06/30 00:00:00,2006/06/30 00:01:00,1151596800000,1151596860000,268 11,2,宾馆803,杭州市下城区xx62路969号,姓名27,U182,2006/07/01 00:00:00,2006/07/01 00:04:00,1151683200000,1151683440000,141 12,7,宾馆838,杭州市萧山区xx418路194号,姓名2,U984,2006/07/01 00:00:00,2006/07/01 00:19:00,1151683200000,1151684340000,684 13,7,宾馆596,杭州市萧山区xx669路289号,姓名80,U819,2006/07/02 00:00:00,2006/07/02 00:19:00,1151769600000,1151770740000,305 14,3,宾馆110,杭州市拱墅区xx544路718号,姓名82,U955,2006/07/02 00:00:00,2006/07/02 00:06:00,1151769600000,1151769960000,1
在本地建立文件夹
/opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive
2.测试读取文件到hdfs上
编写flume的配置文件vim spool_dir_hdfs.conf #设置客户端是agent1 #source的名称是lcc_local_txt_source1,通道(缓冲器)名称lcc_memory_channel,sink的名称为lcc_sink1 agent1.sources = lcc_local_txt_source1 agent1.channels = lcc_memory_channel agent1.sinks = lcc_sink1 ###################设置source数据源################################# agent1.sources.lcc_local_txt_source1.type = spooldir agent1.sources.lcc_local_txt_source1.channels = lcc_memory_channel agent1.sources.lcc_local_txt_source1.spoolDir = /opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive agent1.sources.lcc_local_txt_source1.fileHeader = true ###################设置channel的属性################################# agent1.channels.lcc_memory_channel.type = memory agent1.channels.lcc_memory_channel.capacity = 100000 agent1.channels.lcc_memory_channel.transactionCapacity = 100000 agent1.channels.lcc_memory_channel.keep-alive = 30 ###################设置sink要输出到哪里################################# # Define a logger sink that simply logs all events it receives # and connect it to the other end of the same channel. agent1.sinks.lcc_sink1.channel = lcc_memory_channel agent1.sinks.lcc_sink1.type = hdfs agent1.sinks.lcc_sink1.hdfs.path = hdfs://192.168.10.173:8020/flumeTest agent1.sinks.lcc_sink1.hdfs.writeFormat = Text agent1.sinks.lcc_sink1.hdfs.fileType = DataStream agent1.sinks.lcc_sink1.hdfs.rollInterval = 0 agent1.sinks.lcc_sink1.hdfs.rollSize = 1000000 agent1.sinks.lcc_sink1.hdfs.rollCount = 0 agent1.sinks.lcc_sink1.hdfs.batchSize = 1000 agent1.sinks.lcc_sink1.hdfs.txnEventMax = 1000 agent1.sinks.lcc_sink1.hdfs.callTimeout = 60000 agent1.sinks.lcc_sink1.hdfs.appendTimeout = 60000 然后运行 [root@biluos conf]# ../bin/flume-ng agent --conf conf --conf-file spool_dir_hdfs.conf --name agent1 -Dflume.root.logger=INFO,console 提示错误如下 17/09/< 1844b span class="hljs-number">07 12:47:57 ERROR source.SpoolDirectorySource: FATAL: Spool Directory source lcc_local_txt_source1: { spoolDir: /opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive }: Uncaught exception in SpoolDirectorySource thread. Restart or reconfigure Flume to continue processing. 17/09/07 12:47:58 ERROR hdfs.HDFSEventSink: process failed java.lang.OutOfMemoryError: GC overhead limit exceeded at java.lang.String.toCharArray(String.java:2899) at java.util.zip.ZipCoder.getBytes(ZipCoder.java:78) at java.util.zip.ZipFile.getEntry(ZipFile.java:310) com.google.common.collect.MapMakerInternalMap.createSegment(MapMakerInternalMap.java:1937) at com.google.common.collect.MapMakerInternalMap.<init>(MapMakerInternalMap.java:260) at com.google.common.collect.MapMaker.makeCustomMap(MapMaker.java:602) at com.google.common.collect.Interners$CustomInterner.<init>(Interners.java:59) at org.apache.flume.sink.DefaultSinkProcessor.process(DefaultSinkProcessor.java:67) at org.apache.flume.SinkRunner$PollingRunner.run(SinkRunner.java:145) at java.lang.Thread.run(Thread.java:745) Exception in thread "SinkRunner-PollingRunner-DefaultSinkProcessor" java.lang.OutOfMemoryError: GC overhead limit exceeded at java.lang.String.toCharArray(String.java:2899) at java.util.zip.ZipCoder.getBytes(ZipCoder.java:78) at java.util.zip.ZipFile.getEntry(ZipFile.java:310) at com.google.common.collect.MapMakerInternalMap.createSegment(MapMakerInternalMap.java:1937) at com.google.common.collect.MapMakerInternalMap.<init>(MapMakerInternalMap.java:260) at com.google.common.collect.MapMaker.makeCustomMap(MapMaker.java:602) at com.google.common.collect.Interners$CustomInterner.<init>(Interners.java:59 at org.apache.flume.sink.DefaultSinkProcessor.process(DefaultSinkProcessor.java:67) at org.apache.flume.SinkRunner$PollingRunner.run(SinkRunner.java:145) at java.lang.Thread.run(Thread.java:745)
3.java.lang.OutOfMemoryError: GC overhead limit exceeded解决方法
解决办法: <1>ps -aux|grep flume 查看刚才启动的flume进程,发现如下信息 /usr/jdk/bin/java -Xmx20m -Dflume.root.logger=INFO -cp conf 1 <2>于是看一个flume-ng的python脚本,发现 JAVA_OPTS="-Xmx20m" 1 问题就是出在这里了,然后我把flume-ng脚本里的这个值调大后,一切运行正常了。 vim ../bin/flume-ng JAVA_OPTS="-Xmx2048m"
重新启动就不报错了
4。新问题:
我拖过去/opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive这个文件夹放入一个133M的文件,发现集群中很多文件http://192.168.10.173:50070/explorer.html#/flumeTest 这个目录下生成的Permission Owner Group Size Last Modified Replication Block Size Name -rw-r--r-- root supergroup 106 B 2017/9/4 上午10:48:59 1 128 MB FlumeData.1504493223881 -rw-r--r-- root supergroup 232 B 2017/9/4 下午12:51:08 1 128 MB FlumeData.1504493358928 -rw-r--r-- root supergroup 126 B 2017/9/4 下午1:57:14 1 128 MB FlumeData.1504504621247 -rw-r--r-- root supergroup 126 B 2017/9/4 下午2:08:45 1 128 MB FlumeData.1504505309265 -rw-r--r-- root supergroup 126 B 2017/9/7 上午11:50:26 1 128 MB FlumeData.1504755927154 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571012 -rw-r--r-- root supergroup 1.08 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571013 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571014 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571015 -rw-r--r-- root supergroup 1.08 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571016 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571017 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:14 1 128 MB FlumeData.1504756571018 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:15 1 128 MB FlumeData.1504756571019 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:15 1 128 MB FlumeData.1504756571020 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:15 1 128 MB FlumeData.1504756571021 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:15 1 128 MB FlumeData.1504756571022 -rw-r--r-- root supergroup 1.08 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571023 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571024 -rw-r--r-- root supergroup 1.08 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571025 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571026 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571027 -rw-r--r-- root supergroup 1.07 KB 2017/9/7 上午11:56:16 1 128 MB FlumeData.1504756571028
关键是这些文件非常多,里面只有9条数据,太少了,浪费空间
5.修改配置文件
#设置客户端是agent1 ###source的名称是lcc_local_txt_source1,通道(缓冲器)名称lcc_memory_channel,sink的名称为lcc_sink1 agent1.sources = lcc_local_txt_source1 agent1.channels = lcc_memory_channel agent1.sinks = lcc_sink1 #####################设置source数据源################################# agent1.sources.lcc_local_txt_source1.type = spooldir agent1.sources.lcc_local_txt_source1.channels = lcc_memory_channel agent1.sources.lcc_local_txt_source1.spoolDir = /opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive agent1.sources.lcc_local_txt_source1.fileHeader = true #####################设置channel的属性################################# agent1.channels.lcc_memory_channel.type = memory agent1.channels.lcc_memory_channel.capacity = 100000 agent1.channels.lcc_memory_channel.transactionCapacity = 100000 agent1.channels.lcc_memory_channel.keep-alive = 30 #####################设置sink要输出到哪里################################# ### Define a logger sink that simply logs all events it receives agent1.sinks.lcc_sink1.channel = lcc_memory_channel agent1.sinks.lcc_sink1.type = hdfs #指定前缀 需要打开这个useLocalTimeStamp = true agent1.sinks.lcc_sink1.hdfs.filePrefix = events-%{host}-%y-%m-%d agent1.sinks.lcc_sink1.hdfs.path = hdfs://192.168.10.173:8020/flumeTest agent1.sinks.lcc_sink1.hdfs.useLocalTimeStamp = true agent1.sinks.lcc_sink1.hdfs.minBlockReplicas=1 agent1.sinks.lcc_sink1.hdfs.rollInterval=60 agent1.sinks.lcc_sink1.hdfs.rollSize=0 agent1.sinks.lcc_sink1.hdfs.rollCount=0 agent1.sinks.lcc_sink1.hdfs.idleTimeout=0
这里注意使用这些%{host}-%y-%m-%d需要打开这个useLocalTimeStamp = true,不然会报错
java.lang.NullPointerException: Expected timestamp in the Flume event headers, but it was null
原因:
sink是hdfs,然后使用目录自动生成功能。出现如题的错误,看官网文档说的是需要在每个文件记录行的开头需要有时间戳,但是时间戳的格式可能比较难调节,所以亦可设置hdfs.useLocalTimeStamp这个参数,比如以每个小时作为一个文件夹,那么配置应该是这样:
a1.sinks.k1.hdfs.path = hdfs://ubuntu:9000/flume/events/%y-%m-%d/%H a1.sinks.k1.hdfs.filePrefix = events- a1.sinks.k1.hdfs.round = true a1.sinks.k1.hdfs.roundValue = 1 a1.sinks.k1.hdfs.roundUnit = hour a1.sinks.k1.hdfs.useLocalTimeStamp = true
使用新的配置文件,发现能正常生成一个你多大的文件,就生成多大文件的hdfs上传文件
-rw-r--r-- root supergroup 153 MB 2017/9/7 下午3:25:19 1 128 MB events--17-09-07.1504769055418
然后我用WinSCP工具往/opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive这个目录下拖拽新文件,模拟日志论滚过程,发现报错
17/09/07 15:18:43 INFO hdfs.HDFSSequenceFile: writeFormat = Writable, UseRawLocalFileSystem = false 17/09/07 15:18:43 INFO hdfs.BucketWriter: Creating hdfs://192.168.10.173:8020/flumeTest/events--17-09-07.1504768723253.tmp 17/09/07 15:18:43 ERROR source.SpoolDirectorySource: FATAL: Spool Directory source lcc_local_txt_source1: { spoolDir: /opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive }: Uncaught exception in SpoolDirectorySource thread. Restart or reconfigure Flume to continue processing. java.nio.charset.MalformedInputException: Input length = 2 at java.nio.charset.CoderResult.throwException(CoderResult.java:281)
问题分析:
上传没出现问题,可就是agent老是会挂掉,报这个异常。
网上解决:
然后让我重启agent才会把Spooling Directory Source所监控的目录下面的文件抽取到HDFS上去,感觉很莫名,网上搜索了一下这个错误的原因,很多都是说可能传输的文件字符集的原因,不以为然,因为我反复测试了一下,如果是字符集的原因,那么为什么我重启一下agent又可以成功的抽取数据了。
于是我想了想是不是由于同时读写导致的问题,因为我SCP文件过去,文件较大,需要一定的时间,而flume监测到有文件马上就开始逐行读取文件转化成EVENT发送到HDFS上去,这中间肯定存在同时读写一个文件了,然后就产生的这个异常问题?
目前仅仅是猜测,于是我修改了Spooling Directory Source的配置,加了这么一个配置:
tier1.sources.source1.ignorePattern = ^(.)*\.tmp$
就是忽略监控目录下面的.tmp文件。然后我修改了scp的逻辑,拷贝到另一台主机上时,先命名为:原文件名.tmp(由于是.tmp文件,agent不会采集此类文件),等SCP执行成功之后,在mv这个.tmp文件,去掉.tmp后缀,这样agent又会抽取这个文件的数据了,通过这么一处理,就巧妙的避免了同时读写一个文件的问题。
脚本调整好之后,重新运行脚本,惊喜的发现成功了,这次agent没有挂掉,大功告成了。
我的任然报错,我测试了一下,原来我上传文件的时候,临时文件的后缀名不是tmp是filepart
新的配置文件如下
#设置客户端是agent1 ###source的名称是lcc_local_txt_source1,通道(缓冲器)名称lcc_memory_channel,sink的名称为lcc_sink1 agent1.sources = lcc_local_txt_source1 agent1.channels = lcc_memory_channel agent1.sinks = lcc_sink1 #####################设置source数据源################################# agent1.sources.lcc_local_txt_source1.type = spooldir agent1.sources.lcc_local_txt_source1.channels = lcc_memory_channel agent1.sources.lcc_local_txt_source1.spoolDir = /opt/moudles/01_all_test_data/02_flume_dir_to_hdfs_and_hbase_and_hive agent1.sources.lcc_local_txt_source1.fileHeader = true agent1.sources.lcc_local_txt_source1.ignorePattern = ^(.)*\\.filepart$ #####################设置channel的属性################################# agent1.channels.lcc_memory_channel.type = memory agent1.channels.lcc_memory_channel.capacity = 100000 agent1.channels.lcc_memory_channel.transactionCapacity = 100000 agent1.channels.lcc_memory_channel.keep-alive = 30 #####################设置sink要输出到哪里################################# ### Define a logger sink that simply logs all events it receives agent1.sinks.lcc_sink1.channel = lcc_memory_channel agent1.sinks.lcc_sink1.type = hdfs #指定前缀 需要打开这个useLocalTimeStamp = true agent1.sinks.lcc_sink1.hdfs.filePrefix = events-%{host}-%y-%m-%d agent1.sinks.lcc_sink1.hdfs.path = hdfs://192.168.10.173:8020/flumeTest agent1.sinks.lcc_sink1.hdfs.useLocalTimeStamp = true agent1.sinks.lcc_sink1.hdfs.minBlockReplicas=1 agent1.sinks.lcc_sink1.hdfs.rollInterval=60 agent1.sinks.lcc_sink1.hdfs.rollSize=0 agent1.sinks.lcc_sink1.hdfs.rollCount=0 agent1.sinks.lcc_sink1.hdfs.idleTimeout=0
然后重新运行就不报错误了。
相关文章推荐
- Flume-ng 1.7.0 安装、配置及说明之1-直接读取Nginx日志存入HDFS
- Flume实现日志文件夹数据加载到HDFS
- spark读取kafka nginx网站日志消息 并写入HDFS中
- 公司员工没有管理员权限怎么办 C#文件夹、文件添加权限 C#读取windows系统日志 C#设置环境变量
- 用Flume采集多台机器上的多种日志并存储于HDFS
- Flume之——Flume读取日志数据写入Kafka
- flume 增量上传日志文件到HDFS中
- Hive读取Flume正在写入的HDFS
- flume读取日志数据写入kafka
- flume上传日志到ha hadoop hdfs上
- Flume 收集Nginx日志到Hdfs Tail-to-hdfs sink
- flume + kafka + sparkStreaming + HDFS 构建实时日志分析系统
- Flume-NG + HDFS + HIVE 日志收集分析
- Flume采集Nginx日志到HDFS
- flume 从文件夹导入hdfs
- 公司员工没有管理员权限怎么办 C#文件夹、文件添加权限 C#读取windows系统日志 C#设置环境变量
- flume学习(三):flume将log4j日志数据写入到hdfs(转)
- CentOS 7.0+flume类似日志输出到HDFS
- Flume监听文件夹中的文件变化,并把文件下沉到hdfs
- Spark中加载本地(或者hdfs)文件以及 spark使用SparkContext实例的textFile读取多个文件夹(嵌套)下的多个数据文件