Compare commits
12 Commits
e10ef8a460
...
2f93c4d503
| Author | SHA1 | Date | |
|---|---|---|---|
| 2f93c4d503 | |||
| b542205c0e | |||
| 6ba0c1f2ae | |||
| d1cae68ce7 | |||
| ccd9a8c83d | |||
| f5e955b583 | |||
| 61984d1529 | |||
| 1978ca59b3 | |||
| 4ee6609111 | |||
| aeb78eab38 | |||
| 88c6f6dcc7 | |||
| d5ff77b278 |
47
src/hz.erl
47
src/hz.erl
@ -66,6 +66,8 @@
|
|||||||
contract_create/8,
|
contract_create/8,
|
||||||
prepare_contract/1,
|
prepare_contract/1,
|
||||||
prepare_aaci/1,
|
prepare_aaci/1,
|
||||||
|
cache_aaci/2,
|
||||||
|
lookup_aaci/1,
|
||||||
aaci_lookup_spec/2,
|
aaci_lookup_spec/2,
|
||||||
contract_call/5,
|
contract_call/5,
|
||||||
contract_call/6,
|
contract_call/6,
|
||||||
@ -1073,7 +1075,7 @@ contract_create2(CreatorID, Nonce, Amount, TTL, Gas, GasPrice, Source, Options,
|
|||||||
InitArgs :: [string()],
|
InitArgs :: [string()],
|
||||||
Result :: {ok, CreateTX} | {error, Reason},
|
Result :: {ok, CreateTX} | {error, Reason},
|
||||||
CreateTX :: binary(),
|
CreateTX :: binary(),
|
||||||
Reason :: file:posix() | term().
|
Reason :: file:posix() | bad_fun_name | aaci_not_found | term().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% This function takes the compiler output (instead of starting from source),
|
%% This function takes the compiler output (instead of starting from source),
|
||||||
%% and returns the unsigned create contract call data with default values.
|
%% and returns the unsigned create contract call data with default values.
|
||||||
@ -1187,7 +1189,7 @@ read_aci(Path) ->
|
|||||||
|
|
||||||
-spec contract_call(CallerID, AACI, ConID, Fun, Args) -> Result
|
-spec contract_call(CallerID, AACI, ConID, Fun, Args) -> Result
|
||||||
when CallerID :: unicode:chardata(),
|
when CallerID :: unicode:chardata(),
|
||||||
AACI :: aaci(),
|
AACI :: aaci() | {aaci, Label :: term()},
|
||||||
ConID :: unicode:chardata(),
|
ConID :: unicode:chardata(),
|
||||||
Fun :: string(),
|
Fun :: string(),
|
||||||
Args :: [string()],
|
Args :: [string()],
|
||||||
@ -1222,7 +1224,7 @@ contract_call(CallerID, AACI, ConID, Fun, Args) ->
|
|||||||
-spec contract_call(CallerID, Gas, AACI, ConID, Fun, Args) -> Result
|
-spec contract_call(CallerID, Gas, AACI, ConID, Fun, Args) -> Result
|
||||||
when CallerID :: unicode:chardata(),
|
when CallerID :: unicode:chardata(),
|
||||||
Gas :: pos_integer(),
|
Gas :: pos_integer(),
|
||||||
AACI :: aaci(),
|
AACI :: aaci() | {aaci, Label :: term()},
|
||||||
ConID :: unicode:chardata(),
|
ConID :: unicode:chardata(),
|
||||||
Fun :: string(),
|
Fun :: string(),
|
||||||
Args :: [string()],
|
Args :: [string()],
|
||||||
@ -1260,7 +1262,7 @@ contract_call(CallerID, Gas, AACI, ConID, Fun, Args) ->
|
|||||||
GasPrice :: pos_integer(),
|
GasPrice :: pos_integer(),
|
||||||
Amount :: non_neg_integer(),
|
Amount :: non_neg_integer(),
|
||||||
TTL :: non_neg_integer(),
|
TTL :: non_neg_integer(),
|
||||||
AACI :: aaci(),
|
AACI :: aaci() | {aaci, Label :: term()},
|
||||||
ConID :: unicode:chardata(),
|
ConID :: unicode:chardata(),
|
||||||
Fun :: string(),
|
Fun :: string(),
|
||||||
Args :: [string()],
|
Args :: [string()],
|
||||||
@ -2207,11 +2209,34 @@ zip_record_field({Name, Type}, {Remaining, Missing}) ->
|
|||||||
{missing, {Remaining, [Name | Missing]}}
|
{missing, {Remaining, [Name | Missing]}}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
|
-spec cache_aaci(Label, AACI) -> ok
|
||||||
|
when Label :: term(),
|
||||||
|
AACI :: aaci().
|
||||||
|
%% @doc
|
||||||
|
%% Caches an AACI for future reference in calls that would otherwise require
|
||||||
|
%% the AACI as an argument. Once cached, a pre-built AACI can be referenced in
|
||||||
|
%% later calls by substituting the AACI argument with `{aaci, Label}'.
|
||||||
|
|
||||||
|
cache_aaci(Label, AACI) ->
|
||||||
|
hz_man:cache_aaci(Label, AACI).
|
||||||
|
|
||||||
|
|
||||||
|
-spec lookup_aaci(Label) -> Result
|
||||||
|
when Label :: term(),
|
||||||
|
Result :: {ok, aaci()} | error.
|
||||||
|
%% @doc
|
||||||
|
%% Retrieve a previously prepared and cached AACI.
|
||||||
|
|
||||||
|
lookup_aaci(Label) ->
|
||||||
|
hz_man:lookup_aaci(Label).
|
||||||
|
|
||||||
|
|
||||||
-spec aaci_lookup_spec(AACI, Fun) -> {ok, Type} | {error, Reason}
|
-spec aaci_lookup_spec(AACI, Fun) -> {ok, Type} | {error, Reason}
|
||||||
when AACI :: aaci(),
|
when AACI :: aaci() | {aaci, Label :: term()},
|
||||||
Fun :: binary() | string(),
|
Fun :: binary() | string(),
|
||||||
Type :: {term(), term()}, % FIXME
|
Type :: {term(), term()}, % FIXME
|
||||||
Reason :: bad_fun_name.
|
Reason :: bad_fun_name | aaci_not_found.
|
||||||
|
|
||||||
%% @doc
|
%% @doc
|
||||||
%% Look up the type information of a given function, in the AACI provided by
|
%% Look up the type information of a given function, in the AACI provided by
|
||||||
@ -2222,6 +2247,11 @@ aaci_lookup_spec({aaci, _, FunDefs, _}, Fun) ->
|
|||||||
case maps:find(Fun, FunDefs) of
|
case maps:find(Fun, FunDefs) of
|
||||||
A = {ok, _} -> A;
|
A = {ok, _} -> A;
|
||||||
error -> {error, bad_fun_name}
|
error -> {error, bad_fun_name}
|
||||||
|
end;
|
||||||
|
aaci_lookup_spec({aaci, Label}, Fun) ->
|
||||||
|
case hz_man:lookup_aaci(Label) of
|
||||||
|
{ok, AACI} -> aaci_lookup_spec(AACI, Fun);
|
||||||
|
error -> {error, aaci_not_found}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
-spec min_gas_price() -> integer().
|
-spec min_gas_price() -> integer().
|
||||||
@ -2252,6 +2282,11 @@ encode_call_data({aaci, _ContractName, FunDefs, _TypeDefs}, Fun, Args) ->
|
|||||||
case maps:find(Fun, FunDefs) of
|
case maps:find(Fun, FunDefs) of
|
||||||
{ok, {ArgDef, _ResultDef}} -> encode_call_data2(ArgDef, Fun, Args);
|
{ok, {ArgDef, _ResultDef}} -> encode_call_data2(ArgDef, Fun, Args);
|
||||||
error -> {error, bad_fun_name}
|
error -> {error, bad_fun_name}
|
||||||
|
end;
|
||||||
|
encode_call_data({aaci, Label}, Fun, Args) ->
|
||||||
|
case hz_man:lookup_aaci(Label) of
|
||||||
|
{ok, AACI} -> encode_call_data(AACI, Fun, Args);
|
||||||
|
error -> {error, aaci_not_found}
|
||||||
end.
|
end.
|
||||||
|
|
||||||
encode_call_data2(ArgDef, Fun, Args) ->
|
encode_call_data2(ArgDef, Fun, Args) ->
|
||||||
|
|||||||
@ -26,8 +26,10 @@
|
|||||||
-copyright("Craig Everett <ceverett@tsuriai.jp>").
|
-copyright("Craig Everett <ceverett@tsuriai.jp>").
|
||||||
-license("GPL-3.0-or-later").
|
-license("GPL-3.0-or-later").
|
||||||
|
|
||||||
-export([amount/1, amount/2, amount/3, amount/4,
|
-export([amount/1, amount/2, amount/3,
|
||||||
|
approx_amount/2, approx_amount/3,
|
||||||
read/1,
|
read/1,
|
||||||
|
one/1, mark/1,
|
||||||
price_to_string/1, string_to_price/1]).
|
price_to_string/1, string_to_price/1]).
|
||||||
|
|
||||||
-spec amount(Pucks) -> Formatted
|
-spec amount(Pucks) -> Formatted
|
||||||
@ -35,6 +37,19 @@
|
|||||||
Formatted :: string().
|
Formatted :: string().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% A convenience formatting function.
|
%% A convenience formatting function.
|
||||||
|
%% ```
|
||||||
|
%% hz_format:amount(1) ->
|
||||||
|
%% 木0.000,000,000,000,000,001
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(5000) ->
|
||||||
|
%% 木0.000,000,000,000,005
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(5000000000000000000) ->
|
||||||
|
%% 木5
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(500000123000000000000000) ->
|
||||||
|
%% 木500,000.123
|
||||||
|
%% '''
|
||||||
%% @equiv amount(us, Pucks).
|
%% @equiv amount(us, Pucks).
|
||||||
|
|
||||||
amount(Pucks) ->
|
amount(Pucks) ->
|
||||||
@ -49,6 +64,25 @@ amount(Pucks) ->
|
|||||||
Formatted :: string().
|
Formatted :: string().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% A money formatting function.
|
%% A money formatting function.
|
||||||
|
%% ```
|
||||||
|
%% hz_format:amount(us, 100500040123000000000000000) ->
|
||||||
|
%% 木100,500,040.123
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(jp, 100500040123000000000000000) ->
|
||||||
|
%% 1億50万40木 12京3000兆本
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(metric, 100500040123000000000000000) ->
|
||||||
|
%% 木100m 500k 40 G 123p P
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(legacy, 100500040123000000000000000) ->
|
||||||
|
%% 木100m 500k 40 G 123q P
|
||||||
|
%%
|
||||||
|
%% hz_format:amount({$_, 3}, 100500040123000000000000000) ->
|
||||||
|
%% 木100_500_040.123
|
||||||
|
%%
|
||||||
|
%% hz_format:amount({$_, 4}, 100500040123000000000000000) ->
|
||||||
|
%% 木1_0050_0040.123
|
||||||
|
%% '''
|
||||||
%% @equiv amount(gaju, Style, Pucks).
|
%% @equiv amount(gaju, Style, Pucks).
|
||||||
|
|
||||||
amount(Style, Pucks) ->
|
amount(Style, Pucks) ->
|
||||||
@ -64,6 +98,31 @@ amount(Style, Pucks) ->
|
|||||||
Formatted :: string().
|
Formatted :: string().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% A simplified format function covering the most common formats desired.
|
%% A simplified format function covering the most common formats desired.
|
||||||
|
%% ```
|
||||||
|
%% hz_format:amount(gaju, us, 100500040123000004500000000) ->
|
||||||
|
%% 木100,500,040.123,000,004,5
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(puck, us, 100500040123000004500000000) ->
|
||||||
|
%% 本100,500,040,123,000,004,500,000,000
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(gaju, jp, 100500040123000004500000000) ->
|
||||||
|
%% 1億50万40木 12京3000兆45億本
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(puck, jp, 100500040123000004500000000) ->
|
||||||
|
%% 100秭5000垓4012京3000兆45億本
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(gaju, metric, 100500040123000004500000000) ->
|
||||||
|
%% 木100m 500k 40 G 123p 4g 500m P
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(puck, metric, 100500040123000004500000000) ->
|
||||||
|
%% 本100y 500z 40e 123p 4g 500m P
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(gaju, legacy, 100500040123000004500000000) ->
|
||||||
|
%% 木100m 500k 40 G 123q 4b 500m P
|
||||||
|
%%
|
||||||
|
%% hz_format:amount(puck, legacy, 100500040123000004500000000) ->
|
||||||
|
%% 本100y 500z 40e 123q 4b 500m P
|
||||||
|
%% '''
|
||||||
|
|
||||||
amount(gaju, us, Pucks) ->
|
amount(gaju, us, Pucks) ->
|
||||||
western($,, $., 3, all, Pucks);
|
western($,, $., 3, all, Pucks);
|
||||||
@ -81,66 +140,51 @@ amount(puck, {Separator, Span}, Pucks) ->
|
|||||||
western(Separator, Span, Pucks).
|
western(Separator, Span, Pucks).
|
||||||
|
|
||||||
|
|
||||||
-spec amount(Unit, Style, Precision, Pucks) -> Serialized
|
|
||||||
when Unit :: gaju | puck,
|
-spec approx_amount(Precision, Pucks) -> Serialized
|
||||||
Style :: us | jp | metric | legacy | {Separator, Span},
|
when Precision :: all | 0..18,
|
||||||
|
Pucks :: integer(),
|
||||||
|
Serialized :: string().
|
||||||
|
%% A formatter for decimal notation which permits a precision
|
||||||
|
%% value to be applied to the puck side of the format.
|
||||||
|
%% @equiv approx_amount(us, Precision, Pucks).
|
||||||
|
%% ```
|
||||||
|
%% hz_format:approx_amount(3, 100500040123000004500000001) ->
|
||||||
|
%% 木100,500,040.123...
|
||||||
|
%%
|
||||||
|
%% hz_format:approx_amount(13, 100500040123000004500000001) ->
|
||||||
|
%% 木100,500,040.123,000,004,5...
|
||||||
|
%%
|
||||||
|
%% hz_format:approx_amount(all, 100500040123000004500000001) ->
|
||||||
|
%% 木100,500,040.123,000,004,500,000,001
|
||||||
|
%% '''
|
||||||
|
|
||||||
|
approx_amount(Precision, Pucks) ->
|
||||||
|
approx_amount(us, Precision, Pucks).
|
||||||
|
|
||||||
|
|
||||||
|
-spec approx_amount(Style, Precision, Pucks) -> Serialized
|
||||||
|
when Style :: us | {Separator, Span},
|
||||||
Precision :: all | 0..18,
|
Precision :: all | 0..18,
|
||||||
Separator :: $, | $_,
|
Separator :: $, | $_,
|
||||||
Span :: 3 | 4,
|
Span :: 3 | 4,
|
||||||
Pucks :: integer(),
|
Pucks :: integer(),
|
||||||
Serialized :: string().
|
Serialized :: string().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% A flexible, if annoyingly complex, formatting function.
|
%% A formatter for decimal notation which permits a precision
|
||||||
%%
|
%% value to be applied to the puck side of the format.
|
||||||
%% ```
|
%% ```
|
||||||
%% amount(gaju, us, 3, 123456789123456789123456789) ->
|
%% hz_format:approx_amount({$_, 3}, 3, 100500040123000004500000001) ->
|
||||||
%% "木123,456,789.123...".
|
%% 木100_500_040.123...
|
||||||
%%
|
%%
|
||||||
%% amount(gaju, us, 3, 123456789123000000000000000) ->
|
%% hz_format:approx_amount({$_, 4}, 12, 100500040123000004500000001) ->
|
||||||
%% "木123,456,789.123".
|
%% 木1_0050_0040.1230_0000_45...
|
||||||
%%
|
|
||||||
%% amount(gaju, {$,, 3}, 3, 123456789123456789123456789) ->
|
|
||||||
%% "木123,456,789.123...".
|
|
||||||
%%
|
|
||||||
%% amount(gaju, {$,, 3}, 6, 123456789123000000000000000) ->
|
|
||||||
%% "木123,456,789.123"
|
|
||||||
%%
|
|
||||||
%% amount(gaju, {$_, 4}, 10, 123456789123456789123456789) ->
|
|
||||||
%% "木1_2345_6789.1234_5678_91..."
|
|
||||||
%%
|
|
||||||
%% amount(gaju, jp, 3, 123456789123456789123456789) ->
|
|
||||||
%% "1億2345万6789木 12京3000兆本"
|
|
||||||
%%
|
|
||||||
%% amount(gaju, jp, 6, 123456789123456789123456789) ->
|
|
||||||
%% "1億2345万6789木 12京3456兆本"
|
|
||||||
%%
|
|
||||||
%% amount(gaju, jp, 0, 123456789123456789123456789) ->
|
|
||||||
%% "1億2345万6789木"
|
|
||||||
%%
|
|
||||||
%% amount(puck, jp, all, 123456789123456789123456789) ->
|
|
||||||
%% "123秭4567垓8912京3456兆7891億2345万6789本"
|
|
||||||
%% '''
|
%% '''
|
||||||
|
|
||||||
amount(gaju, us, Precision, Pucks) ->
|
approx_amount(us, Precision, Pucks) ->
|
||||||
western($,, $., 3, Precision, Pucks);
|
western($,, $., 3, Precision, Pucks);
|
||||||
amount(gaju, jp, Precision, Pucks) ->
|
approx_amount({Separator, Span}, Precision, Pucks) ->
|
||||||
jp(gaju, Precision, Pucks);
|
western(Separator, $., Span, Precision, Pucks).
|
||||||
amount(gaju, metric, Precision, Pucks) ->
|
|
||||||
bestern(gaju, ranks(metric), Precision, Pucks);
|
|
||||||
amount(gaju, legacy, Precision, Pucks) ->
|
|
||||||
bestern(gaju, ranks(heresy), Precision, Pucks);
|
|
||||||
amount(gaju, {Separator, Span}, Precision, Pucks) ->
|
|
||||||
western(Separator, $., Span, Precision, Pucks);
|
|
||||||
amount(puck, us, _, Pucks) ->
|
|
||||||
western($,, 3, Pucks);
|
|
||||||
amount(puck, jp, _, Pucks) ->
|
|
||||||
jp(puck, all, Pucks);
|
|
||||||
amount(puck, metric, _, Pucks) ->
|
|
||||||
bestern(puck, ranks(metric), all, Pucks);
|
|
||||||
amount(puck, legacy, _, Pucks) ->
|
|
||||||
bestern(puck, ranks(heresy), all, Pucks);
|
|
||||||
amount(puck, {Separator, Span}, _, Pucks) ->
|
|
||||||
western(Separator, Span, Pucks).
|
|
||||||
|
|
||||||
|
|
||||||
western(Separator, Span, Pucks) when Pucks >= 0 ->
|
western(Separator, Span, Pucks) when Pucks >= 0 ->
|
||||||
@ -150,7 +194,7 @@ western(Separator, Span, Pucks) when Pucks < 0 ->
|
|||||||
|
|
||||||
western2(Separator, Span, Pucks) ->
|
western2(Separator, Span, Pucks) ->
|
||||||
P = lists:reverse(integer_to_list(Pucks)),
|
P = lists:reverse(integer_to_list(Pucks)),
|
||||||
[puck_mark() | separate(Separator, Span, P)].
|
[mark(puck) | separate(Separator, Span, P)].
|
||||||
|
|
||||||
|
|
||||||
western(Separator, Break, Span, Precision, Pucks) when Pucks >= 0 ->
|
western(Separator, Break, Span, Precision, Pucks) when Pucks >= 0 ->
|
||||||
@ -160,30 +204,30 @@ western(Separator, Break, Span, Precision, Pucks) when Pucks < 0 ->
|
|||||||
|
|
||||||
|
|
||||||
western2(Separator, _, Span, 0, Pucks) ->
|
western2(Separator, _, Span, 0, Pucks) ->
|
||||||
G = lists:reverse(integer_to_list(Pucks div one_gaju())),
|
G = lists:reverse(integer_to_list(Pucks div one(gaju))),
|
||||||
[gaju_mark() | separate(Separator, Span, G)];
|
[mark(gaju) | separate(Separator, Span, G)];
|
||||||
western2(Separator, Break, Span, Precision, Pucks) ->
|
western2(Separator, Break, Span, Precision, Pucks) ->
|
||||||
SP = integer_to_list(Pucks),
|
SP = integer_to_list(Pucks),
|
||||||
Length = length(SP),
|
Length = length(SP),
|
||||||
Over18 = Length > 18,
|
Over18 = Length > 18,
|
||||||
NoPucks = (Pucks rem one_gaju()) =:= 0,
|
NoPucks = (Pucks rem one(gaju)) =:= 0,
|
||||||
case {Over18, NoPucks} of
|
case {Over18, NoPucks} of
|
||||||
{true, true} ->
|
{true, true} ->
|
||||||
Gs = lists:reverse(lists:sublist(SP, Length - 18)),
|
Gs = lists:reverse(lists:sublist(SP, Length - 18)),
|
||||||
[gaju_mark() | separate(Separator, Span, Gs)];
|
[mark(gaju) | separate(Separator, Span, Gs)];
|
||||||
{true, false} ->
|
{true, false} ->
|
||||||
{PChars, GChars} = lists:split(18, lists:reverse(SP)),
|
{PChars, GChars} = lists:split(18, lists:reverse(SP)),
|
||||||
H = [gaju_mark() | separate(Separator, Span, GChars)],
|
H = [mark(gaju) | separate(Separator, Span, GChars)],
|
||||||
{P, E} = decimal_pucks(Precision, lists:reverse(PChars)),
|
{P, E} = decimal_pucks(Precision, lists:reverse(PChars)),
|
||||||
T = lists:reverse(separate(Separator, Span, P)),
|
T = lists:reverse(separate(Separator, Span, P)),
|
||||||
lists:flatten([H, Break, T, E]);
|
lists:flatten([H, Break, T, E]);
|
||||||
{false, true} ->
|
{false, true} ->
|
||||||
[gaju_mark(), $0];
|
[mark(gaju), $0];
|
||||||
{false, false} ->
|
{false, false} ->
|
||||||
PChars = lists:flatten(string:pad(SP, 18, leading, $0)),
|
PChars = lists:flatten(string:pad(SP, 18, leading, $0)),
|
||||||
{P, E} = decimal_pucks(Precision, PChars),
|
{P, E} = decimal_pucks(Precision, PChars),
|
||||||
T = lists:reverse(separate(Separator, Span, P)),
|
T = lists:reverse(separate(Separator, Span, P)),
|
||||||
lists:flatten([gaju_mark(), $0, Break, T, E])
|
lists:flatten([mark(gaju), $0, Break, T, E])
|
||||||
end.
|
end.
|
||||||
|
|
||||||
decimal_pucks(all, PChars) ->
|
decimal_pucks(all, PChars) ->
|
||||||
@ -212,13 +256,13 @@ separate(S, P, N, [H | T], A) ->
|
|||||||
|
|
||||||
|
|
||||||
bestern(gaju, Ranks, Precision, Pucks) when Pucks >= 0 ->
|
bestern(gaju, Ranks, Precision, Pucks) when Pucks >= 0 ->
|
||||||
[gaju_mark(), bestern2(gaju, Ranks, 3, Precision, Pucks)];
|
[mark(gaju), bestern2(gaju, Ranks, 3, Precision, Pucks)];
|
||||||
bestern(gaju, Ranks, Precision, Pucks) when Pucks < 0 ->
|
bestern(gaju, Ranks, Precision, Pucks) when Pucks < 0 ->
|
||||||
[$-, gaju_mark(), bestern2(gaju, Ranks, 3, Precision, Pucks * -1)];
|
[$-, mark(gaju), bestern2(gaju, Ranks, 3, Precision, Pucks * -1)];
|
||||||
bestern(puck, Ranks, Precision, Pucks) when Pucks >= 0 ->
|
bestern(puck, Ranks, Precision, Pucks) when Pucks >= 0 ->
|
||||||
[puck_mark(), bestern2(puck, Ranks, 3, Precision, Pucks)];
|
[mark(puck), bestern2(puck, Ranks, 3, Precision, Pucks)];
|
||||||
bestern(puck, Ranks, Precision, Pucks) when Pucks < 0 ->
|
bestern(puck, Ranks, Precision, Pucks) when Pucks < 0 ->
|
||||||
[$-, puck_mark(), bestern2(puck, Ranks, 3, Precision, Pucks * -1)].
|
[$-, mark(puck), bestern2(puck, Ranks, 3, Precision, Pucks * -1)].
|
||||||
|
|
||||||
jp(Unit, Precision, Pucks) when Pucks >= 0 ->
|
jp(Unit, Precision, Pucks) when Pucks >= 0 ->
|
||||||
bestern2(Unit, ranks(jp), 4, Precision, Pucks);
|
bestern2(Unit, ranks(jp), 4, Precision, Pucks);
|
||||||
@ -226,24 +270,24 @@ jp(Unit, Precision, Pucks) when Pucks < 0 ->
|
|||||||
[$-, bestern2(Unit, ranks(jp), 4, Precision, Pucks * -1)].
|
[$-, bestern2(Unit, ranks(jp), 4, Precision, Pucks * -1)].
|
||||||
|
|
||||||
bestern2(gaju, Ranks, Span, 0, Pucks) ->
|
bestern2(gaju, Ranks, Span, 0, Pucks) ->
|
||||||
G = lists:reverse(integer_to_list(Pucks div one_gaju())),
|
G = lists:reverse(integer_to_list(Pucks div one(gaju))),
|
||||||
case Span of
|
case Span of
|
||||||
3 -> period("G", Ranks, G);
|
3 -> period("G", Ranks, G);
|
||||||
4 -> myriad(gaju_mark(), Ranks, G)
|
4 -> myriad(mark(gaju), Ranks, G)
|
||||||
end;
|
end;
|
||||||
bestern2(gaju, Ranks, Span, all, Pucks) ->
|
bestern2(gaju, Ranks, Span, all, Pucks) ->
|
||||||
P = lists:flatten(string:pad(integer_to_list(Pucks rem one_gaju()), 18, leading, $0)),
|
P = lists:flatten(string:pad(integer_to_list(Pucks rem one(gaju)), 18, leading, $0)),
|
||||||
Zilch = lists:all(fun(C) -> C =:= $0 end, P),
|
Zilch = lists:all(fun(C) -> C =:= $0 end, P),
|
||||||
{H, T} =
|
{H, T} =
|
||||||
case {Span, Zilch} of
|
case {Span, Zilch} of
|
||||||
{3, false} -> {bestern2(gaju, Ranks, 3, 0, Pucks), period("P", Ranks, lists:reverse(P))};
|
{3, false} -> {bestern2(gaju, Ranks, 3, 0, Pucks), period("P", Ranks, lists:reverse(P))};
|
||||||
{4, false} -> {jp(gaju, 0, Pucks), myriad(puck_mark(), Ranks, lists:reverse(P))};
|
{4, false} -> {jp(gaju, 0, Pucks), myriad(mark(puck), Ranks, lists:reverse(P))};
|
||||||
{3, true} -> {bestern2(gaju, Ranks, 3, 0, Pucks), ""};
|
{3, true} -> {bestern2(gaju, Ranks, 3, 0, Pucks), ""};
|
||||||
{4, true} -> {jp(gaju, 0, Pucks), ""}
|
{4, true} -> {jp(gaju, 0, Pucks), ""}
|
||||||
end,
|
end,
|
||||||
lists:flatten([H, " ", T]);
|
lists:flatten([H, " ", T]);
|
||||||
bestern2(gaju, Ranks, Span, Precision, Pucks) ->
|
bestern2(gaju, Ranks, Span, Precision, Pucks) ->
|
||||||
P = lists:flatten(string:pad(integer_to_list(Pucks rem one_gaju()), 18, leading, $0)),
|
P = lists:flatten(string:pad(integer_to_list(Pucks rem one(gaju)), 18, leading, $0)),
|
||||||
H =
|
H =
|
||||||
case Span of
|
case Span of
|
||||||
3 -> bestern2(gaju, Ranks, 3, 0, Pucks);
|
3 -> bestern2(gaju, Ranks, 3, 0, Pucks);
|
||||||
@ -259,7 +303,7 @@ bestern2(gaju, Ranks, Span, Precision, Pucks) ->
|
|||||||
false ->
|
false ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> period("P", Ranks, PuckingString);
|
3 -> period("P", Ranks, PuckingString);
|
||||||
4 -> myriad(puck_mark(), Ranks, PuckingString)
|
4 -> myriad(mark(puck), Ranks, PuckingString)
|
||||||
end;
|
end;
|
||||||
true ->
|
true ->
|
||||||
""
|
""
|
||||||
@ -274,12 +318,12 @@ bestern2(puck, Ranks, Span, all, Pucks) ->
|
|||||||
false ->
|
false ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> period("P", Ranks, P);
|
3 -> period("P", Ranks, P);
|
||||||
4 -> myriad(puck_mark(), Ranks, P)
|
4 -> myriad(mark(puck), Ranks, P)
|
||||||
end;
|
end;
|
||||||
true ->
|
true ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> [$0, " P"];
|
3 -> [$0, " P"];
|
||||||
4 -> [$0, puck_mark()]
|
4 -> [$0, mark(puck)]
|
||||||
end
|
end
|
||||||
end;
|
end;
|
||||||
bestern2(puck, Ranks, Span, Precision, Pucks) ->
|
bestern2(puck, Ranks, Span, Precision, Pucks) ->
|
||||||
@ -289,7 +333,7 @@ bestern2(puck, Ranks, Span, Precision, Pucks) ->
|
|||||||
true ->
|
true ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> [$0, " P"];
|
3 -> [$0, " P"];
|
||||||
4 -> [$0, puck_mark()]
|
4 -> [$0, mark(puck)]
|
||||||
end;
|
end;
|
||||||
false ->
|
false ->
|
||||||
PucksToGive = lists:sublist(P, Digits),
|
PucksToGive = lists:sublist(P, Digits),
|
||||||
@ -298,12 +342,12 @@ bestern2(puck, Ranks, Span, Precision, Pucks) ->
|
|||||||
false ->
|
false ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> period("P", Ranks, PuckingString);
|
3 -> period("P", Ranks, PuckingString);
|
||||||
4 -> myriad(puck_mark(), Ranks, PuckingString)
|
4 -> myriad(mark(puck), Ranks, PuckingString)
|
||||||
end;
|
end;
|
||||||
true ->
|
true ->
|
||||||
case Span of
|
case Span of
|
||||||
3 -> [$0, " P"];
|
3 -> [$0, " P"];
|
||||||
4 -> [$0, puck_mark()]
|
4 -> [$0, mark(puck)]
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end.
|
end.
|
||||||
@ -418,11 +462,11 @@ ranks(heresy) ->
|
|||||||
["k ", "m ", "b ", "t ", "q ", "e ", "z ", "y ", "r ", "Q "].
|
["k ", "m ", "b ", "t ", "q ", "e ", "z ", "y ", "r ", "Q "].
|
||||||
|
|
||||||
|
|
||||||
gaju_mark() -> $木.
|
mark(gaju) -> $木;
|
||||||
|
mark(puck) -> $本.
|
||||||
|
|
||||||
puck_mark() -> $本.
|
one(gaju) -> 1_000_000_000_000_000_000;
|
||||||
|
one(puck) -> 1.
|
||||||
one_gaju() -> 1_000_000_000_000_000_000.
|
|
||||||
|
|
||||||
|
|
||||||
-spec read(Format) -> Result
|
-spec read(Format) -> Result
|
||||||
@ -430,10 +474,26 @@ one_gaju() -> 1_000_000_000_000_000_000.
|
|||||||
Result :: {ok, Pucks} | error,
|
Result :: {ok, Pucks} | error,
|
||||||
Pucks :: integer().
|
Pucks :: integer().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% Convery any valid string formatted representation and output a value in pucks.
|
%% Convert any valid string formatted representation and output a value in pucks.
|
||||||
%% This routine can fail in the special case of `ch' style formatting with a single
|
%% NOTE: This function does not accept approximated values.
|
||||||
%% comma and/or a single period in it, as this can trigger misinterpretation as `us'
|
%% ```
|
||||||
%% style. When in doubt, always call `read/2' with a style specified.
|
%% 1> hz_format:read("木100,500,040.123,000,004,5").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 2> hz_format:read("本100,500,040,123,000,004,500,000,000").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 3> hz_format:read("1億50万40木 12京3000兆45億本").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 4> hz_format:read("100秭5000垓4012京3000兆45億本").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 5> hz_format:read("木100m 500k 40 G 123p 4g 500m P").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 6> hz_format:read("本100y 500z 40e 123p 4g 500m P").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 7> hz_format:read("木100m 500k 40 G 123q 4b 500m P").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% 8> hz_format:read("本100y 500z 40e 123q 4b 500m P").
|
||||||
|
%% {ok,100500040123000004500000000}
|
||||||
|
%% '''
|
||||||
|
|
||||||
read([$木 | Rest]) ->
|
read([$木 | Rest]) ->
|
||||||
read_w_gajus(Rest, []);
|
read_w_gajus(Rest, []);
|
||||||
@ -459,6 +519,8 @@ read([C | Rest]) when $0 =< C andalso C =< $9 ->
|
|||||||
read([C | Rest]) when $0 =< C andalso C =< $9 ->
|
read([C | Rest]) when $0 =< C andalso C =< $9 ->
|
||||||
NumC = C - $0 + $0,
|
NumC = C - $0 + $0,
|
||||||
read(Rest, [NumC], []);
|
read(Rest, [NumC], []);
|
||||||
|
read(String) when is_binary(String) ->
|
||||||
|
read(binary_to_list(String));
|
||||||
read(_) ->
|
read(_) ->
|
||||||
error.
|
error.
|
||||||
|
|
||||||
@ -474,13 +536,13 @@ read_w_gajus([$_ | Rest], A) ->
|
|||||||
read_w_gajus([$. | Rest], A) ->
|
read_w_gajus([$. | Rest], A) ->
|
||||||
case read_w_pucks(Rest, []) of
|
case read_w_pucks(Rest, []) of
|
||||||
{ok, P} ->
|
{ok, P} ->
|
||||||
G = list_to_integer(lists:reverse(A)) * one_gaju(),
|
G = list_to_integer(lists:reverse(A)) * one(gaju),
|
||||||
{ok, G + P};
|
{ok, G + P};
|
||||||
Error ->
|
Error ->
|
||||||
Error
|
Error
|
||||||
end;
|
end;
|
||||||
read_w_gajus([], A) ->
|
read_w_gajus([], A) ->
|
||||||
G = list_to_integer(lists:reverse(A)) * one_gaju(),
|
G = list_to_integer(lists:reverse(A)) * one(gaju),
|
||||||
{ok, G};
|
{ok, G};
|
||||||
read_w_gajus([C, 32 | Rest], A) ->
|
read_w_gajus([C, 32 | Rest], A) ->
|
||||||
read(Rest, [], [{C, A}]);
|
read(Rest, [], [{C, A}]);
|
||||||
@ -488,7 +550,10 @@ read_w_gajus([32, $G, 32 | Rest], A) ->
|
|||||||
read(Rest, [], [{$G, A}], []);
|
read(Rest, [], [{$G, A}], []);
|
||||||
read_w_gajus([32, $G], A) ->
|
read_w_gajus([32, $G], A) ->
|
||||||
calc([{$G, A}], []);
|
calc([{$G, A}], []);
|
||||||
read_w_gajus(_, _) ->
|
read_w_gajus([32, $P], A) ->
|
||||||
|
calc([], [{$P, A}]);
|
||||||
|
read_w_gajus(A, B) ->
|
||||||
|
io:format("A: ~ts, B: ~p~n", [A, B]),
|
||||||
error.
|
error.
|
||||||
|
|
||||||
read_w_pucks([C | Rest], A) when $0 =< C andalso C =< $9 ->
|
read_w_pucks([C | Rest], A) when $0 =< C andalso C =< $9 ->
|
||||||
@ -500,6 +565,10 @@ read_w_pucks([$, | Rest], A) ->
|
|||||||
read_w_pucks(Rest, A);
|
read_w_pucks(Rest, A);
|
||||||
read_w_pucks([$_ | Rest], A) ->
|
read_w_pucks([$_ | Rest], A) ->
|
||||||
read_w_pucks(Rest, A);
|
read_w_pucks(Rest, A);
|
||||||
|
read_w_pucks([C, 32 | Rest], A) ->
|
||||||
|
read(Rest, [], [], [{C, A}]);
|
||||||
|
read_w_pucks([32, $P], A) ->
|
||||||
|
calc([], [{$P, A}]);
|
||||||
read_w_pucks([], A) ->
|
read_w_pucks([], A) ->
|
||||||
Padded = lists:flatten(string:pad(lists:reverse(A), 18, trailing, $0)),
|
Padded = lists:flatten(string:pad(lists:reverse(A), 18, trailing, $0)),
|
||||||
{ok, list_to_integer(Padded)}.
|
{ok, list_to_integer(Padded)}.
|
||||||
@ -514,6 +583,10 @@ read([$木], A, G) ->
|
|||||||
calc([{$G, A} | G], []);
|
calc([{$G, A} | G], []);
|
||||||
read([$G], A, G) ->
|
read([$G], A, G) ->
|
||||||
calc([{$G, A} | G], []);
|
calc([{$G, A} | G], []);
|
||||||
|
read([32, $G], A, G) ->
|
||||||
|
calc([{$G, A} | G], []);
|
||||||
|
read([32, $G, 32 | Rest], A, G) ->
|
||||||
|
read(Rest, [], [{$G, A} | G], []);
|
||||||
read([$木, 32 | Rest], A, G) ->
|
read([$木, 32 | Rest], A, G) ->
|
||||||
read(Rest, [], [{$G, A} | G], []);
|
read(Rest, [], [{$G, A} | G], []);
|
||||||
read([$G, 32 | Rest], A, G) ->
|
read([$G, 32 | Rest], A, G) ->
|
||||||
@ -522,6 +595,8 @@ read([$本], A, P) ->
|
|||||||
calc([], [{$P, A} | P]);
|
calc([], [{$P, A} | P]);
|
||||||
read([$P], A, P) ->
|
read([$P], A, P) ->
|
||||||
calc([], [{$P, A} | P]);
|
calc([], [{$P, A} | P]);
|
||||||
|
read([32, $P], A, P) ->
|
||||||
|
calc([], [{$P, A} | P]);
|
||||||
read([C, 32 | Rest], A, G) ->
|
read([C, 32 | Rest], A, G) ->
|
||||||
read(Rest, [], [{C, A} | G]);
|
read(Rest, [], [{C, A} | G]);
|
||||||
read([C | Rest], A, G) ->
|
read([C | Rest], A, G) ->
|
||||||
@ -540,6 +615,8 @@ read([$本], A, G, P) ->
|
|||||||
calc(G, [{$P, A} | P]);
|
calc(G, [{$P, A} | P]);
|
||||||
read([$P], A, G, P) ->
|
read([$P], A, G, P) ->
|
||||||
calc(G, [{$P, A} | P]);
|
calc(G, [{$P, A} | P]);
|
||||||
|
read([32, $P], A, G, P) ->
|
||||||
|
calc(G, [{$P, A} | P]);
|
||||||
read([C, 32 | Rest], A, G, P) ->
|
read([C, 32 | Rest], A, G, P) ->
|
||||||
read(Rest, [], G, [{C, A} | P]);
|
read(Rest, [], G, [{C, A} | P]);
|
||||||
read([C | Rest], A, G, P) ->
|
read([C | Rest], A, G, P) ->
|
||||||
@ -564,7 +641,7 @@ calc(U, [{_, []} | S], A) ->
|
|||||||
calc(U, [{M, Cs} | S], A) ->
|
calc(U, [{M, Cs} | S], A) ->
|
||||||
case magnitude(M) of
|
case magnitude(M) of
|
||||||
{ok, J} ->
|
{ok, J} ->
|
||||||
N = list_to_integer(lists:reverse(Cs)) * J * unit(U),
|
N = list_to_integer(lists:reverse(Cs)) * J * one(U),
|
||||||
calc(U, S, A + N);
|
calc(U, S, A + N);
|
||||||
Error ->
|
Error ->
|
||||||
Error
|
Error
|
||||||
@ -572,9 +649,6 @@ calc(U, [{M, Cs} | S], A) ->
|
|||||||
calc(_, [], A) ->
|
calc(_, [], A) ->
|
||||||
{ok, A}.
|
{ok, A}.
|
||||||
|
|
||||||
unit(gaju) -> one_gaju();
|
|
||||||
unit(puck) -> 1.
|
|
||||||
|
|
||||||
|
|
||||||
magnitude($G) ->
|
magnitude($G) ->
|
||||||
{ok, 1};
|
{ok, 1};
|
||||||
@ -607,7 +681,7 @@ rank(_, [], _, _) ->
|
|||||||
%% in Gajus. Useful for formatting generic output for UI elements
|
%% in Gajus. Useful for formatting generic output for UI elements
|
||||||
|
|
||||||
price_to_string(Pucks) ->
|
price_to_string(Pucks) ->
|
||||||
Gaju = 1_000_000_000_000_000_000,
|
Gaju = one(gaju),
|
||||||
H = integer_to_list(Pucks div Gaju),
|
H = integer_to_list(Pucks div Gaju),
|
||||||
R = Pucks rem Gaju,
|
R = Pucks rem Gaju,
|
||||||
case string:strip(lists:flatten(io_lib:format("~18..0w", [R])), right, $0) of
|
case string:strip(lists:flatten(io_lib:format("~18..0w", [R])), right, $0) of
|
||||||
|
|||||||
@ -38,14 +38,14 @@
|
|||||||
|
|
||||||
-module(hz_grids).
|
-module(hz_grids).
|
||||||
-vsn("0.7.0").
|
-vsn("0.7.0").
|
||||||
-export([url/2, parse/1, req/2, req/3]).
|
-export([url/2, url/3, url/4, parse/1, req/2, req/3]).
|
||||||
|
|
||||||
|
|
||||||
-spec url(Instruction, HTTP) -> Result
|
-spec url(Instruction, HTTP) -> Result
|
||||||
when Instruction :: spend | transfer | sign,
|
when Instruction :: spend | transfer | sign,
|
||||||
HTTP :: uri_string:uri_string(),
|
HTTP :: uri_string:uri_string(),
|
||||||
GRIDS :: uri_string:uri_string(),
|
Result :: {ok, GRIDS} | uri_string:uri_error(),
|
||||||
Result :: {ok, GRIDS} | uri_string:uri_error().
|
GRIDS :: uri_string:uri_string().
|
||||||
%% @doc
|
%% @doc
|
||||||
%% Takes
|
%% Takes
|
||||||
|
|
||||||
@ -66,6 +66,63 @@ url2(Instruction, URL = #{path := Path}) ->
|
|||||||
{ok, uri_string:recompose(GRIDS)}.
|
{ok, uri_string:recompose(GRIDS)}.
|
||||||
|
|
||||||
|
|
||||||
|
-spec url(Instruction, Recipient, Amount) -> GRIDS
|
||||||
|
when Instruction :: {spend, Network} | {transfer, Node},
|
||||||
|
Network :: string(),
|
||||||
|
Node :: {inet:ip_address() | inet:hostname(), inet:port_number()}
|
||||||
|
| uri_string:uri_string(),
|
||||||
|
Recipient :: string(),
|
||||||
|
Amount :: non_neg_integer(),
|
||||||
|
GRIDS :: uri_string:uri_string().
|
||||||
|
%% @doc
|
||||||
|
%% Forms a GRIDS URL for spends or transfers.
|
||||||
|
%% @equiv uri(Instruction, Recipient, Amount, "").
|
||||||
|
|
||||||
|
url(Instruction, Recipient, Amount) ->
|
||||||
|
url(Instruction, Recipient, Amount, "").
|
||||||
|
|
||||||
|
|
||||||
|
-spec url(Instruction, Recipient, Amount, Payload) -> GRIDS
|
||||||
|
when Instruction :: {spend, Network} | {transfer, Node},
|
||||||
|
Network :: string(),
|
||||||
|
Node :: {inet:ip_address() | inet:hostname(), inet:port_number()}
|
||||||
|
| uri_string:uri_string(), % "http://..." | "https://..."
|
||||||
|
Recipient :: string(),
|
||||||
|
Amount :: non_neg_integer() | none,
|
||||||
|
Payload :: binary(),
|
||||||
|
GRIDS :: uri_string:uri_string().
|
||||||
|
%% @doc
|
||||||
|
%% Forms a GRIDS URL for spends or transfers.
|
||||||
|
|
||||||
|
url({spend, Network}, Recipient, Amount, Payload) ->
|
||||||
|
Elements = ["grids://", Network, "/1/s/", Recipient, qwargs(Amount, Payload)],
|
||||||
|
unicode:characters_to_list(Elements);
|
||||||
|
url({transfer, Node}, Recipient, Amount, Payload) ->
|
||||||
|
Prefix =
|
||||||
|
case Node of
|
||||||
|
{H, P} -> ["grid://", h_to_s(H), ":", integer_to_list(P)];
|
||||||
|
"https://" ++ H -> ["grids://", H];
|
||||||
|
"http://" ++ H -> ["grid://", H];
|
||||||
|
<<"https://", H/binary>> -> ["grids://", H];
|
||||||
|
<<"http://", H/binary>> -> ["grid://", H]
|
||||||
|
end,
|
||||||
|
unicode:characters_to_list([Prefix, "/1/t/", Recipient, qwargs(Amount, Payload)]).
|
||||||
|
|
||||||
|
h_to_s(Host) when is_list(Host) -> Host;
|
||||||
|
h_to_s(Host) when is_binary(Host) -> Host;
|
||||||
|
h_to_s(Host) when is_tuple(Host) -> inet:ntoa(Host);
|
||||||
|
h_to_s(Host) when is_atom(Host) -> atom_to_list(Host).
|
||||||
|
|
||||||
|
qwargs(none, "") ->
|
||||||
|
[];
|
||||||
|
qwargs(Amount, "") ->
|
||||||
|
["?a=", integer_to_list(Amount)];
|
||||||
|
qwargs(none, Payload) ->
|
||||||
|
[$? | uri_string:compose_query([{"p", Payload}])];
|
||||||
|
qwargs(Amount, Payload) ->
|
||||||
|
[$? | uri_string:compose_query([{"a", integer_to_list(Amount)}, {"p", Payload}])].
|
||||||
|
|
||||||
|
|
||||||
-spec parse(GRIDS) -> Result
|
-spec parse(GRIDS) -> Result
|
||||||
when GRIDS :: string(),
|
when GRIDS :: string(),
|
||||||
Result :: {ok, Instruction} | uri_string:error(),
|
Result :: {ok, Instruction} | uri_string:error(),
|
||||||
|
|||||||
@ -20,6 +20,9 @@
|
|||||||
chain_nodes/0, chain_nodes/1,
|
chain_nodes/0, chain_nodes/1,
|
||||||
timeout/0, timeout/1]).
|
timeout/0, timeout/1]).
|
||||||
|
|
||||||
|
%% Contract caching
|
||||||
|
-export([cache_aaci/2, lookup_aaci/1]).
|
||||||
|
|
||||||
%% The whole point of this module:
|
%% The whole point of this module:
|
||||||
-export([request_sticky/1, request_sticky/2, request/1, request/2]).
|
-export([request_sticky/1, request_sticky/2, request/1, request/2]).
|
||||||
|
|
||||||
@ -44,7 +47,8 @@
|
|||||||
chain_nodes = {[], []} :: {[hz:chain_node()], [hz:chain_node()]},
|
chain_nodes = {[], []} :: {[hz:chain_node()], [hz:chain_node()]},
|
||||||
sticky = none :: none | hz:chain_node(),
|
sticky = none :: none | hz:chain_node(),
|
||||||
fetchers = [] :: [#fetcher{}],
|
fetchers = [] :: [#fetcher{}],
|
||||||
timeout = 5000 :: pos_integer()}).
|
timeout = 5000 :: pos_integer(),
|
||||||
|
cache = #{} :: #{Label :: term() := AACI :: hz:aaci()}}).
|
||||||
|
|
||||||
|
|
||||||
-type state() :: #s{}.
|
-type state() :: #s{}.
|
||||||
@ -94,6 +98,22 @@ timeout(Value) when 0 < Value, Value =< 120000 ->
|
|||||||
gen_server:cast(?MODULE, {timeout, Value}).
|
gen_server:cast(?MODULE, {timeout, Value}).
|
||||||
|
|
||||||
|
|
||||||
|
-spec cache_aaci(Label, AACI) -> ok
|
||||||
|
when Label :: term(),
|
||||||
|
AACI :: hz:aaci().
|
||||||
|
|
||||||
|
cache_aaci(Label, AACI) ->
|
||||||
|
gen_server:call(?MODULE, {cache, Label, AACI}).
|
||||||
|
|
||||||
|
|
||||||
|
-spec lookup_aaci(Label) -> Result
|
||||||
|
when Label :: term(),
|
||||||
|
Result :: {ok, hz:aaci()} | error.
|
||||||
|
|
||||||
|
lookup_aaci(Label) ->
|
||||||
|
gen_server:call(?MODULE, {lookup, Label}).
|
||||||
|
|
||||||
|
|
||||||
-spec request_sticky(Path) -> {ok, Value} | {error, Reason}
|
-spec request_sticky(Path) -> {ok, Value} | {error, Reason}
|
||||||
when Path :: unicode:charlist(),
|
when Path :: unicode:charlist(),
|
||||||
Value :: map(),
|
Value :: map(),
|
||||||
@ -167,6 +187,12 @@ handle_call({request, Request}, From, State) ->
|
|||||||
handle_call({request_sticky, Request}, From, State) ->
|
handle_call({request_sticky, Request}, From, State) ->
|
||||||
NewState = do_request_sticky(Request, From, State),
|
NewState = do_request_sticky(Request, From, State),
|
||||||
{noreply, NewState};
|
{noreply, NewState};
|
||||||
|
handle_call({lookup, Label}, _, State) ->
|
||||||
|
Result = do_lookup(Label, State),
|
||||||
|
{reply, Result, State};
|
||||||
|
handle_call({cache, Label, AACI}, _, State) ->
|
||||||
|
NewState = do_cache_aaci(Label, AACI, State),
|
||||||
|
{reply, ok, NewState};
|
||||||
handle_call(tls, _, State = #s{tls = TLS}) ->
|
handle_call(tls, _, State = #s{tls = TLS}) ->
|
||||||
{reply, TLS, State};
|
{reply, TLS, State};
|
||||||
handle_call(chain_nodes, _, State) ->
|
handle_call(chain_nodes, _, State) ->
|
||||||
@ -265,6 +291,15 @@ do_tls(_, State) ->
|
|||||||
State.
|
State.
|
||||||
|
|
||||||
|
|
||||||
|
do_cache_aaci(Label, AACI, State = #s{cache = Cache}) ->
|
||||||
|
NewCache = maps:put(Label, AACI, Cache),
|
||||||
|
State#s{cache = NewCache}.
|
||||||
|
|
||||||
|
|
||||||
|
do_lookup(Label, #s{cache = Cache}) ->
|
||||||
|
maps:find(Label, Cache).
|
||||||
|
|
||||||
|
|
||||||
do_request_sticky(_, From, State = #s{sticky = none}) ->
|
do_request_sticky(_, From, State = #s{sticky = none}) ->
|
||||||
ok = gen_server:reply(From, {error, no_nodes}),
|
ok = gen_server:reply(From, {error, no_nodes}),
|
||||||
State;
|
State;
|
||||||
|
|||||||
@ -19,6 +19,6 @@
|
|||||||
{copyright,"Craig Everett"}.
|
{copyright,"Craig Everett"}.
|
||||||
{file_exts,[]}.
|
{file_exts,[]}.
|
||||||
{license,"MIT"}.
|
{license,"MIT"}.
|
||||||
{repo_url,"https://gitlab.com/ioecs/hakuzaru"}.
|
{repo_url,"https://git.qpq.swiss/QPQ-AG/hakuzaru"}.
|
||||||
{tags,["qpq","gajumaru","blockchain","hakuzaru","crypto","defi"]}.
|
{tags,["qpq","gajumaru","blockchain","hakuzaru","crypto","defi"]}.
|
||||||
{ws_url,"https://gitlab.com/ioecs/hakuzaru"}.
|
{ws_url,"https://git.qpq.swiss/QPQ-AG/hakuzaru"}.
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user