1: -module(graphql_domain_SUITE). 2: 3: -include_lib("common_test/include/ct.hrl"). 4: -include_lib("eunit/include/eunit.hrl"). 5: -include_lib("exml/include/exml.hrl"). 6: 7: -compile([export_all, nowarn_export_all]). 8: 9: -import(distributed_helper, [mim/0, require_rpc_nodes/1, rpc/4]). 10: -import(graphql_helper, [execute_auth/2, init_admin_handler/1]). 11: 12: -define(HOST_TYPE, <<"dummy auth">>). 13: -define(SECOND_HOST_TYPE, <<"test type">>). 14: 15: suite() -> 16: require_rpc_nodes([mim]) ++ escalus:suite(). 17: 18: all() -> 19: [{group, domain_handler}]. 20: 21: groups() -> 22: [{domain_handler, [sequence], domain_handler()}]. 23: 24: domain_handler() -> 25: [create_domain, 26: unknown_host_type_error_formatting, 27: static_domain_error_formatting, 28: domain_duplicate_error_formatting, 29: domain_not_found_error_formatting_after_mutation_disable_domain, 30: domain_not_found_error_formatting_after_mutation_enable_domain, 31: domain_not_found_error_formatting_after_query, 32: wrong_host_type_error_formatting, 33: disable_domain, 34: enable_domain, 35: get_domains_by_host_type, 36: get_domain_details, 37: delete_domain, 38: get_domains_after_deletion, 39: set_domain_password, 40: set_nonexistent_domain_password, 41: delete_domain_password 42: ]. 43: 44: init_per_suite(Config) -> 45: case mongoose_helper:is_rdbms_enabled(?HOST_TYPE) of 46: true -> escalus:init_per_suite(init_admin_handler(Config)); 47: false -> {skip, require_rdbms} 48: end. 49: 50: end_per_suite(Config) -> 51: escalus_fresh:clean(), 52: escalus:end_per_suite(Config). 53: 54: init_per_testcase(CaseName, Config) -> 55: escalus:init_per_testcase(CaseName, Config). 56: 57: end_per_testcase(CaseName, Config) -> 58: escalus:end_per_testcase(CaseName, Config). 59: 60: create_domain(Config) -> 61: create_domain(Config, <<"exampleDomain">>), 62: create_domain(Config, <<"exampleDomain2">>). 63: 64: create_domain(Config, DomainName) -> 65: Vars = #{domain => DomainName, hostType => ?HOST_TYPE}, 66: Result = execute_auth(#{query => create_domain_call(), variables => Vars, 67: operationName => <<"M1">>}, Config), 68: ParsedResult = ok_result(<<"domains">>, <<"addDomain">>, Result), 69: ?assertEqual(#{<<"domain">> => DomainName, 70: <<"hostType">> => ?HOST_TYPE, 71: <<"enabled">> => null}, ParsedResult). 72: 73: unknown_host_type_error_formatting(Config) -> 74: DomainName = <<"exampleDomain">>, 75: HostType = <<"NonExistingHostType">>, 76: Vars = #{domain => DomainName, hostType => HostType}, 77: Result = execute_auth(#{query => create_domain_call(), variables => Vars, 78: operationName => <<"M1">>}, Config), 79: ParsedResult = error_result(1, Result), 80: ?assertEqual(#{<<"extensions">> => 81: #{<<"code">> => <<"unknown_host_type">>, 82: <<"hostType">> => HostType}, 83: <<"message">> => <<"Unknown host type">>, 84: <<"path">> => [<<"domains">>, <<"addDomain">>]}, ParsedResult). 85: 86: static_domain_error_formatting(Config) -> 87: DomainName = <<"localhost">>, 88: Vars = #{domain => DomainName, hostType => ?HOST_TYPE}, 89: Result = execute_auth(#{query => create_domain_call(), variables => Vars, 90: operationName => <<"M1">>}, Config), 91: ParsedResult = error_result(1, Result), 92: ?assertEqual(#{<<"extensions">> => 93: #{<<"code">> => <<"domain_static">>, 94: <<"domain">> => DomainName}, 95: <<"message">> => <<"Domain static">>, 96: <<"path">> => [<<"domains">>, <<"addDomain">>]}, ParsedResult). 97: 98: domain_duplicate_error_formatting(Config) -> 99: DomainName = <<"exampleDomain">>, 100: Vars = #{domain => DomainName, hostType => ?SECOND_HOST_TYPE}, 101: Result = execute_auth(#{query => create_domain_call(), variables => Vars, 102: operationName => <<"M1">>}, Config), 103: ParsedResult = error_result(1, Result), 104: ?assertEqual(#{<<"extensions">> => 105: #{<<"code">> => <<"domain_duplicate">>, 106: <<"domain">> => DomainName}, 107: <<"message">> => <<"Domain already exists">>, 108: <<"path">> => [<<"domains">>, <<"addDomain">>]}, ParsedResult). 109: 110: domain_not_found_error_formatting_after_mutation_enable_domain(Config) -> 111: DomainName = <<"NonExistingDomain">>, 112: Vars = #{domain => DomainName}, 113: Result = execute_auth(#{query => enable_domain_call(), variables => Vars, 114: operationName => <<"M1">>}, Config), 115: domain_not_found_error_formatting(Result, DomainName, <<"enableDomain">>). 116: 117: domain_not_found_error_formatting_after_mutation_disable_domain(Config) -> 118: DomainName = <<"NonExistingDomain">>, 119: Vars = #{domain => DomainName}, 120: Result = execute_auth(#{query => disable_domain_call(), variables => Vars, 121: operationName => <<"M1">>}, Config), 122: domain_not_found_error_formatting(Result, DomainName, <<"disableDomain">>). 123: 124: domain_not_found_error_formatting_after_query(Config) -> 125: DomainName = <<"NonExistingDomain">>, 126: Vars = #{domain => DomainName}, 127: Result = execute_auth(#{query => get_domain_details_call(), variables => Vars, 128: operationName => <<"Q1">>}, Config), 129: domain_not_found_error_formatting(Result, DomainName, <<"domainDetails">>). 130: 131: domain_not_found_error_formatting(Result, DomainName, GraphqlCall) -> 132: ParsedResult = error_result(1, Result), 133: ?assertEqual(#{<<"extensions">> => 134: #{<<"code">> => <<"domain_not_found">>, 135: <<"domain">> => DomainName}, 136: <<"message">> => <<"Given domain does not exist">>, 137: <<"path">> => [<<"domains">>, GraphqlCall]}, ParsedResult). 138: 139: wrong_host_type_error_formatting(Config) -> 140: DomainName = <<"exampleDomain">>, 141: Vars = #{domain => DomainName, hostType => ?SECOND_HOST_TYPE}, 142: Result = execute_auth(#{query => delete_domain_call(), variables => Vars, 143: operationName => <<"M1">>}, Config), 144: ParsedResult = error_result(1, Result), 145: ?assertEqual(#{<<"extensions">> => 146: #{<<"code">> => <<"wrong_host_type">>, 147: <<"hostType">> => ?SECOND_HOST_TYPE}, 148: <<"message">> => <<"Wrong host type">>, 149: <<"path">> => [<<"domains">>, <<"removeDomain">>]}, ParsedResult). 150: 151: disable_domain(Config) -> 152: Vars = #{domain => <<"exampleDomain">>}, 153: Result = execute_auth(#{query => disable_domain_call(), variables => Vars, 154: operationName => <<"M1">>}, Config), 155: ParsedResult = ok_result(<<"domains">>, <<"disableDomain">>, Result), 156: ?assertEqual(#{<<"domain">> => <<"exampleDomain">>, <<"enabled">> => false}, ParsedResult), 157: {ok, Domain} = rpc(mim(), mongoose_domain_sql, select_domain, [<<"exampleDomain">>]), 158: ?assertEqual(#{host_type => ?HOST_TYPE, 159: enabled => false}, Domain). 160: 161: 162: enable_domain(Config) -> 163: Vars = #{domain => <<"exampleDomain">>}, 164: Result = execute_auth(#{query => enable_domain_call(), variables => Vars, 165: operationName => <<"M1">>}, Config), 166: ParsedResult = ok_result(<<"domains">>, <<"enableDomain">>, Result), 167: ?assertEqual(#{<<"domain">> => <<"exampleDomain">>, <<"enabled">> => true}, ParsedResult). 168: 169: get_domains_by_host_type(Config) -> 170: Vars = #{hostType => ?HOST_TYPE}, 171: Result = execute_auth(#{query => get_domains_by_host_type_call(), 172: variables => Vars, 173: operationName => <<"Q1">>}, Config), 174: ParsedResult = ok_result(<<"domains">>, <<"domainsByHostType">>, Result), 175: ?assertEqual(lists:sort([<<"exampleDomain">>, <<"exampleDomain2">>]), 176: lists:sort(ParsedResult)). 177: 178: get_domain_details(Config) -> 179: Vars = #{domain => <<"exampleDomain">>}, 180: Result = execute_auth(#{query => get_domain_details_call(), 181: variables => Vars, 182: operationName => <<"Q1">>}, Config), 183: ParsedResult = ok_result(<<"domains">>, <<"domainDetails">>, Result), 184: ?assertEqual(#{<<"domain">> => <<"exampleDomain">>, 185: <<"hostType">> => ?HOST_TYPE, 186: <<"enabled">> => true}, ParsedResult). 187: 188: delete_domain(Config) -> 189: Vars = #{domain => <<"exampleDomain">>, hostType => ?HOST_TYPE}, 190: Result1 = execute_auth(#{query => delete_domain_call(), variables => Vars, 191: operationName => <<"M1">>}, Config), 192: ParsedResult1 = ok_result(<<"domains">>, <<"removeDomain">>, Result1), 193: ?assertEqual(#{<<"msg">> => <<"Domain removed!">>, 194: <<"domain">> => #{<<"domain">> => <<"exampleDomain">>}}, 195: ParsedResult1), 196: 197: Vars2 = #{domain => <<"exampleDomain2">>, hostType => ?HOST_TYPE}, 198: Result2 = execute_auth(#{query => delete_domain_call(), variables => Vars2, 199: operationName => <<"M1">>}, Config), 200: ParsedResult2 = ok_result(<<"domains">>, <<"removeDomain">>, Result2), 201: ?assertEqual(#{<<"msg">> => <<"Domain removed!">>, 202: <<"domain">> => #{<<"domain">> => <<"exampleDomain2">>}}, 203: ParsedResult2). 204: 205: get_domains_after_deletion(Config) -> 206: Vars = #{hostType => ?HOST_TYPE}, 207: Result = execute_auth(#{query => get_domains_by_host_type_call(), 208: variables => Vars, 209: operationName => <<"Q1">>}, Config), 210: ParsedResult = ok_result(<<"domains">>, <<"domainsByHostType">>, Result), 211: ?assertEqual([], ParsedResult). 212: 213: set_domain_password(Config) -> 214: Result = execute_auth(#{query => set_domain_password_call(), 215: variables => #{domain => domain_helper:domain(), 216: password => <<"secret">>}, 217: operationName => <<"M1">>}, Config), 218: ParsedResult = ok_result(<<"domains">>, <<"setDomainPassword">>, Result), 219: ?assertNotEqual(nomatch, binary:match(ParsedResult, <<"successfully">>)). 220: 221: set_nonexistent_domain_password(Config) -> 222: Domain = <<"unknown-domain.com">>, 223: Result = execute_auth(#{query => set_domain_password_call(), 224: variables => #{domain => Domain, 225: password => <<"secret">>}, 226: operationName => <<"M1">>}, Config), 227: domain_not_found_error_formatting(Result, Domain, <<"setDomainPassword">>). 228: 229: delete_domain_password(Config) -> 230: Result = execute_auth(#{query => delete_domain_password_call(), 231: variables => #{domain => domain_helper:domain()}, 232: operationName => <<"M1">>}, Config), 233: ParsedResult = ok_result(<<"domains">>, <<"deleteDomainPassword">>, Result), 234: ?assertNotEqual(nomatch, binary:match(ParsedResult, <<"successfully">>)). 235: 236: create_domain_call() -> 237: <<"mutation M1($domain: String!, $hostType: String!) 238: {domains 239: {addDomain(domain: $domain, hostType: $hostType) 240: { 241: domain 242: hostType 243: enabled 244: } 245: } 246: }">>. 247: 248: enable_domain_call() -> 249: <<"mutation M1($domain: String!) 250: {domains 251: {enableDomain(domain: $domain) 252: { 253: enabled 254: domain 255: } 256: } 257: }">>. 258: 259: disable_domain_call() -> 260: <<"mutation M1($domain: String!) 261: {domains 262: {disableDomain(domain: $domain) 263: { 264: enabled 265: domain 266: } 267: } 268: }">>. 269: 270: get_domains_by_host_type_call() -> 271: <<"query Q1($hostType: String!) 272: {domains 273: {domainsByHostType(hostType: $hostType)} 274: }">>. 275: 276: get_domain_details_call() -> 277: <<"query Q1($domain: String!) 278: {domains 279: {domainDetails(domain: $domain) 280: { 281: domain 282: hostType 283: enabled 284: } 285: } 286: }">>. 287: 288: delete_domain_call() -> 289: <<"mutation M1($domain: String!, $hostType: String!) 290: {domains 291: {removeDomain(domain: $domain, hostType: $hostType) 292: { 293: msg 294: domain 295: {domain} 296: } 297: } 298: }">>. 299: 300: set_domain_password_call() -> 301: <<"mutation M1($domain: String!, $password: String!)" 302: "{ domains { setDomainPassword(domain: $domain, password: $password)} }">>. 303: 304: delete_domain_password_call() -> 305: <<"mutation M1($domain: String!)" 306: "{ domains { deleteDomainPassword(domain: $domain)} }">>. 307: 308: %% Helpers 309: ok_result(What1, What2, {{<<"200">>, <<"OK">>}, #{<<"data">> := Data}}) -> 310: maps:get(What2, maps:get(What1, Data)). 311: 312: error_result(ErrorNumber, {{<<"200">>, <<"OK">>}, #{<<"errors">> := Errors}}) -> 313: lists:nth(ErrorNumber, Errors).