在storm中使用bloom_filter消重服务

bloom_filter服务


bloom_filter的简介与使用请看这里
bloom_filter的配置文件conf.ini如下

[filter]
cnt=4 
num_bits=4294967296
num_hash_func=7 
[server]
pid_file=/var/run/bloom_filter.pid 
daemonlize=1 
port=8000

cnt表示启动的bloom_filter的数量
num_bits表示位数组大小
cnt* num_bits/(8 * 1024 * 1024 * 1024)即为bloom_filter运行时所占用的内存大小(GB)。

数据插入

提供两种方式:
1、远程http请求。curl http://w21*********.8000/?ks=1,2 -X POST 。这种方式网络开销较大,数据量很大时不推荐。
2、本地文件导入。当启动bloom_filter服务时,会默认读取当前目录下名为new_users的文件(待改进),将每一行当作一条记录插入bloom_filter中。速度可达100,000条/秒。

数据查询

http请求,curl http://w21********:8000/?ks=1,2
在w6机器上,qps可达4000/s。由于每个http请求中可以带多个参数,因此可以支持每秒上万个记录的查询任务。

storm计算新用户

任务:计算2014年1月1号的游戏级新用户。


启动bloom_filter服务。

在机器上启动bloom_filter服务,并将2014年1月1号前的所有游戏级新用户采用读取本地文件的方式导入bloom_filter中。

编写storm的bolt脚本。

程序从标准输入中,每读取30条记录,将就其拼接成一条curl请求,然后访问bloom_filter服务,根据返回值计算这里面有多少个新用户。

$filter_service = "http://w21*******:8000/?ks="; 
$uv_count = 0;
$record_combine = array();
while(($line = fgets(STDIN)) !== false) {
   $line = trim($line); 
   $record = explode("\t", $line); 
   $id = $record[0];   
   if(count($record)%3 !== 0)  { 
       echo "$id\tack\n";      
       fwrite(STDERR, "wrong data".$line."\n"); 
       flush();        
       continue; 
   }   
for($i = 0; $i<count($record); $i+=3){ 
   $qid = $record[$i+1];
   $gkey = $record[$i+2]; 
   $record_combine[] = $qid.$gkey;}
   if(count($record_combine)===30){
          $request = $filter_service;
          $request .= implode(",", $record_combine);
          $ch = curl_init(); 
          curl_setopt($ch, CURLOPT_URL, $request); 
         curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
         $filter_result = curl_exec($ch); 
         curl_close($ch);
         $uv_count +=substr_count($filter_result,"false");
         fwrite(STDERR, "uv is ".$uv_count."\n"); 
         unset($record_combine);
   }
   echo "$id\tack\n";  flush(); 
}

一次查询多条记录,能够大幅度减少网络压力与耗时。

提交storm任务到测试集群,并发送数据。

运行run.sh脚本提交任务。然后发送异步数据,
cat glogin_daily_2014_1_1.dat | async_send -batch 100 webgame_statistic_49 >/dev/null
这里采用 -batch指令,将日志每300行发送一次。
单个spout的发送数据的速度有限,为30~40万次/小时,若一次只发送一行日志,将大幅度降低storm的吞吐量

误判率


理论误判率计算公式在storm中使用bloom_filter消重服务。
m为位数组大小,k为哈希函数个数,n为记录数。
令m=235,k=7,n=240,000,000。
带入公式计算得到的理论误判率为:5.64e-10。
从程序中查询得到的程序理论误判率为:1.4e-4。
storm运行结果与线上数据比对后,得到程序实际误判率为:1.86e-3。
令m=236,k=7,n=240,000,000。
带入公式计算得到的理论误判率为:4.79e-12。
从程序中查询得到的程序理论误判率为:1.95e-6。
storm运行结果与线上数据比对后,得到程序实际误判率为:9.3e-4。
程序实际误判率比理论值大

结果比对


1、将storm任务运行时中bloom_fliter的返回结果(json)保存成日志
2、去掉json中的花括号{}。

cat log | awk '/"*"/ {print $0}' >process_log

3、找出返回结果为true的记录,并去掉引号""。

cat process_log | awk -F ":" '{gsub(/\"/, ""); if(match($2,/true/)) print $1}' >process_log_true

4、去掉记录的空格

sed 's/ //g' process_log_true > process_log_final

5、从hadoop中导出2014年1月1号的新用户的记录,并存成文本。

hive -e 
"SELECT gp.qid, gp.gkey FROM 
    (SELECT distinct qid, gkey FROM glogin_daily WHERE year!=2014) np 
RIGHT OUTER JOIN 
    (SELECT distinct qid, gkey FROM glogin_daily where year=2014 and month = 1 and day = 1) gp 
    ON np.qid = gp.qid AND np.gkey = gp.gkey 
    WHERE np.qid IS NOT NULL and np.gkey IS NOT NULL and gp.qid IS NOT NULL and gp.gkey IS NOT NULL;" 
> exists_game_2014_01_01.dat

6、比对storm与hadoop中的记录。发现确实是bloom_filter误判了。
例如记录为"101326892zwj",并没有在以往的日志中出现过,确实是新用户,但bloom_filter中却认为是已存在的用户,返回结果为true。

注意的问题

1、bloom_filter的误判率,与占用的总内存有关。就是说,存储2.4亿数据,使用4个512M的bloom_filter,与使用1个2G的bloom_filter的误判率是一样的。从公式也可以看出来。
2、storm集群若与bloom_filter的服务器跨机房,则会因为网络延迟,导致bolt中的数据没有被及时处理而堵塞。导致spout经常性失败 。
3、为防止iptable的设置导致bloom_filter不可用,可以开放8000端口。 sudo iptables -I INPUT -p tcp --dport 8000 -j ACCEPT
4、hadoop中的日志,不能只看分区,由于hydra任务的堆积,会使今天的部分日志记录到明天的分区中。因此需要指定year,month,day来导出日志

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 215,923评论 6 498
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,154评论 3 392
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 161,775评论 0 351
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,960评论 1 290
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,976评论 6 388
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,972评论 1 295
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,893评论 3 416
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,709评论 0 271
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,159评论 1 308
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,400评论 2 331
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,552评论 1 346
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,265评论 5 341
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,876评论 3 325
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,528评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,701评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,552评论 2 368
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,451评论 2 352

推荐阅读更多精彩内容

  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,649评论 18 139
  • 布隆过滤器 Bloom Filter 布隆过滤器,用来判断一个元素是否在集合中。它的特点是节省空间,但是有误判。有...
    周肃阅读 4,573评论 0 5
  • http://geek.csdn.net/news/detail/210469http://www.36dsj.c...
    Albert陈凯阅读 5,147评论 1 21
  • 教你如何迅速秒杀掉:99%的海量数据处理面试题 本文经过大量细致的优化后,收录于我的新书《编程之法》第六章中,新书...
    Helen_Cat阅读 7,413评论 1 39
  • 前些日子,闺密发给我这两张图片,与之伴随发来的是一个痛心疾首的表情。 我的第一反应是她疯了吗?!为什么会有这种想法...
    复明的瞎子阅读 571评论 0 2