%%-*- mode: erlang -*-
%% emqx_management config mapping

{mapping, "management.max_row_limit", "emqx_management.max_row_limit", [
  {default, 10000},
  {datatype, integer}
]}.

{mapping, "management.default_application.id", "emqx_management.default_application_id", [
  {default, undefined},
  {datatype, string}
]}.

{mapping, "management.default_application.secret", "emqx_management.default_application_secret", [
  {default, undefined},
  {datatype, string}
]}.

{mapping, "management.application.default_secret", "emqx_management.application", [
  {default, undefined},
  {datatype, string}
]}.

{mapping, "management.listener.http", "emqx_management.listeners", [
  {datatype, [integer, ip]}
]}.

{mapping, "management.listener.http.acceptors", "emqx_management.listeners", [
  {default, 4},
  {datatype, integer}
]}.

{mapping, "management.listener.http.max_clients", "emqx_management.listeners", [
  {default, 512},
  {datatype, integer}
]}.

{mapping, "management.listener.http.backlog", "emqx_management.listeners", [
  {default, 1024},
  {datatype, integer}
]}.

{mapping, "management.listener.http.send_timeout", "emqx_management.listeners", [
  {datatype, {duration, ms}},
  {default, "15s"}
]}.

{mapping, "management.listener.http.send_timeout_close", "emqx_management.listeners", [
  {datatype, flag},
  {default, on}
]}.

{mapping, "management.listener.http.recbuf", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.http.sndbuf", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.http.buffer", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.http.tune_buffer", "emqx_management.listeners", [
  {datatype, flag},
  hidden
]}.

{mapping, "management.listener.http.nodelay", "emqx_management.listeners", [
  {datatype, {enum, [true, false]}},
  hidden
]}.

{mapping, "management.listener.http.inet6", "emqx_management.listeners", [
  {default, false},
  {datatype, {enum, [true, false]}}
]}.

{mapping, "management.listener.http.ipv6_v6only", "emqx_management.listeners", [
  {default, false},
  {datatype, {enum, [true, false]}}
]}.

{mapping, "management.listener.https", "emqx_management.listeners", [
  {datatype, [integer, ip]}
]}.

{mapping, "management.listener.https.acceptors", "emqx_management.listeners", [
  {default, 8},
  {datatype, integer}
]}.

{mapping, "management.listener.https.max_clients", "emqx_management.listeners", [
  {default, 64},
  {datatype, integer}
]}.

{mapping, "management.listener.https.backlog", "emqx_management.listeners", [
  {default, 1024},
  {datatype, integer}
]}.

{mapping, "management.listener.https.send_timeout", "emqx_management.listeners", [
  {datatype, {duration, ms}},
  {default, "15s"}
]}.

{mapping, "management.listener.https.send_timeout_close", "emqx_management.listeners", [
  {datatype, flag},
  {default, on}
]}.

{mapping, "management.listener.https.recbuf", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.https.sndbuf", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.https.buffer", "emqx_management.listeners", [
  {datatype, bytesize},
  hidden
]}.

{mapping, "management.listener.https.tune_buffer", "emqx_management.listeners", [
  {datatype, flag},
  hidden
]}.

{mapping, "management.listener.https.nodelay", "emqx_management.listeners", [
  {datatype, {enum, [true, false]}},
  hidden
]}.

{mapping, "management.listener.https.keyfile", "emqx_management.listeners", [
  {datatype, string}
]}.

{mapping, "management.listener.https.certfile", "emqx_management.listeners", [
  {datatype, string}
]}.

{mapping, "management.listener.https.cacertfile", "emqx_management.listeners", [
  {datatype, string}
]}.

{mapping, "management.listener.https.verify", "emqx_management.listeners", [
  {datatype, atom}
]}.

{mapping, "management.listener.https.ciphers", "emqx_management.listeners", [
  {datatype, string}
]}.

{mapping, "management.listener.https.tls_versions", "emqx_management.listeners", [
  {datatype, string}
]}.

{mapping, "management.listener.https.fail_if_no_peer_cert", "emqx_management.listeners", [
  {datatype, {enum, [true, false]}}
]}.

