Просмотр исходного кода

Merge pull request #7183 from lafirest/refactor/retainer_api

refactor(retainer): refactor the api use swagger
JianBo He 4 лет назад
Родитель
Сommit
cc7db4a104
1 измененных файлов с 89 добавлено и 89 удалено
  1. 89 89
      apps/emqx_retainer/src/emqx_retainer_api.erl

+ 89 - 89
apps/emqx_retainer/src/emqx_retainer_api.erl

@@ -19,105 +19,102 @@
 -behaviour(minirest_api).
 
 -include_lib("emqx/include/emqx.hrl").
+-include_lib("typerefl/include/types.hrl").
 
--export([api_spec/0]).
+%% API
+-export([api_spec/0, paths/0, schema/1, namespace/0, fields/1]).
 
 -export([ lookup_retained_warp/2
         , with_topic_warp/2
         , config/2]).
 
--import(emqx_mgmt_api_configs, [gen_schema/1]).
--import(emqx_mgmt_util, [ object_array_schema/2
-                        , object_schema/2
-                        , schema/1
-                        , schema/2
-                        , error_schema/2
-                        , page_params/0
-                        , properties/1]).
+-import(hoconsc, [mk/2, ref/1, ref/2, array/1]).
+-import(emqx_dashboard_swagger, [error_codes/2]).
 
 -define(MAX_PAYLOAD_SIZE, 1048576). %% 1MB = 1024 x 1024
+-define(PREFIX, "/mqtt/retainer").
+-define(TAGS, [<<"retainer">>]).
+
+namespace() -> "retainer".
 
 api_spec() ->
-    {[lookup_retained_api(), with_topic_api(), config_api()], []}.
+    emqx_dashboard_swagger:spec(?MODULE, #{check_schema => true, translate_body => true}).
+
+paths() ->
+    [?PREFIX, ?PREFIX ++ "/messages", ?PREFIX ++ "/message/:topic"].
+
+schema(?PREFIX) ->
+    #{operationId => config,
+      get => #{tags => ?TAGS,
+               description => <<"Get retainer config">>,
+               responses => #{200 => mk(conf_schema(), #{desc => "The config content"}),
+                              404 => error_codes(['NOT_FOUND'], <<"Config not found">>)
+                             }
+              },
+      put => #{tags => ?TAGS,
+               description => <<"Update retainer config">>,
+               'requestBody' => mk(conf_schema(), #{desc => "The config content"}),
+               responses => #{200 => mk(conf_schema(), #{desc => "Update configs successfully"}),
+                              404 => error_codes(['UPDATE_FAILED'], <<"Update config failed">>)
+                             }
+              }
+     };
+
+schema(?PREFIX ++ "/messages") ->
+    #{operationId => lookup_retained_warp,
+      get => #{tags => ?TAGS,
+               description => <<"List retained messages">>,
+               parameters => page_params(),
+               responses => #{200 => mk(array(ref(message_summary)), #{desc => "The result list"}),
+                              405 => error_codes(['ACTION_NOT_ALLOWED'], <<"Unsupported backend">>)
+                             }
+              }
+        };
+
+schema(?PREFIX ++ "/message/:topic") ->
+    #{operationId => with_topic_warp,
+      get => #{tags => ?TAGS,
+               description => <<"Lookup a message by a topic without wildcards">>,
+               parameters => parameters(),
+               responses => #{200 => mk(ref(message), #{desc => "Details of the message"}),
+                              404 => error_codes(['NOT_FOUND'], <<"Viewed message doesn't exist">>),
+                              405 => error_codes(['ACTION_NOT_ALLOWED'], <<"Unsupported backend">>)
+                             }
+              },
+      delete => #{tags => ?TAGS,
+                  description => <<"Delete matching messages">>,
+                  parameters => parameters(),
+                  responses => #{204 => <<>>,
+                                 405 => error_codes(['ACTION_NOT_ALLOWED'],
+                                                    <<"Unsupported backend">>)
+                                }
+                 }
+     }.
+
+page_params() ->
+    emqx_dashboard_swagger:fields(page) ++ emqx_dashboard_swagger:fields(limit).
 
 conf_schema() ->
-    gen_schema(emqx:get_raw_config([retainer])).
-
-message_props() ->
-    properties([
-        {id, string, <<"Message ID">>},
-        {topic, string, <<"MQTT Topic">>},
-        {qos, integer, <<"MQTT QoS">>, [0, 1, 2]},
-        {payload, string, <<"MQTT Payload">>},
-        {publish_at, string, <<"Publish datetime, in RFC 3339 format">>},
-        {from_clientid, string, <<"Publisher ClientId">>},
-        {from_username, string, <<"Publisher Username">>}
-    ]).
+    ref(emqx_retainer_schema, "retainer").
 
 parameters() ->
