./ct_report/coverage/mod_muc_light_room_config.COVER.html

1 %%%----------------------------------------------------------------------
2 %%% File : mod_muc_light_room_config.erl
3 %%% Author : Piotr Nosek <piotr.nosek@erlang-solutions.com>
4 %%% Purpose : Stateless utilities for room config processing
5 %%% Created : 15 Nov 2019 by Piotr Nosek <piotr.nosek@erlang-solutions.com>
6 %%%
7 %%% This program is free software; you can redistribute it and/or
8 %%% modify it under the terms of the GNU General Public License as
9 %%% published by the Free Software Foundation; either version 2 of the
10 %%% License, or (at your option) any later version.
11 %%%
12 %%% This program is distributed in the hope that it will be useful,
13 %%% but WITHOUT ANY WARRANTY; without even the implied warranty of
14 %%% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 %%% General Public License for more details.
16 %%%
17 %%% You should have received a copy of the GNU General Public License
18 %%% along with this program; if not, write to the Free Software
19 %%% Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20 %%%
21 %%%----------------------------------------------------------------------
22
23 -module(mod_muc_light_room_config).
24
25 %% API
26 -export([from_binary_kv_diff/2, from_binary_kv/2, to_binary_kv/2]).
27
28 -include("mod_muc_light.hrl").
29
30 -export_type([binary_kv/0, kv/0, schema/0]).
31
32 %% Config primitives
33 -type key() :: atom().
34 -type value() :: binary() | integer() | float().
35 -type value_type() :: binary | integer | float.
36
37 %% Actual config
38 -type item() :: {key(), value()}.
39 -type kv() :: [item()].
40 -type binary_kv() :: [{Key :: binary(), Value :: binary()}].
41
42 %% User definition processing
43 -type schema_item() :: {FieldName :: binary(), DefaultValue :: value(),
44 key(), value_type()}.
45 -type schema() :: [schema_item()]. % has to be sorted
46
47 %%====================================================================
48 %% API
49 %%====================================================================
50
51 %% Guarantees that config will have unique fields
52 -spec from_binary_kv_diff(RawConfig :: binary_kv(), ConfigSchema :: schema()) ->
53 {ok, kv()} | validation_error().
54 from_binary_kv_diff(RawConfig, ConfigSchema) ->
55 23 from_binary_kv_diff(lists:ukeysort(1, RawConfig), ConfigSchema, []).
56
57 from_binary_kv_diff([], [], Config) ->
58
:-(
{ok, Config};
59 from_binary_kv_diff(RawConfig, ConfigSchema, Config) ->
60 23 case take_next_kv(RawConfig, ConfigSchema) of
61 {error, Reason} ->
62
:-(
{error, Reason};
63 {value, RRawConfig, RConfigSchema, KV} ->
64 16 from_binary_kv(RRawConfig, RConfigSchema, [KV | Config]);
65 {default, _, _, _} ->
66 % do not populate the diff with default values
67 7 from_binary_kv(RawConfig, ConfigSchema, Config)
68 end.
69
70 -spec from_binary_kv(RawConfig :: binary_kv(), ConfigSchema :: schema()) ->
71 {ok, kv()} | validation_error().
72 from_binary_kv(RawConfig, ConfigSchema) ->
73 196 from_binary_kv(lists:ukeysort(1, RawConfig), ConfigSchema, []).
74
75 from_binary_kv([], [], Config) ->
76 218 {ok, Config};
77 from_binary_kv(RawConfig, ConfigSchema, Config) ->
78 423 case take_next_kv(RawConfig, ConfigSchema) of
79 {error, Reason} ->
80 1 {error, Reason};
81 {_, RRawConfig, RConfigSchema, KV} ->
82 422 from_binary_kv(RRawConfig, RConfigSchema, [KV | Config])
83 end.
84
85 take_next_kv([{KeyBin, ValBin} | RRawConfig], [{KeyBin, _Default, Key, Type} | RSchema]) ->
86 156 {value, RRawConfig, RSchema, {Key, b2value(ValBin, Type)}};
87 take_next_kv(RawConfig, [{_KeyBin, Default, Key, _Type} | RSchema]) ->
88 289 {default, RawConfig, RSchema, {Key, Default}};
89 take_next_kv([{KeyBin, _} | _], _) ->
90 1 {error, {KeyBin, not_found}}.
91
92 -spec to_binary_kv(Config :: kv(), ConfigSchema :: schema()) -> binary_kv().
93 to_binary_kv(Config, ConfigSchema) ->
94 23 ConfigWithSchema = lists:zip(lists:sort(Config), lists:keysort(3, ConfigSchema)),
95 23 [{KeyBin, value2b(Val, Type)} || {{Key, Val}, {KeyBin, _Default, Key, Type}} <- ConfigWithSchema].
96
97 %%====================================================================
98 %% Internal functions
99 %%====================================================================
100
101 -spec b2value(ValBin :: binary(), Type :: value_type()) -> Converted :: value().
102 156 b2value(ValBin, binary) -> ValBin;
103
:-(
b2value(ValBin, integer) -> binary_to_integer(ValBin);
104
:-(
b2value(ValBin, float) -> binary_to_float(ValBin).
105
106 -spec value2b(Val :: value(), Type :: value_type()) -> Converted :: binary().
107 46 value2b(Val, binary) -> Val;
108
:-(
value2b(Val, integer) -> integer_to_binary(Val);
109
:-(
value2b(Val, float) -> float_to_binary(Val).
Line Hits Source