WIP: encoding #p_srvr and #projection_v1, just starting. Damn tedious.

This commit is contained in:
Scott Lystig Fritchie 2015-06-24 12:50:37 +09:00
parent d3b0b7fdc5
commit 2068f70700
3 changed files with 172 additions and 7 deletions

View file

@ -83,6 +83,15 @@ message Mpb_FileInfo {
required string file_name = 2;
}
// #p_srvr{} type
message Mpb_P_Srvr {
required string name = 1;
required string proto_mod = 2;
required string address = 3;
required string port = 4;
required bytes props = 5;
}
//////////////////////////////////////////
//
// requests & responses
@ -97,7 +106,21 @@ message Mpb_ErrorResp {
optional bytes extra = 3;
}
// ping() request & response
//////////////////////////////////////////
//
// High Level API requests:
//
// echo() : Mpb_EchoReq and Mpb_EchoResp
// auth() : Mpb_AuthReq and Mpb_AuthResp
// append_chunk() : Mpb_AppendChunkReq and Mpb_AppendChunkResp
// write_chunk() : Mpb_WriteChunkReq and Mpb_WriteChunkResp
// read_chunk() : Mpb_ReadChunkReq and Mpb_ReadChunkResp
// checksum_list() : Mpb_ChecksumListReq and Mpb_ChecksumListResp
// list_files() : Mpb_ListFilesReq and Mpb_ListFilesResp
//
//////////////////////////////////////////
// High level API: echo() request & response
message Mpb_EchoReq {
optional string message = 1;
@ -107,7 +130,7 @@ message Mpb_EchoResp {
optional string message = 1;
}
// Authentication request & response
// High level API: auth() request & response (not yet implemented)
message Mpb_AuthReq {
required bytes user = 1;
@ -119,7 +142,7 @@ message Mpb_AuthResp {
// TODO: not implemented yet
}
// append_chunk() request & response
// High level API: append_chunk() request & response
message Mpb_AppendChunkReq {
optional bytes placement_key = 1;
@ -135,7 +158,7 @@ message Mpb_AppendChunkResp {
optional Mpb_ChunkPos chunk_pos = 2;
}
// write_chunk() request & response
// High level API: write_chunk() request & response
message Mpb_WriteChunkReq {
required string file = 1;
@ -148,7 +171,7 @@ message Mpb_WriteChunkResp {
required Mpb_GeneralStatusCode status = 1;
}
// read_chunk() request & response
// High level API: read_chunk() request & response
message Mpb_ReadChunkReq {
required string file = 1;
@ -167,7 +190,7 @@ message Mpb_ReadChunkResp {
optional Mpb_ChunkCSum csum = 3;
}
// checksum_list() request & response
// High level API: checksum_list() request & response
message Mpb_ChecksumListReq {
required string file = 1;
@ -178,7 +201,7 @@ message Mpb_ChecksumListResp {
optional bytes chunk = 2;
}
// list_files() request & response
// High level API: list_files() request & response
message Mpb_ListFilesReq {
}

125
src/machi_pb_wrap.erl Normal file
View file

@ -0,0 +1,125 @@
%% -------------------------------------------------------------------
%%
%% Machi: a small village of replicated files
%%
%% Copyright (c) 2014-2015 Basho Technologies, Inc. All Rights Reserved.
%%
%% This file is provided to you under the Apache License,
%% Version 2.0 (the "License"); you may not use this file
%% except in compliance with the License. You may obtain
%% a copy of the License at
%%
%% http://www.apache.org/licenses/LICENSE-2.0
%%
%% Unless required by applicable law or agreed to in writing,
%% software distributed under the License is distributed on an
%% "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
%% KIND, either express or implied. See the License for the
%% specific language governing permissions and limitations
%% under the License.
%%
%% -------------------------------------------------------------------
-module(machi_pb_wrap).
-include("machi_pb.hrl").
-include("machi_projection.hrl").
-export([enc_p_srvr/1, dec_p_srvr/1,
enc_projection_v1/1, dec_projection_v1/1]).
-ifdef(TEST).
-compile(export_all).
-endif. % TEST
enc_p_srvr(#p_srvr{name=Name,
proto_mod=ProtoMod,
address=Address,
port=Port,
props=Props}) ->
machi_pb:encode_mpb_p_srvr(#mpb_p_srvr{name=to_list(Name),
proto_mod=to_list(ProtoMod),
address=to_list(Address),
port=to_list(Port),
props=todo_enc_opaque(Props)}).
dec_p_srvr(Bin) ->
#mpb_p_srvr{name=Name,
proto_mod=ProtoMod,
address=Address,
port=Port,
props=Props} = machi_pb:decode_mpb_p_srvr(Bin),
#p_srvr{name=to_atom(Name),
proto_mod=to_atom(ProtoMod),
address=to_list(Address),
port=to_integer(Port),
props=todo_dec_opaque(Props)}.
enc_projection_v1(#projection_v1{dbg=Dbg,
dbg2=Dbg2,
members_dict=MembersDict} = P) ->
term_to_binary(P#projection_v1{dbg=enc_sexp(Dbg),
dbg2=enc_sexp(Dbg2),
members_dict=enc_members_dict(MembersDict)}).
dec_projection_v1(Bin) ->
P = #projection_v1{dbg=Dbg,
dbg2=Dbg2,
members_dict=MembersDict} = binary_to_term(Bin),
P#projection_v1{dbg=dec_sexp(Dbg),
dbg2=dec_sexp(Dbg2),
members_dict=dec_members_dict(MembersDict)}.
%%%%%%%%%%%%%%%%%%%
enc_sexp(T) ->
lists:flatten(io_lib:format("~w.", [T])).
dec_sexp(String) ->
{ok,Tks,_} = erl_scan:string(String),
{ok,E} = erl_parse:parse_exprs(Tks),
{value,Funs,_} = erl_eval:exprs(E,[]),
Funs.
enc_members_dict(D) ->
%% Use list_to_binary() here to "flatten" the serialized #p_srvr{}
[{K, list_to_binary(enc_p_srvr(V))} || {K, V} <- orddict:to_list(D)].
dec_members_dict(List) ->
orddict:from_list([{K, dec_p_srvr(V)} || {K, V} <- List]).
to_binary(X) when is_list(X) ->
list_to_binary(X);
to_binary(X) when is_integer(X) ->
list_to_binary(integer_to_list(X));
to_binary(X) when is_atom(X) ->
erlang:atom_to_binary(X, latin1);
to_binary(X) when is_binary(X) ->
X.
to_list(X) when is_atom(X) ->
atom_to_list(X);
to_list(X) when is_binary(X) ->
binary_to_list(X);
to_list(X) when is_integer(X) ->
integer_to_list(X);
to_list(X) when is_list(X) ->
X.
to_atom(X) when is_list(X) ->
list_to_atom(X);
to_atom(X) when is_binary(X) ->
erlang:binary_to_atom(X, latin1);
to_atom(X) when is_atom(X) ->
X.
to_integer(X) when is_list(X) ->
list_to_integer(X);
to_integer(X) when is_binary(X) ->
list_to_binary(binary_to_list(X));
to_integer(X) when is_integer(X) ->
X.
todo_enc_opaque(X) ->
erlang:term_to_binary(X).
todo_dec_opaque(X) ->
erlang:binary_to_term(X).

View file

@ -22,6 +22,7 @@
-module(machi_pb_test).
-include("machi_pb.hrl").
-include("machi_projection.hrl").
-compile(export_all).
@ -62,6 +63,22 @@ smoke_responses_test() ->
ok.
smoke_p_srvr_test() ->
P1 = #p_srvr{name=a, address="localhost", port=5555,
props=[{dir,"./data.a"}]},
P1 = machi_pb_wrap:dec_p_srvr(
list_to_binary(machi_pb_wrap:enc_p_srvr(P1))),
ok.
smoke_projection_v1_test() ->
P1 = #p_srvr{name=a, address="localhost", port=5555,
props=[{dir,"./data.a"}]},
D = orddict:from_list([ {P1#p_srvr.name, P1} ]),
Proj1 = machi_projection:new(a, D, [a], [], [], [{property, 42}]),
Proj1 = machi_pb_wrap:dec_projection_v1(
machi_pb_wrap:enc_projection_v1(Proj1)),
ok.
encdec_request(M) ->
machi_pb:decode_mpb_request(
list_to_binary(machi_pb:encode_mpb_request(M))).