1: -module(graphql_offline_SUITE). 2: 3: -compile([export_all, nowarn_export_all]). 4: 5: -import(distributed_helper, [require_rpc_nodes/1]). 6: -import(domain_helper, [host_type/0, domain/0]). 7: -import(graphql_helper, [execute_user/3, execute_auth/2, user_to_bin/1]). 8: -import(config_parser_helper, [mod_config/2]). 9: -import(mongooseimctl_helper, [mongooseimctl/3, rpc_call/3]). 10: 11: -include_lib("common_test/include/ct.hrl"). 12: -include_lib("eunit/include/eunit.hrl"). 13: -include_lib("exml/include/exml.hrl"). 14: -include_lib("escalus/include/escalus.hrl"). 15: -include("../../include/mod_roster.hrl"). 16: 17: -record(offline_msg, {us, timestamp, expire, from, to, packet, permanent_fields = []}). 18: 19: suite() -> 20: require_rpc_nodes([mim]) ++ escalus:suite(). 21: 22: all() -> 23: [{group, admin_offline}, 24: {group, admin_offline_not_configured}]. 25: 26: groups() -> 27: [{admin_offline, [], admin_offline_handler()}, 28: {admin_offline_not_configured, [], admin_offline_not_configured_handler()}]. 29: 30: admin_offline_handler() -> 31: [admin_delete_expired_messages_test, 32: admin_delete_old_messages_test, 33: admin_delete_expired_messages2_test, 34: admin_delete_old_messages2_test, 35: admin_delete_expired_messages_no_domain_test, 36: admin_delete_old_messages_no_domain_test]. 37: 38: admin_offline_not_configured_handler() -> 39: [admin_delete_expired_messages_offline_not_configured_test, 40: admin_delete_old_messages_offline_not_configured_test]. 41: 42: init_per_suite(Config) -> 43: Config1 = dynamic_modules:save_modules(host_type(), Config), 44: escalus:init_per_suite(Config1). 45: 46: -spec create_config(atom()) -> [{mod_offline, gen_mod:module_opts()}]. 47: create_config(riak) -> 48: [{mod_offline, mod_config(mod_offline, #{backend => riak, 49: riak => #{bucket_type => <<"offline">>}})}]; 50: create_config(Backend) -> 51: [{mod_offline, mod_config(mod_offline, #{backend => Backend})}]. 52: 53: 54: end_per_suite(Config) -> 55: dynamic_modules:restore_modules(Config), 56: escalus:end_per_suite(Config). 57: 58: init_per_group(admin_offline, Config) -> 59: HostType = host_type(), 60: Backend = mongoose_helper:get_backend_mnesia_rdbms_riak(HostType), 61: ModConfig = create_config(Backend), 62: dynamic_modules:ensure_modules(HostType, ModConfig), 63: Config1 = [{backend, Backend} | escalus:init_per_suite(Config)], 64: graphql_helper:init_admin_handler(Config1); 65: init_per_group(admin_offline_not_configured, Config) -> 66: dynamic_modules:ensure_modules(host_type(), [{mod_offline, stopped}]), 67: graphql_helper:init_admin_handler(Config). 68: 69: end_per_group(_, _Config) -> 70: escalus_fresh:clean(). 71: 72: init_per_testcase(CaseName, Config) -> 73: escalus:init_per_testcase(CaseName, Config). 74: 75: end_per_testcase(CaseName, Config) -> 76: escalus:end_per_testcase(CaseName, Config). 77: 78: % Admin test cases 79: 80: admin_delete_expired_messages_test(Config) -> 81: Vars = #{<<"domain">> => domain()}, 82: GraphQlRequest = admin_delete_expired_messages_mutation(Config, Vars), 83: Message = ok_result(<<"offline">>, <<"deleteExpiredMessages">>, GraphQlRequest), 84: ?assertEqual(<<"Removed 0 messages">>, Message). 85: 86: admin_delete_old_messages_test(Config) -> 87: Vars = #{<<"domain">> => domain(), <<"days">> => 2}, 88: GraphQlRequest = admin_delete_old_messages_mutation(Config, Vars), 89: Message = ok_result(<<"offline">>, <<"deleteOldMessages">>, GraphQlRequest), 90: ?assertEqual(<<"Removed 0 messages">>, Message). 91: 92: admin_delete_expired_messages2_test(Config) -> 93: escalus:fresh_story_with_config(Config, [{mike, 1}, {kate, 1}], fun admin_delete_expired_messages2_test/3). 94: 95: admin_delete_expired_messages2_test(Config, JidMike, JidKate) -> 96: generate_message(JidMike, JidKate, 10, 2), 97: generate_message(JidMike, JidKate, 10, 2), 98: Vars = #{<<"domain">> => domain()}, 99: GraphQlRequest = admin_delete_expired_messages_mutation(Config, Vars), 100: Message = ok_result(<<"offline">>, <<"deleteExpiredMessages">>, GraphQlRequest), 101: ?assertEqual(<<"Removed 2 messages">>, Message). 102: 103: admin_delete_old_messages2_test(Config) -> 104: escalus:fresh_story_with_config(Config, [{mike, 1}, {kate, 1}], fun admin_delete_old_messages2_test/3). 105: 106: admin_delete_old_messages2_test(Config, JidMike, JidKate) -> 107: generate_message(JidMike, JidKate, 2, 10), 108: generate_message(JidMike, JidKate, 2, 10), 109: Vars = #{<<"domain">> => domain(), <<"days">> => 2}, 110: GraphQlRequest = admin_delete_old_messages_mutation(Config, Vars), 111: Message = ok_result(<<"offline">>, <<"deleteOldMessages">>, GraphQlRequest), 112: ?assertEqual(<<"Removed 2 messages">>, Message). 113: 114: admin_delete_expired_messages_no_domain_test(Config) -> 115: Vars = #{<<"domain">> => <<"AAAA">>}, 116: GraphQlRequest = admin_delete_expired_messages_mutation(Config, Vars), 117: ParsedResult = error_result(<<"extensions">>, <<"code">>, GraphQlRequest), 118: ?assertEqual(<<"domain_not_found">>, ParsedResult). 119: 120: admin_delete_old_messages_no_domain_test(Config) -> 121: Vars = #{<<"domain">> => <<"AAAA">>, <<"days">> => 2}, 122: GraphQlRequest = admin_delete_old_messages_mutation(Config, Vars), 123: ParsedResult = error_result(<<"extensions">>, <<"code">>, GraphQlRequest), 124: ?assertEqual(<<"domain_not_found">>, ParsedResult). 125: 126: admin_delete_expired_messages_offline_not_configured_test(Config) -> 127: Vars = #{<<"domain">> => domain()}, 128: GraphQlRequest = admin_delete_expired_messages_mutation(Config, Vars), 129: ParsedResult = error_result(<<"extensions">>, <<"code">>, GraphQlRequest), 130: ?assertEqual(<<"module_not_loaded_error">>, ParsedResult). 131: 132: admin_delete_old_messages_offline_not_configured_test(Config) -> 133: Vars = #{<<"domain">> => domain(), <<"days">> => 2}, 134: GraphQlRequest = admin_delete_old_messages_mutation(Config, Vars), 135: ParsedResult = error_result(<<"extensions">>, <<"code">>, GraphQlRequest), 136: ?assertEqual(<<"module_not_loaded_error">>, ParsedResult). 137: 138: % Helpers 139: 140: admin_delete_expired_messages_mutation(Config, Vars) -> 141: Mutation = <<"mutation M1($domain: String!) 142: {offline{deleteExpiredMessages(domain: $domain)}}">>, 143: admin_send_mutation(Config, Vars, Mutation). 144: 145: admin_delete_old_messages_mutation(Config, Vars) -> 146: Mutation = <<"mutation M1($domain: String!, $days: Int!) 147: {offline{deleteOldMessages(domain: $domain, days: $days)}}">>, 148: admin_send_mutation(Config, Vars, Mutation). 149: 150: admin_send_mutation(Config, Vars, Mutation) -> 151: Body = #{query => Mutation, operationName => <<"M1">>, variables => Vars}, 152: execute_auth(Body, Config). 153: 154: error_result(What1, What2, {{<<"200">>, <<"OK">>}, #{<<"errors">> := [Data]}}) -> 155: maps:get(What2, maps:get(What1, Data)). 156: 157: ok_result(What1, What2, {{<<"200">>, <<"OK">>}, #{<<"data">> := Data}}) -> 158: maps:get(What2, maps:get(What1, Data)). 159: 160: generate_message(JidMike, JidKate, TimestampDaysAgo, TimestampExpiringDaysAgo) -> 161: JidRecordMike = jid:from_binary(user_to_bin(JidMike)), 162: JidRecordKate = jid:from_binary(user_to_bin(JidKate)), 163: Domain = domain(), 164: Msg1 = escalus_stanza:chat_to(<<"kate@", Domain/binary>>, "Rolling stones"), 165: OldTimestamp = fallback_timestamp(TimestampDaysAgo, os:system_time(microsecond)), 166: ExpirationTime = fallback_timestamp(TimestampExpiringDaysAgo, os:system_time(microsecond)), 167: OfflineOld = generate_offline_expired_message(JidRecordMike, 168: JidRecordKate, Msg1, 169: OldTimestamp, 170: ExpirationTime), 171: {LUser, LServer} = jid:to_lus(JidRecordKate), 172: rpc_call(mod_offline_backend, write_messages, [host_type(), LUser, LServer, [OfflineOld]]). 173: 174: generate_offline_expired_message(From, To, Msg, TimeStamp, ExpirationTime) -> 175: {LUser, LServer} = jid:to_lus(To), 176: #offline_msg{us = {LUser, LServer}, timestamp = TimeStamp, 177: expire = ExpirationTime, from = From, to = To, packet = Msg}. 178: 179: fallback_timestamp(HowManyDays, TS_MicroSeconds) -> 180: HowManySeconds = HowManyDays * 86400, 181: HowManyMicroSeconds = erlang:convert_time_unit(HowManySeconds, second, microsecond), 182: TS_MicroSeconds - HowManyMicroSeconds.