Riak Core 2,riakcore


Learn Riak Core Step By Step 2

Riak Core, The Coordinator

What is a Coordinator?

顾名思义, Coordinator即使一个协调者,主要工作就是用来协调进来的请求。它强行执行N, R, and W的一致性语义,并且执行想read repairanti-entropy 服务。足药用在分布式集群中,当出现冲突时,用来同步数据。

从技术上说, 协调器是一个gen_fsm,每一个请求都会被他自己的erlang进程处理,一个协调器会和vnode保持通信,直请求结束。

一个协调器总的来说:

  • 协调请求
  • 强一致性
  • 执行anti-entropy
  • 一个实现了gen-fsm行为的erlang进程
  • 与执行请求的vnode实例保持通信

Implementing a Coordinator

和vnode不一样,riak core没有定义协调器的行为。例子中现实了get和put的协调器,可以参照,但不是一成不变的。

例子中使用supervisour和gen_fsm worker的方式实现了协调器。

init(Args) -> {ok, InitialState, SD, Timeout}

Args                :: term()
InitialState        :: atom()
SD                  :: term()
Timeout             :: integer()

这实际上是gen_fsm行为的一部分,必须在回调中制定初始状态名和数据(SD)。有些情况下,你也可以制定超时的值为0以至于马上进入到初始状态-prepare

一个get rts的协调器需要4个参数:

  • RequestId:本次请求的唯一Id

  • From: 应答者

  • Client: The name of the client entity -- the entity that is writing log events to RTS.

  • StatName: 统计项的名字.

init([ReqId, From, Client, StatName]) ->
    SD = #state{req_id=ReqId,
                from=From,
                client=Client,
                stat_name=StatName},
    {ok, prepare, SD, 0}.

rts的写协调者也是一样,但是有两个额外的参数。

  • Op: 执行的操作可以是setappendincrincrby或者sadd中的一种.

  • Val: 被操作的值,incr操作没有这项定义。

init([ReqID, From, Client, StatName, Op, Val]) ->
    SD = #state{req_id=ReqID,
                from=From,
                client=Client,
                stat_name=StatName,
                op=Op,
                val=Val},
    {ok, prepare, SD, 0}.

prepare(timeout, SD0) -> {next_state, NextState, SD, Timeout}

SD0 = SD            :: term()
NextState           :: atom()
Timeout             :: integer()

prepare的工作是建立一个优先列表,这个列表是应该参与本次请求的优先的vnode集合的列表.大部分的工作都被riak_core_util:chash_key/1riak_core_apl:get_apl/3做完了.getwrite协调器这时后做的工作都一样。

计算请求落在环的索引,从索引中确定N个优先处理这个请求的分区。

下面是代码:

prepare(timeout, SD0=#state{client=Client,
                            stat_name=StatName}) ->
    DocIdx = riak_core_util:chash_key({list_to_binary(Client),
                                       list_to_binary(StatName)}),
    Prelist = riak_core_apl:get_apl(DocIdx, ?N, rts_stat),
    SD = SD0#state{preflist=Prelist},
    {next_state, execute, SD, 0}.

execute(timeout, SD0) -> {next_state, NextState, SD}

SD0 = SD            :: term()
NextState           :: atom()

prepare之后就会调用excute,excute会根据优先列表来执行相应的stat请求。

execute(timeout, SD0=#state{req_id=ReqId,
                            stat_name=StatName,
                            preflist=Prelist}) ->
    rts_stat_vnode:get(Prelist, ReqId, StatName),
    {next_state, waiting, SD0}.

写协调器和get协调器一样,就是多了op.

execute(timeout, SD0=#state{req_id=ReqID,
                        stat_name=StatName,
                        op=Op,
                        val=undefined,
                        preflist=Preflist}) ->
    rts_stat_vnode:Op(Preflist, ReqID, StatName),
    {next_state, waiting, SD0}.

waiting(Reply, SD0) -> Result

Reply               :: {ok, ReqID}
Result              :: {next_state, NextState, SD}
                     | {stop, normal, SD}
NextState           :: atom()
SD0 = SD            :: term()

下面是get的代码

