-module(admin_handler_banned_words_tests). -include_lib("eunit/include/eunit.hrl"). -include("records.hrl"). -define(TABLES, [admin, admin_audit, banned_word, ticket]). -define(ADMIN_ID, <<"adm_test_1">>). setup() -> eh_test_support:start_mnesia(), eh_test_support:ensure_tables(?TABLES), eh_test_support:ensure_jwt(), eh_test_support:seed_admin(#{id => ?ADMIN_ID}), ok. cleanup(_) -> eh_test_support:unload_cowboy(), eh_test_support:delete_tables(?TABLES), eh_test_support:stop_mnesia(), ok. admin_banned_words_test_() -> {foreach, fun setup/0, fun cleanup/1, [ {"GET list – success", fun test_list/0}, {"GET list – forbidden without admin", fun test_list_forbidden/0}, {"POST add – success", fun test_add/0}, {"POST add – missing field", fun test_add_missing/0}, {"POST add – already exists", fun test_add_exists/0}, {"DELETE – success", fun test_delete/0}, {"DELETE – not found", fun test_delete_not_found/0}, {"PUT – success", fun test_update/0}, {"PUT – not found", fun test_update_not_found/0}, {"POST batch – success", fun test_batch/0}, {"PATCH – method not allowed", fun test_wrong_method/0} ]}. test_list() -> {ok, _} = core_banned_words:add_banned_word(<<"badword">>, ?ADMIN_ID), {ok, _} = core_banned_words:add_banned_word(<<"spamword">>, ?ADMIN_ID), {Status, _, Body} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"GET">>, path => <<"/v1/admin/banned-words">>, auth => ?ADMIN_ID }), ?assertEqual(200, Status), Result = jsx:decode(Body, [return_maps]), ?assertEqual(2, length(Result)), Words = [maps:get(<<"word">>, W) || W <- Result], ?assert(lists:member(<<"badword">>, Words)), ?assert(lists:member(<<"spamword">>, Words)). test_list_forbidden() -> {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"GET">>, path => <<"/v1/admin/banned-words">>, auth => none }), ?assertEqual(401, Status). test_add() -> {Status, _, Body} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"POST">>, path => <<"/v1/admin/banned-words">>, auth => ?ADMIN_ID, body => jsx:encode(#{<<"word">> => <<"banned">>}) }), ?assertEqual(201, Status), #{<<"status">> := <<"added">>} = jsx:decode(Body, [return_maps]), ?assert(core_banned_words:is_word_banned(<<"banned">>)), Audits = core_admin_audit:list(), ?assert(length(Audits) >= 1). test_add_missing() -> {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"POST">>, path => <<"/v1/admin/banned-words">>, auth => ?ADMIN_ID, body => jsx:encode(#{<<"other">> => <<"data">>}) }), ?assertEqual(400, Status). test_add_exists() -> {ok, _} = core_banned_words:add_banned_word(<<"already">>, ?ADMIN_ID), {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"POST">>, path => <<"/v1/admin/banned-words">>, auth => ?ADMIN_ID, body => jsx:encode(#{<<"word">> => <<"already">>}) }), ?assertEqual(409, Status). test_delete() -> {ok, _} = core_banned_words:add_banned_word(<<"badword">>, ?ADMIN_ID), {Status, _, Body} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"DELETE">>, path => <<"/v1/admin/banned-words/badword">>, bindings => #{word => <<"badword">>}, auth => ?ADMIN_ID }), ?assertEqual(200, Status), #{<<"status">> := <<"deleted">>} = jsx:decode(Body, [return_maps]), ?assertEqual(false, core_banned_words:is_word_banned(<<"badword">>)). test_delete_not_found() -> {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"DELETE">>, path => <<"/v1/admin/banned-words/unknown">>, bindings => #{word => <<"unknown">>}, auth => ?ADMIN_ID }), ?assertEqual(404, Status). test_update() -> {ok, _} = core_banned_words:add_banned_word(<<"old">>, ?ADMIN_ID), {Status, _, Body} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"PUT">>, path => <<"/v1/admin/banned-words/old">>, bindings => #{word => <<"old">>}, auth => ?ADMIN_ID, body => jsx:encode(#{<<"word">> => <<"new">>}) }), ?assertEqual(200, Status), #{<<"status">> := <<"updated">>} = jsx:decode(Body, [return_maps]), ?assert(core_banned_words:is_word_banned(<<"new">>)), ?assertEqual(false, core_banned_words:is_word_banned(<<"old">>)). test_update_not_found() -> {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"PUT">>, path => <<"/v1/admin/banned-words/missing">>, bindings => #{word => <<"missing">>}, auth => ?ADMIN_ID, body => jsx:encode(#{<<"word">> => <<"x">>}) }), ?assertEqual(404, Status). test_batch() -> {ok, _} = core_banned_words:add_banned_word(<<"exists">>, ?ADMIN_ID), {Status, _, Body} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"POST">>, path => <<"/v1/admin/banned-words/batch">>, auth => ?ADMIN_ID, body => jsx:encode(#{<<"words">> => [<<"new1">>, <<"exists">>, <<"new2">>]}) }), ?assertEqual(200, Status), #{<<"added">> := 2, <<"skipped">> := 1} = jsx:decode(Body, [return_maps]), ?assert(core_banned_words:is_word_banned(<<"new1">>)), ?assert(core_banned_words:is_word_banned(<<"new2">>)). test_wrong_method() -> {Status, _, _} = eh_test_support:call(admin_handler_banned_words, #{ method => <<"PATCH">>, path => <<"/v1/admin/banned-words">>, auth => ?ADMIN_ID }), ?assertEqual(405, Status).