{mapping, "management.listener.https.inet6", "emqx_management.listeners", [
  {default, false},
  {datatype, {enum, [true, false]}}
]}.

{mapping, "management.listener.https.ipv6_v6only", "emqx_management.listeners", [
  {default, false},
  {datatype, {enum, [true, false]}}
]}.

{translation, "emqx_management.application", fun(Conf) ->
  Filter = fun(Opts) -> [{K, V} || {K, V} <- Opts, V =/= undefined] end,
  Opts = fun(Prefix) ->
            Filter([{default_secret, cuttlefish:conf_get(Prefix ++ ".default_secret", Conf)}])
         end,
  Prefix = "management.application",
  Transfer = fun(default_secret, V) -> list_to_binary(V);
                (_, V) -> V
             end,
  [{K, Transfer(K, V)}|| {K, V} <- Opts(Prefix)]
end}.

{translation, "emqx_management.listeners", fun(Conf) ->
  Filter = fun(Opts) -> [{K, V} || {K, V} <- Opts, V =/= undefined] end,
  Opts = fun(Prefix) ->
             Filter([{num_acceptors,   cuttlefish:conf_get(Prefix ++ ".acceptors", Conf)},
                     {max_connections, cuttlefish:conf_get(Prefix ++ ".max_clients", Conf)}])
         end,
  TcpOpts = fun(Prefix) ->
                Filter([{backlog, cuttlefish:conf_get(Prefix ++ ".backlog", Conf, undefined)},
                        {send_timeout, cuttlefish:conf_get(Prefix ++ ".send_timeout", Conf, undefined)},
                        {send_timeout_close, cuttlefish:conf_get(Prefix ++ ".send_timeout_close", Conf, undefined)},
                        {recbuf,  cuttlefish:conf_get(Prefix ++ ".recbuf", Conf, undefined)},
                        {sndbuf,  cuttlefish:conf_get(Prefix ++ ".sndbuf", Conf, undefined)},
                        {buffer,  cuttlefish:conf_get(Prefix ++ ".buffer", Conf, undefined)},
                        {nodelay, cuttlefish:conf_get(Prefix ++ ".nodelay", Conf, true)},
                        {inet6, cuttlefish:conf_get(Prefix ++ ".inet6", Conf)},
                        {ipv6_v6only, cuttlefish:conf_get(Prefix ++ ".ipv6_v6only", Conf)}])
            end,

  SplitFun = fun(undefined) -> undefined; (S) -> string:tokens(S, ",") end,

  SslOpts = fun(Prefix) ->
               Versions = case SplitFun(cuttlefish:conf_get(Prefix ++ ".tls_versions", Conf, undefined)) of
                              undefined -> undefined;
                              L -> [list_to_atom(V) || V <- L]
                          end,
                Filter([{versions, Versions},
                        {ciphers, SplitFun(cuttlefish:conf_get(Prefix ++ ".ciphers", Conf, undefined))},
                        {keyfile,    cuttlefish:conf_get(Prefix ++ ".keyfile", Conf, undefined)},
                        {certfile,   cuttlefish:conf_get(Prefix ++ ".certfile", Conf, undefined)},
                        {cacertfile, cuttlefish:conf_get(Prefix ++ ".cacertfile", Conf, undefined)},
                        {verify,     cuttlefish:conf_get(Prefix ++ ".verify", Conf, undefined)},
                        {fail_if_no_peer_cert, cuttlefish:conf_get(Prefix ++ ".fail_if_no_peer_cert", Conf, undefined)}])
              end,
    lists:foldl(
      fun(Proto, Acc) ->
          Prefix = "management.listener." ++ atom_to_list(Proto),
          case cuttlefish:conf_get(Prefix, Conf, undefined) of
              undefined -> Acc;
              Port ->
                  [{Proto, Port, TcpOpts(Prefix) ++ Opts(Prefix)
                    ++ case Proto of
                         http -> [];
                         https -> SslOpts(Prefix)
                       end} | Acc]
          end
      end, [], [http, https])
end}.