waiting({ok, ReqID, Val}, SD0=#state{from=From, num_r=NumR0, replies=Replies0}) ->
    NumR = NumR0 + 1,
    Replies = [Val|Replies0],
    SD = SD0#state{num_r=NumR,replies=Replies},
    if
        NumR =:= ?R ->
            Reply =
                case lists:any(different(Val), Replies) of
                    true ->
                        Replies;
                    false ->
                        Val
                end,
            From ! {ReqID, ok, Reply},
            {stop, normal, SD};
        true -> {next_state, waiting, SD}
    end.

从代码中可以看出所谓强一致性就是等待全部应答,然后把应答结果组织后,一起返回去,没有达到应答数量会一直等待。

写协调更加容易:

waiting({ok, ReqID}, SD0=#state{from=From, num_w=NumW0}) ->
    NumW = NumW0 + 1,
    SD = SD0#state{num_w=NumW},
    if
    NumW =:= ?W ->
            From ! {ReqID, ok},
            {stop, normal, SD};
    true -> {next_state, waiting, SD}
    end.

What About the Entry Coordinator?

Entry只是解析每一个日志,没必要使用协调器,协调器一般用在存储。

Changes to rts.erl and rts_stat_vnode

rts的模块也需要更新,主要增加fsm的代码,rts不会直接和vnode通信,交给fsm间接通信。

rts:get ----> rts_stat_vnode:get (local)

                                                          /--> stat_vnode@rts1
rts:get ----> rts_get_fsm:get ----> rts_stat_vnode:get --|---> stat_vnode@rts2
                                                          \--> stat_vnode@rts3

rts:get/2函数现在也是调用get协调器然后等待结果。

get(Client, StatName) ->
    {ok, ReqID} = rts_get_fsm:get(Client, StatName),
    wait_for_reqid(ReqID, ?TIMEOUT).

写请求也经过了像是的重构。

do_write(Client, StatName, Op) ->
    {ok, ReqID} = rts_write_fsm:write(Client, StatName, Op),
    wait_for_reqid(ReqID, ?TIMEOUT).

do_write(Client, StatName, Op, Val) ->
    {ok, ReqID} = rts_write_fsm:write(Client, StatName, Op, Val),
    wait_for_reqid(ReqID, ?TIMEOUT).

rts_stat_vnode也进行了重构,使用riak_core_vnode_master:command/4并且携带了从参数PreflistMsgSender 和VMaster.

Preflist: 被发送命令的vnode列表

Msg: 被发送的命令.

Sender: 发送者,这里表示协调者. 主要用于vnode正确返回信息。

VMaster: VNode master的名字.
get(Preflist, ReqID, StatName) -> 
    riak_core_vnode_master:command(Preflist, {get, ReqID, StatName}, {fsm, undefined, self()}, ?MASTER).


core 2与core有什不同

1.脑筋急转弯? 多个2 不是啊~?
2.CORE DUO是酷睿一代的双核版本,单核的叫CORE SOLO
3.CORE 2 DUO是酷睿二代的双核版本,单核的叫CORE 2 SOLO
4.酷睿是CORE的中文音译,就是CORE。
5.woodcrest是INTEL针对服务器工作站市场开发的CPU,FSB达到1333MB/S,L2 Cache数目将会为4MB。
6.Kentsfield是INTEL准备在2007年推出的4核心处理器。其实就是两颗双核心Conroe封装在一起而来,与此前Pentium D的设计类似。

2005年秋季的IDF上,INTEL正式宣布将采用全新构架Core的CPU来取代当前Netburst构架的Pentium 4系列,从笔记本使用的移动CPU到桌面CPU再到服务器的XEON系列,全部都将放弃现在的Netburst构架。它将衍生为移动CPU版的Merom,桌面CPU的Conroe和服务器领域的Woodcrest。旧的Netburst构架的首要任务是提升运行频率,而新的Core构架的首要的任务则是更好的集成多颗核心、以更高的效率完成任务、保持高的功耗/性能比.
按照Intel的规划,从2006年第三季度开始,台式机Core Duo将逐渐采用基于Core架构的Conroe核心,改用Socket 775接口,主流型号的前端总线提高到1066MHz FSB.

CORE DUO就是现在笔记本上面用的双核~是原来的P M核心的~
CORE 2 DUO是全新的核心~

Core(酷睿)微体系架构,其针对桌面、笔记本和服务器推出的产品代号分别是,Conroe、Merom和Woodcrest,都拥有64位处理能力,并且是双核产品。
(Conroe扣肉
Merom猫肉
Woodcrest服务器上用的)
 

Core 2怎读?

Core 2读做“酷睿 2”或者“酷睿第二代”

1.CORNOE是核心的研发代号,就象Willamette 是P4早期核心代号,Prescott 是晚期代号一样。CORNOE是桌面级核心。
2.CORE DUO是酷睿一代的双核版本,单核的叫CORE SOLO
3.CORE 2 DUO是酷睿二代的双核版本,单核的叫CORE 2 SOLO
4.酷睿是CORE的中文音译,就是CORE。
5.woodcrest是INTEL针对服务器工作站市场开发的CPU,FSB达到1333MB/S,L2 Cache数目将会为4MB。
6.Kentsfield是INTEL准备在2007年推出的4核心处理器。其实就是两颗双核心Conroe封装在一起而来,与此前Pentium D的设计类似。
 

相关内容

    暂无相关文章