Storm bolt重复消费问题解决

最近碰到一个storm的坑, 两个bolt都需要从kafkaSpout中获取数据进行各自的业务处理, bolt1的处理是幂等的, bolt2的处理是非幂等的, 上线后发现非幂等的bolt处理总是会处理两次, 代码如下:

//创建拓扑作业
        TopologyBuilder builder = new TopologyBuilder();

        //1. 创建Spout,负责时间调度
        builder.setSpout("timeSpout", new TimeScheduleSpout(60 * 60), 1);

        //2. 创建Spout,从Kafka中读取信息,流ID:RcKafkaSpout

        builder.setSpout("RcKafkaSpout", new KafkaSpout(spoutConfig), RiskControllConfig.getInt(StormConfig.STORM_SPOUT_PARALLELISM_HINT, 1));

        //3. 创建Bolt,处理Kafka中读取的信息, redis计数,流ID:RcAnalyzeBolt

        builder.setBolt("RcAnalyzeBolt", new RcAnalyzeBolt(), RiskControllConfig.getInt(StormConfig.STORM_BOLT1_PARALLELISM_HINT, 1)).allGrouping("RcKafkaSpout").allGrouping("timeSpout");//非幂等的叠加操作

        //4. 创建Bolt,将处理的结果存储至Redis

        builder.setBolt("RcAggregateBolt", new RcAggregateBolt(), RiskControllConfig.getInt(StormConfig.STORM_BOLT2_PARALLELISM_HINT, 1)).shuffleGrouping("RcAnalyzeBolt");

        //5. 更新用户已完成订单金额的bolt
        builder.setBolt("LastOrderBolt", new LastOrderBolt(), RiskControllConfig.getInt(StormConfig.STORM_BOLT1_PARALLELISM_HINT, 1)).allGrouping("RcKafkaSpout");//幂等的hbase put操作

 

红色位置即为bug, 错误原因是对 storm 消息分发策略的理解有问题

徐明明的博客在这一点上讲的有点误导: http://xumingming.sinaapp.com/117/twitter-storm%E7%9A%84%E4%B8%80%E4%BA%9B%E5%85%B3%E9%94%AE%E6%A6%82%E5%BF%B5/

All Grouping: 广播发送, 对于每一个tuple, 所有的Bolts都会收到。

实际上, 官网的解释如下:

http://storm.apache.org/documentation/Concepts.html

All grouping: The stream is replicated across all the bolt's tasks. Use this grouping with care

应该是对于每个tuple, 所有Bolt的所有task(也就是线程)都会收到, 也就意味着, 如果你的并行度设置>1, 则每个tuple会被bolt处理N次

 

allgrouping, 一般用于全局的数据同步和共享才需要, 比如全局的配置更新等, 比如上面的用于定时更新缓存数据的timeSpout, 我们就使用的是allgrouping方式

 

posted @ 2014-12-31 12:20  zhwbqd  阅读(2291)  评论(0编辑  收藏  举报