在 Riak 中存储 ejabberd 数据包
Storing ejabberd packets in Riak
我正在尝试在 Riak 中保存离线 ejabberd 消息。我早些时候在连接到 Riak 时遇到了问题,但现在在这个论坛的帮助下这些问题都得到了解决。但是现在,由于我对 Erlang / ejabberd 的理解有限,我无法将 ejabberd 数据包保存为字符串,然后放在 Riak 上。本质上,当 offline_message_hook 被锁存时,我采用 Packet 参数,然后想为每个双引号添加一个反斜杠,这样我就可以采用这个修改后的字符串并在 Riak 上保存为字符串值。但是,我似乎在努力修改传入的数据包以将“字符替换为 \”。
这是正确的方法吗?还是我的设计中遗漏了什么?我的应用程序依赖于 xml 格式,所以我应该改为使用 p1_xml 模块解析数据包并在将其存储到 Riak 之前使用提取的数据元素重建 xml。
对于非常基本和多个问题表示歉意,但如果有人可以在这里提出一些建议,我们将不胜感激!
我用来尝试将传入数据包中的“替换为 \”的代码是:(它不太有效):
NewPacket = re:replace(Packet, "\"", "\\"", [{return, list}, global]),
所以基本上,我会将 NewPacket 作为值传递给我的 Riak 调用。
ejabberd 与 Riak 兼容,它已经在 Riak 中存储数据包。例如,mod_offline
就是这样做的。
您可以直接查看 ejabberd 代码以了解如何执行此操作。例如,在 mod_offline
中,ejabberd 存储离线消息的方式如下:
store_offline_msg(Host, {User, _}, Msgs, Len, MaxOfflineMsgs,
riak) ->
Count = if MaxOfflineMsgs =/= infinity ->
Len + count_offline_messages(User, Host);
true -> 0
end,
if
Count > MaxOfflineMsgs ->
discard_warn_sender(Msgs);
true ->
lists:foreach(
fun(#offline_msg{us = US,
timestamp = TS} = M) ->
ejabberd_riak:put(M, offline_msg_schema(),
[{i, TS}, {'2i', [{<<"us">>, US}]}])
end, Msgs)
end.
ejabberd_riak:put/3
的代码是:
put(Rec, RecSchema, IndexInfo) ->
Key = encode_key(proplists:get_value(i, IndexInfo, element(2, Rec))),
SecIdxs = [encode_index_key(K, V) ||
{K, V} <- proplists:get_value('2i', IndexInfo, [])],
Table = element(1, Rec),
Value = encode_record(Rec, RecSchema),
case put_raw(Table, Key, Value, SecIdxs) of
ok ->
ok;
{error, _} = Error ->
log_error(Error, put, [{record, Rec},
{index_info, IndexInfo}]),
Error
end.
put_raw(Table, Key, Value, Indexes) ->
Bucket = make_bucket(Table),
Obj = riakc_obj:new(Bucket, Key, Value, "application/x-erlang-term"),
Obj1 = if Indexes /= [] ->
MetaData = dict:store(<<"index">>, Indexes, dict:new()),
riakc_obj:update_metadata(Obj, MetaData);
true ->
Obj
end,
catch riakc_pb_socket:put(get_random_pid(), Obj1).
您应该已经具备适当的 API 功能,可以在 ejabberd 中执行有关 Riak 数据包存储的操作。
我正在尝试在 Riak 中保存离线 ejabberd 消息。我早些时候在连接到 Riak 时遇到了问题,但现在在这个论坛的帮助下这些问题都得到了解决。但是现在,由于我对 Erlang / ejabberd 的理解有限,我无法将 ejabberd 数据包保存为字符串,然后放在 Riak 上。本质上,当 offline_message_hook 被锁存时,我采用 Packet 参数,然后想为每个双引号添加一个反斜杠,这样我就可以采用这个修改后的字符串并在 Riak 上保存为字符串值。但是,我似乎在努力修改传入的数据包以将“字符替换为 \”。
这是正确的方法吗?还是我的设计中遗漏了什么?我的应用程序依赖于 xml 格式,所以我应该改为使用 p1_xml 模块解析数据包并在将其存储到 Riak 之前使用提取的数据元素重建 xml。
对于非常基本和多个问题表示歉意,但如果有人可以在这里提出一些建议,我们将不胜感激!
我用来尝试将传入数据包中的“替换为 \”的代码是:(它不太有效):
NewPacket = re:replace(Packet, "\"", "\\"", [{return, list}, global]),
所以基本上,我会将 NewPacket 作为值传递给我的 Riak 调用。
ejabberd 与 Riak 兼容,它已经在 Riak 中存储数据包。例如,mod_offline
就是这样做的。
您可以直接查看 ejabberd 代码以了解如何执行此操作。例如,在 mod_offline
中,ejabberd 存储离线消息的方式如下:
store_offline_msg(Host, {User, _}, Msgs, Len, MaxOfflineMsgs,
riak) ->
Count = if MaxOfflineMsgs =/= infinity ->
Len + count_offline_messages(User, Host);
true -> 0
end,
if
Count > MaxOfflineMsgs ->
discard_warn_sender(Msgs);
true ->
lists:foreach(
fun(#offline_msg{us = US,
timestamp = TS} = M) ->
ejabberd_riak:put(M, offline_msg_schema(),
[{i, TS}, {'2i', [{<<"us">>, US}]}])
end, Msgs)
end.
ejabberd_riak:put/3
的代码是:
put(Rec, RecSchema, IndexInfo) ->
Key = encode_key(proplists:get_value(i, IndexInfo, element(2, Rec))),
SecIdxs = [encode_index_key(K, V) ||
{K, V} <- proplists:get_value('2i', IndexInfo, [])],
Table = element(1, Rec),
Value = encode_record(Rec, RecSchema),
case put_raw(Table, Key, Value, SecIdxs) of
ok ->
ok;
{error, _} = Error ->
log_error(Error, put, [{record, Rec},
{index_info, IndexInfo}]),
Error
end.
put_raw(Table, Key, Value, Indexes) ->
Bucket = make_bucket(Table),
Obj = riakc_obj:new(Bucket, Key, Value, "application/x-erlang-term"),
Obj1 = if Indexes /= [] ->
MetaData = dict:store(<<"index">>, Indexes, dict:new()),
riakc_obj:update_metadata(Obj, MetaData);
true ->
Obj
end,
catch riakc_pb_socket:put(get_random_pid(), Obj1).
您应该已经具备适当的 API 功能,可以在 ejabberd 中执行有关 Riak 数据包存储的操作。