-    [#{
-        name => topic,
-        in => path,
-        required => true,
-        schema => #{type => "string"}
-    }].
-
-lookup_retained_api() ->
-    Metadata = #{
-        get => #{
-            description => <<"List retained messages">>,
-            parameters => page_params(),
-            responses => #{
-                <<"200">> => object_array_schema(
-                    maps:without([payload], message_props()),
-                    <<"List retained messages">>),
-                <<"405">> => schema(<<"NotAllowed">>)
-            }
-        }
-    },
-    {"/mqtt/retainer/messages", Metadata, lookup_retained_warp}.
-
-with_topic_api() ->
-    MetaData = #{
-        get => #{
-            description => <<"lookup matching messages">>,
-            parameters => parameters(),
-            responses => #{
-                <<"200">> => object_schema(message_props(), <<"List retained messages">>),
-                <<"404">> => error_schema(<<"Retained Not Exists">>, ['NOT_FOUND']),
-                <<"405">> => schema(<<"NotAllowed">>)
-            }
-        },
-        delete => #{
-            description => <<"delete matching messages">>,
-            parameters => parameters(),
-            responses => #{
-                <<"204">> => schema(<<"Succeeded">>),
-                <<"405">> => schema(<<"NotAllowed">>)
-            }
-        }
-    },
-    {"/mqtt/retainer/message/:topic", MetaData, with_topic_warp}.
-
-config_api() ->
-    MetaData = #{
-        get => #{
-            description => <<"get retainer config">>,
-            responses => #{
-                <<"200">> => schema(conf_schema(), <<"Get configs successfully">>),
-                <<"404">> => error_schema(<<"Config not found">>, ['NOT_FOUND'])
-            }
-        },
-        put => #{
-            description => <<"Update retainer config">>,
-            'requestBody' => schema(conf_schema()),
-            responses => #{
-                <<"200">> => schema(conf_schema(), <<"Update configs successfully">>),
-                <<"400">> => error_schema(<<"Update configs failed">>, ['UPDATE_FAILED'])
-            }
-        }
-    },
-    {"/mqtt/retainer", MetaData, config}.
+    [{topic, mk(binary(), #{in => path,
+                            required => true,
+                            desc => "The target topic"
+                           })}].
+
+fields(message_summary) ->
+    [ {id, mk(binary(), #{desc => <<"Message ID">>})}
+    , {topic, mk(binary(), #{desc => "The topic"})}
+    , {qos, mk(emqx_schema:qos(), #{desc => "The QoS"})}
+    , {publish_at, mk(string(), #{desc => "Publish datetime, in RFC 3339 format"})}
+    , {from_clientid, mk(binary(), #{desc => "Publisher ClientId"})}
+    , {from_username, mk(binary(), #{desc => "Publisher Username"})}
+    ];
+
+fields(message) ->
+    [{payload, mk(binary(), #{desc => "The payload content"})} |
+     fields(message_summary)].
 
 lookup_retained_warp(Type, Params) ->
     check_backend(Type, Params, fun lookup_retained/2).
@@ -134,7 +131,7 @@ config(put, #{body := Body}) ->
         {200, emqx:get_raw_config([retainer])}
     catch _:Reason:_ ->
             {400,
-             #{code => 'UPDATE_FAILED',
+             #{code => <<"UPDATE_FAILED">>,
                message => iolist_to_binary(io_lib:format("~p~n", [Reason]))}}
     end.
 
@@ -154,7 +151,9 @@ with_topic(get, #{bindings := Bindings}) ->
         [H | _] ->
             {200, format_detail_message(H)};
         _ ->
-            {404, #{code => 'NOT_FOUND'}}
+            {404, #{code => <<"NOT_FOUND">>,
+                    message => <<"Viewed message doesn't exist">>
+                   }}
     end;
 
 with_topic(delete, #{bindings := Bindings}) ->
@@ -193,6 +192,7 @@ check_backend(Type, Params, Cont) ->
             Cont(Type, Params);
         _ ->
             {405,
-             #{<<"content-type">> => <<"text/plain">>},
-             <<"This API only for built in database">>}
+             #{code => <<"ACTION_NOT_ALLOWED">>,
+               message => <<"This API only for built in database">>}
+            }
     end.