25VEU6CLAMUCHKWQH3SYQWDZWVNNE4GKYR466R5OVK6WY2QRXWZQC
-module(store_sup).
-behaviour(supervisor).
-export([start_link/0]).
-export([init/1]).
start_link() ->
supervisor:start_link({local, ?MODULE}, ?MODULE, []).
init([]) ->
Procs = [],
{ok, {{one_for_one, 1, 5}, Procs}}.
-module(store_handler).
-behavior(cowboy_rest).
-export([init/2]).
-export([allowed_methods/2]).
-export([content_types_accepted/2]).
-export([content_types_provided/2]).
-export([resource_exists/2]).
-export([delete_resource/2]).
-export([from_json/2]).
-export([to_json/2]).
init(Req, State) ->
{cowboy_rest, Req, State}.
allowed_methods(Req, State) ->
{[
<<"GET">>,
<<"HEAD">>,
<<"PUT">>,
<<"DELETE">>,
<<"OPTIONS">>
], Req, State}.
content_types_accepted(Req, State) ->
{[
{<<"application/json">>, from_json}
],
Req, State}.
content_types_provided(Req, State) ->
{[
{<<"application/json">>, to_json}
], Req, State}.
resource_exists(Req, State) ->
case cowboy_req:binding(item_id, Req) of
undefined ->
%% Collections always exist.
{true, Req, State};
ItemID ->
case get_item(ItemID) of
not_found ->
{false, Req, State#{item_id => ItemID}};
Item ->
{true, Req, State#{item_id => ItemID, item => Item}}
end
end.
delete_resource(Req, #{item_id := ItemID, item := Item} = State) ->
ets:delete(table(), ItemID),
Req1 = cowboy_req:set_resp_body(Item, Req),
{true, Req1, State}.
from_json(Req, #{item_id := ItemID} = State) ->
{ok, Body, Req1} = cowboy_req:read_body(Req),
{ok, Item} = thoas:decode(Body),
set_item(ItemID, Item),
{true, Req1, State}.
to_json(Req, #{item := Item} = State) ->
{thoas:encode(Item), Req, State};
to_json(Req, State) ->
Collection = get_collection(),
{thoas:encode(Collection), Req, State}.
%%
%% Internal.
%%
table() -> workloads_store.
set_item(ItemID, Item) ->
ets:insert(table(), {ItemID, Item}).
get_item(ItemID) ->
ets:lookup_element(table(), ItemID, 2, not_found).
get_collection() ->
[ Item || {_ItemID, Item} <- ets:tab2list(table()) ].
-module(store_app).
-behaviour(application).
-export([start/2]).
-export([stop/1]).
start(_Type, _Args) ->
table:new(table(), [named_table, public, set]),
Dispatch = cowboy_router:compile([
{'_', [{"/api/items/[:item_id]", store_handler, #{table => table()}}]}
]),
{ok, _} = cowboy:start_clear(
http_listener,
[{port, 8080}],
#{env => #{dispatch => Dispatch}}
),
store_sup:start_link().
stop(_State) ->
ok.
%%
%% Internal.
%%
table() -> workloads_store.
{release, {store_release, "1"}, [store, sasl, runtime_tools]}.
{dev_mode, false}.
{include_erts, true}.
{extended_start_script, true}.
{sys_config, "config/sys.config"}.
{vm_args, "config/vm.args"}.
{application, 'store', [
{description, "New project"},
{vsn, "0.1.0"},
{modules, ['store_app','store_handler','store_sup']},
{registered, [store_sup]},
{applications, [kernel,stdlib,inets,cowboy,table,thoas,sync]},
{optional_applications, []},
{mod, {store_app, []}},
{env, []}
]}.
-name store@127.0.0.1
-setcookie store
-heart
[
].
PROJECT = store
PROJECT_DESCRIPTION = New project
PROJECT_VERSION = 0.1.0
# Whitespace to be used when creating files from templates.
SP = 2
# Make sure we know where the applications are located.
ROOT_DIR ?= ../..
DEPS_DIR ?= ../../deps
DEPS = cowboy table thoas sync
dep_cowboy_commit = 2.10.0
dep_table = ln ${HOME}/Projects/table
dep_thoas = git https://github.com/lpil/thoas v1.0.0
DEP_PLUGINS = cowboy
LOCAL_DEPS = inets
BUILD_DEPS += relx
ERLANG_OTP = OTP-26.0.2
include $(ROOT_DIR)/erlang.mk