Storm Multi-Language Protocol

本文详细介绍了Apache Storm中用于支持多种编程语言的Shell组件协议,包括ShellBolt、ShellSpout和ShellProcess的工作原理,以及如何通过JSON编码的命令和响应进行交互。此外还讲解了在集群环境中正确打包和配置Shell组件的方法。

Storm Multi-Language Protocol

Shell Components

通过类ShellBolt、ShellSpout和ShellProcess实现multiple languages的支持,这些类利用java类ProcessBuilder实现接口IBolt、ISpout和支持通过shell执行脚本/程序的协议。

Output fields

Output fields是topology的Thrift定义的一部分,这意味着在Java中使用多语言时,你需要创建一个扩展ShellBolt、实现IRichBolt的Bolt ,并在declareOutputFields中定义output fields。

Protocol

一个简单的协议通过执行脚本/程序的STDIN和STDOUT来实现,跟process交互的数据均以JSON编码,使得支持更多的语言称为可能。

Packaging Your Stuff

在集群中执行shellcomponent时,在提交给masterjar中,shell脚本必须放在目录resources/下。但在单机上进行开发和测试,resources目录需要配置在classpath

The Protocol

注意

  • protocol的两端使用line-reading机制,因此需要保证在输入中截取中一行并将之添加至输出。

  • 所有JSON输入和输出以单行终结,分割符不以JSON编码。

  • 句点是由script所在STDINSTDOUT写入的。

Initial Handshake

在两种类型的shellcomponents中进行initialhandshake

  • STDIN: Setup 信息。包括StormconfigurationTopologycontext和一个PIDdirectoryJSON对象,如下:

{
    "conf": {
        "topology.message.timeout.secs": 3,
        // etc
    },
    "context": {
        "task->component": {
            "1": "example-spout",
            "2": "__acker",
            "3": "example-bolt"
        },
        "taskid": 3
    },
    "pidDir": "..."
}

你的脚本需要再这个目录下创建一个命名为PID的空文件,这个文件使得supervisor知道PID 以使得以后可以shutdown此进程

  • STDOUT: 你的PID,在一个JSON 对象,如{"pid":1234}shellcomponent 将会把此PID 写入它的log

接下来需要做什么取决于component的类型

Spouts

Shell spouts是同步的,如下以while(true) 循环进行:

  • STDIN: nextackfail命令。

"next" 即为ISpoutnextTuple,如下:

{"command": "next"}

"ack" 如下:

{"command": "ack", "id": "1231231"}

"fail" 如下:

{"command": "fail", "id": "1231231"}
  • STDOUT: 基于前面命令,你的spout的结果,可为一序列emitslogs.

emit如下:

{
    "command": "emit",
    // The id for the tuple. Leave this out for an unreliable emit. The id can
    // be a string or a number.
    "id": "1231231",
    // The id of the stream this tuple was emitted to. Leave this empty to emit to default stream.
    "stream": "1",
    // If doing an emit direct, indicate the task to send the tuple to
    "task": 9,
    // All the values in this tuple
    "tuple": ["field1", 2, 3]
}

若不直接emit,你将立即获得taskids,作为JSON数组的tupleSTDIN上被emittaskids

"log"记录workerlog上的一条信息,如下:

{
    "command": "log",
    // the message to log
    "msg": "hello world!"
}
  • STDOUT: 一序列emits/ logs之后的"sync"命令,如下:

{"command": "sync"}

sync之后,ShellSpout不再读取你的输出直到发送另一个nextack或者fail命令。注意,与ISpout相似,

worker上的所有spoutsnextackfail命令之后将被lock直到sync;也如ISpout, 如果next没有emittuples,你应该syncing之前sleep一定时间,ShellSpout 并不自动sleep

Bolts

shell bolt 协议是异步的,一旦可用将在STDIN上接受tuples,你可以在任意时间通过写入STDOUTemitackfaillog,如下:

  • STDIN: 一个tuple!一个JSON编码的解构体如下:

{
    // The tuple's id - this is a string to support languages lacking 64-bit precision
    "id": "-6955786537413359385",
    // The id of the component that created this tuple
    "comp": "1",
    // The id of the stream this tuple was emitted to
    "stream": "1",
    // The id of the task that created this tuple
    "task": 9,
    // All the values in this tuple
    "tuple": ["snow white and the seven dwarfs", "field2", 3]
}
  • STDOUT: 一个ackfailemitlog. Emits 如下:

{
    "command": "emit",
    // The ids of the tuples this output tuples should be anchored to
    "anchors": ["1231231", "-234234234"],
    // The id of the stream this tuple was emitted to. Leave this empty to emit to default stream.
    "stream": "1",
    // If doing an emit direct, indicate the task to send the tuple to
    "task": 9,
    // All the values in this tuple
    "tuple": ["field1", 2, 3]
}

如果不直接emit你将立即获得taskids,作为JSON数组的tupleSTDIN上被emittaskids。注意: 基于shellbolt协议的异步性质,emitting之后读操作无法接受到taskids,你可以处理前面的emit或一个新tuple来替代读取task ids。你将以对应emits的次序获得taskid列表。

ack 如下:

{
    "command": "ack",
    // the id of the tuple to ack
    "id": "123123"
}

fail如下:

{
    "command": "fail",
    // the id of the tuple to fail
    "id": "123123"
}

"log" 记录workerlog上的一条信息,如下:

{
    "command": "log",
    // the message to log
    "msg": "hello world!"
}
  • 注意,0.7.1版本,不再需要shell bolt 'sync'



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值