1: %%============================================================================== 2: %% Copyright 2010 Erlang Solutions Ltd. 3: %% 4: %% Licensed under the Apache License, Version 2.0 (the "License"); 5: %% you may not use this file except in compliance with the License. 6: %% You may obtain a copy of the License at 7: %% 8: %% http://www.apache.org/licenses/LICENSE-2.0 9: %% 10: %% Unless required by applicable law or agreed to in writing, software 11: %% distributed under the License is distributed on an "AS IS" BASIS, 12: %% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13: %% See the License for the specific language governing permissions and 14: %% limitations under the License. 15: %%============================================================================== 16: 17: -module(privacy_SUITE). 18: -compile([export_all, nowarn_export_all]). 19: 20: -include_lib("exml/include/exml.hrl"). 21: -include_lib("escalus/include/escalus.hrl"). 22: -include_lib("common_test/include/ct.hrl"). 23: -include_lib("escalus/include/escalus_xmlns.hrl"). 24: 25: -define(SLEEP_TIME, 50). 26: 27: %%-------------------------------------------------------------------- 28: %% Suite configuration 29: %%-------------------------------------------------------------------- 30: 31: all() -> 32: [ 33: {group, management}, 34: {group, blocking}, 35: {group, allowing} 36: ]. 37: 38: groups() -> 39: G = [{management, [parallel], management_test_cases()}, 40: {blocking, [parallel], blocking_test_cases()}, 41: {allowing, [parallel], allowing_test_cases()}], 42: ct_helper:repeat_all_until_all_ok(G). 43: 44: management_test_cases() -> 45: [ 46: discover_support, 47: get_all_lists, 48: get_existing_list, 49: get_many_lists, 50: get_nonexistent_list, 51: set_list, 52: activate, 53: activate_nonexistent, 54: deactivate, 55: default, 56: %default_conflict, % fails, as of bug #7073 57: default_nonexistent, 58: no_default, 59: remove_list, 60: get_all_lists_with_active, 61: get_all_lists_with_default 62: ]. 63: 64: blocking_test_cases() -> 65: [ 66: block_jid_message, 67: block_group_message, 68: block_subscription_message, 69: block_all_message, 70: block_jid_presence_in, 71: block_jid_presence_out, 72: block_jid_iq, 73: block_jid_all, 74: block_jid_message_but_not_presence, 75: newly_blocked_presense_jid_by_new_list, 76: newly_blocked_presense_jid_by_list_change, 77: newly_blocked_presence_not_notify_self, 78: iq_reply_doesnt_crash_user_process 79: ]. 80: 81: allowing_test_cases() -> 82: [allow_subscription_to_from_message, 83: allow_subscription_both_message]. 84: 85: suite() -> 86: escalus:suite(). 87: 88: %%-------------------------------------------------------------------- 89: %% Init & teardown 90: %%-------------------------------------------------------------------- 91: 92: init_per_suite(Config0) -> 93: HostType = domain_helper:host_type(), 94: Config1 = dynamic_modules:save_modules(HostType, Config0), 95: Backend = mongoose_helper:get_backend_mnesia_rdbms_riak(HostType), 96: ModConfig = [{mod_privacy, set_opts(Backend)}], 97: dynamic_modules:ensure_modules(HostType, ModConfig), 98: [{escalus_no_stanzas_after_story, true}, 99: {backend, Backend} | 100: escalus:init_per_suite(Config1)]. 101: 102: set_opts(riak) -> 103: #{riak => config_parser_helper:config([modules, mod_privacy, riak], #{}), backend => riak}; 104: set_opts(Backend) -> 105: #{backend => Backend}. 106: 107: end_per_suite(Config) -> 108: escalus_fresh:clean(), 109: dynamic_modules:restore_modules(Config), 110: escalus:end_per_suite(Config). 111: 112: init_per_group(_GroupName, Config) -> 113: Config. 114: 115: end_per_group(_GroupName, Config) -> 116: Config. 117: 118: init_per_testcase(CaseName, Config) -> 119: escalus:init_per_testcase(CaseName, Config). 120: 121: end_per_testcase(CaseName, Config) -> 122: escalus:end_per_testcase(CaseName, Config). 123: 124: %%-------------------------------------------------------------------- 125: %% Tests 126: %%-------------------------------------------------------------------- 127: 128: %% In terms of server response to blocked communication, we strive to implement the following 129: %% as defined in XEP-0016: 130: %% If someone I block tries to communicate with me, then the following rules apply: 131: %% * For presence stanzas (including notifications, subscriptions, and probes), the server MUST NOT respond and MUST NOT 132: %% return an error. 133: %% * For message stanzas, the server SHOULD return an error, which SHOULD be <service-unavailable/>. 134: %% * For IQ stanzas of type "get" or "set", the server MUST return an error, which SHOULD be <service-unavailable/>. IQ 135: %% stanzas of other types MUST be silently dropped by the server. 136: %% If I want to communicate with someone I block, then: 137: %% * If the user attempts to send an outbound stanza to a contact and that stanza type is blocked, the user's server MUST 138: %% NOT route the stanza to the contact but instead MUST return a <not-acceptable/> error: 139: 140: 141: %% TODO: 142: %% x get all privacy lists 143: %% x get single privacy list 144: %% x that exists 145: %% x that doesn't exist (ensure server returns item-not-found) 146: %% x request more than one at a time (ensure server returns bad-request) 147: %% x set new/edit privacy list (ensure server pushes notifications 148: %% to all resources) 149: %% - remove existing list 150: %% x remove existing list (ensure server push) 151: %% - remove, but check conflict case 152: %% x manage active list(s) 153: %% x activate 154: %% x activate nonexistent (ensure item-not-found) 155: %% x deactivate by sending empty <active /> 156: %% - manage default list 157: %% x set default 158: %% - set default, but check the conflict case, i.e.: 159: %% "Client attempts to change the default list but that list is in use 160: %% by another resource", 161: %% !!! ejabberd doesn't support this, bug filed (#7073) 162: %% x set nonexistent default list 163: %% x use domain's routing, i.e. no default list -> send empty <default /> 164: %% - set no default list, but check conflict case, 165: %% when a resource currently uses the default list 166: %% 167: %% TODO later: 168: %% - big picture: 169: %% - blocking can be done on jids, roster groups, 170: %% subscription type or globally 171: %% - a blocking rule may block one or more of {message, presence-in, 172: %% presence-out, iqs} by specifying these as children to the list item 173: %% or block all of them, when the item has no children 174: %% - blocking: messages, presence (in/out), iqs, all 175: 176: discover_support(Config) -> 177: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 178: Server = escalus_client:server(Alice), 179: IqGet = escalus_stanza:disco_info(Server), 180: Result = escalus:send_iq_and_wait_for_result(Alice, IqGet), 181: escalus:assert(has_feature, [?NS_PRIVACY], Result) 182: end). 183: 184: get_all_lists(Config) -> 185: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 186: 187: escalus:send(Alice, escalus_stanza:privacy_get_all()), 188: escalus:assert(is_privacy_result, escalus:wait_for_stanza(Alice)) 189: 190: end). 191: 192: get_all_lists_with_active(Config) -> 193: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 194: 195: privacy_helper:set_and_activate(Alice, {<<"deny_client">>, Bob}), 196: 197: escalus:send(Alice, escalus_stanza:privacy_get_all()), 198: escalus:assert(is_privacy_result_with_active, [<<"deny_client">>], 199: escalus:wait_for_stanza(Alice)) 200: 201: end). 202: 203: get_all_lists_with_default(Config) -> 204: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 205: 206: privacy_helper:set_list(Alice, {<<"deny_client">>, Bob}), 207: privacy_helper:set_list(Alice, {<<"allow_client">>, Bob}), 208: privacy_helper:set_default_list(Alice, <<"allow_client">>), 209: 210: escalus:send(Alice, escalus_stanza:privacy_get_all()), 211: escalus:assert(is_privacy_result_with_default, 212: escalus:wait_for_stanza(Alice)) 213: 214: end). 215: 216: get_nonexistent_list(Config) -> 217: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 218: 219: escalus_client:send(Alice, 220: escalus_stanza:privacy_get_lists([<<"public">>])), 221: escalus_assert:is_privacy_list_nonexistent_error( 222: escalus_client:wait_for_stanza(Alice)) 223: 224: end). 225: 226: get_many_lists(Config) -> 227: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 228: 229: Request = escalus_stanza:privacy_get_lists([<<"public">>, <<"private">>]), 230: escalus_client:send(Alice, Request), 231: Response = escalus_client:wait_for_stanza(Alice), 232: escalus_assert:is_error(Response, <<"modify">>, <<"bad-request">>) 233: 234: end). 235: 236: get_existing_list(Config) -> 237: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 238: 239: privacy_helper:set_list(Alice, {<<"deny_client">>, Bob}), 240: 241: escalus:send(Alice, escalus_stanza:privacy_get_lists([<<"deny_client">>])), 242: Response = escalus:wait_for_stanza(Alice), 243: 244: <<"deny_client">> = exml_query:path(Response, [{element, <<"query">>}, 245: {element, <<"list">>}, 246: {attr, <<"name">>}]) 247: 248: end). 249: 250: activate(Config) -> 251: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 252: 253: privacy_helper:set_list(Alice, {<<"deny_client">>, Bob}), 254: 255: Request = escalus_stanza:privacy_activate(<<"deny_client">>), 256: escalus_client:send(Alice, Request), 257: 258: Response = escalus_client:wait_for_stanza(Alice), 259: escalus:assert(is_iq_result, Response) 260: 261: end). 262: 263: activate_nonexistent(Config) -> 264: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 265: 266: Request = escalus_stanza:privacy_activate(<<"some_list">>), 267: escalus_client:send(Alice, Request), 268: 269: Response = escalus_client:wait_for_stanza(Alice), 270: escalus:assert(is_error, [<<"cancel">>, <<"item-not-found">>], Response) 271: 272: end). 273: 274: deactivate(Config) -> 275: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 276: 277: Request = escalus_stanza:privacy_deactivate(), 278: escalus_client:send(Alice, Request), 279: 280: Response = escalus_client:wait_for_stanza(Alice), 281: escalus:assert(is_iq_result, Response) 282: 283: end). 284: 285: default(Config) -> 286: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 287: 288: privacy_helper:set_list(Alice, {<<"deny_client">>, Bob}), 289: 290: Request = escalus_stanza:privacy_set_default(<<"deny_client">>), 291: escalus_client:send(Alice, Request), 292: 293: Response = escalus_client:wait_for_stanza(Alice), 294: escalus:assert(is_iq_result, Response) 295: 296: end). 297: 298: default_conflict(Config) -> 299: escalus:fresh_story(Config, [{alice, 2}, {bob, 1}], fun(Alice, Alice2, Bob) -> 300: 301: %% testcase setup 302: %% setup list on server 303: privacy_helper:send_set_list(Alice, {<<"deny_client">>, Bob}), 304: privacy_helper:send_set_list(Alice, {<<"allow_client">>, Bob}), 305: %% skip responses 306: escalus_client:wait_for_stanzas(Alice, 4), 307: %% make a default list for Alice2 308: R1 = escalus_stanza:privacy_set_default(Alice2, <<"deny_client">>), 309: escalus_client:send(Alice2, R1), 310: escalus:assert_many([is_privacy_set, is_privacy_set, is_iq_result], 311: escalus_client:wait_for_stanzas(Alice2, 3)), 312: %% setup done 313: 314: Request = escalus_stanza:privacy_set_default(<<"allow_client">>), 315: escalus_client:send(Alice, Request), 316: 317: Response = escalus_client:wait_for_stanza(Alice), 318: %% TODO: should fail on this (result) and receive error 319: %% this is a bug and was filed to the esl redmine as Bug #7073 320: %true = exmpp_iq:is_result(Response), 321: %% but this should pass just fine 322: escalus:assert(is_error, [<<"cancel">>, <<"conflict">>], Response) 323: 324: end). 325: 326: default_nonexistent(Config) -> 327: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 328: 329: Request = escalus_stanza:privacy_set_default(<<"some_list">>), 330: escalus_client:send(Alice, Request), 331: 332: Response = escalus_client:wait_for_stanza(Alice), 333: escalus_assert:is_error(Response, <<"cancel">>, <<"item-not-found">>) 334: 335: end). 336: 337: no_default(Config) -> 338: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 339: 340: Request = escalus_stanza:privacy_no_default(), 341: escalus_client:send(Alice, Request), 342: 343: Response = escalus_client:wait_for_stanza(Alice), 344: escalus:assert(is_iq_result, Response) 345: 346: end). 347: 348: set_list(Config) -> 349: escalus:fresh_story(Config, [{alice, 3}, {bob, 1}], fun(Alice, Alice2, Alice3, Bob) -> 350: 351: privacy_helper:send_set_list(Alice, {<<"deny_client">>, Bob}), 352: 353: %% Verify that original Alice gets iq result and notification. 354: %% It's a bit quirky as these come in undefined order 355: %% (actually, they always came with 'push' first and then 'result', 356: %% but I suppose it's not mandatory). 357: AliceResponses = escalus_client:wait_for_stanzas(Alice, 2), 358: escalus:assert_many([ 359: fun escalus_pred:is_iq_result/1, 360: fun privacy_helper:is_privacy_list_push/1 361: ], AliceResponses), 362: 363: %% Verify that other resources also get the push. 364: escalus:assert(fun privacy_helper:is_privacy_list_push/1, 365: escalus:wait_for_stanza(Alice2)), 366: escalus:assert(fun privacy_helper:is_privacy_list_push/1, 367: escalus:wait_for_stanza(Alice3)) 368: 369: %% All in all, the spec requires the resources to reply 370: %% (as to every iq), but it's omitted here. 371: 372: end). 373: 374: remove_list(Config) -> 375: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 376: 377: privacy_helper:send_set_list(Alice, {<<"deny_client">>, Bob}), 378: 379: %% These are the pushed notification and iq result. 380: escalus_client:wait_for_stanzas(Alice, 2), 381: 382: %% Request list deletion by sending an empty list. 383: RemoveRequest = escalus_stanza:privacy_set_list( 384: escalus_stanza:privacy_list(<<"someList">>, [])), 385: escalus_client:send(Alice, RemoveRequest), 386: 387: %% These too are the pushed notification and iq result. 388: escalus:assert_many([ 389: fun privacy_helper:is_privacy_list_push/1, 390: is_iq_result 391: ], escalus_client:wait_for_stanzas(Alice, 2)), 392: 393: escalus_client:send(Alice, 394: escalus_stanza:privacy_get_lists([<<"someList">>])), 395: 396: %% Finally ensure that the list doesn't exist anymore. 397: escalus_assert:is_privacy_list_nonexistent_error( 398: escalus_client:wait_for_stanza(Alice)) 399: 400: end). 401: 402: block_jid_message(Config) -> 403: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 404: 405: %% Alice should receive message 406: escalus_client:send(Bob, 407: escalus_stanza:chat_to(Alice, <<"Hi! What's your name?">>)), 408: escalus_assert:is_chat_message(<<"Hi! What's your name?">>, 409: escalus_client:wait_for_stanza(Alice)), 410: 411: %% set the list on server and make it active 412: privacy_helper:set_and_activate(Alice, {<<"deny_client_message">>, Bob}), 413: 414: %% Alice should NOT receive message, while Bob gets error message 415: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, Alice!">>)), 416: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 417: timer:sleep(?SLEEP_TIME), 418: escalus_assert:has_no_stanzas(Alice), 419: 420: %% Blocking only applies to incoming messages, so Alice can still send 421: %% Bob a message 422: %% and Bob gets nothing 423: escalus_client:send(Alice, escalus_stanza:chat_to( 424: Bob, <<"Hi, Bobbb!">>)), 425: escalus_assert:is_chat_message(<<"Hi, Bobbb!">>, 426: escalus_client:wait_for_stanza(Bob)) 427: 428: end). 429: 430: block_group_message(Config) -> 431: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 432: 433: %% Alice should receive message 434: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 435: escalus_assert:is_chat_message(<<"Hi!">>, 436: escalus_client:wait_for_stanza(Alice)), 437: 438: %% add Bob to Alices' group 'ignored' 439: add_sample_contact(Alice, Bob, [<<"ignored">>], <<"Ugly Bastard">>), 440: 441: %% set the list on server and make it active 442: privacy_helper:set_and_activate(Alice, <<"deny_group_message">>), 443: 444: %% Alice should NOT receive message 445: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, blocked group!">>)), 446: timer:sleep(?SLEEP_TIME), 447: escalus_assert:has_no_stanzas(Alice), 448: privacy_helper:gets_error(Bob, <<"service-unavailable">>) 449: 450: end). 451: 452: block_subscription_message(Config) -> 453: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 454: 455: %% Alice should receive message 456: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 457: escalus_assert:is_chat_message(<<"Hi!">>, 458: escalus_client:wait_for_stanza(Alice)), 459: 460: %% Alice sends unsubscribe 461: Stanza = escalus_stanza:presence_direct(escalus_utils:get_short_jid(Bob), 462: <<"unsubscribe">>), 463: escalus_client:send(Alice, Stanza), 464: 465: %% set the list on server and make it active 466: privacy_helper:set_and_activate(Alice, <<"deny_unsubscribed_message">>), 467: 468: %% Alice should NOT receive message 469: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 470: timer:sleep(?SLEEP_TIME), 471: escalus_assert:has_no_stanzas(Alice), 472: privacy_helper:gets_error(Bob, <<"service-unavailable">>) 473: 474: end). 475: 476: allow_subscription_to_from_message(Config) -> 477: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 478: %% deny all message but not from subscribed "to" 479: privacy_helper:set_and_activate(Alice, <<"deny_all_message_but_subscription_to">>), 480: 481: %% deny all message but not from subscribed "from" 482: privacy_helper:set_and_activate(Bob, <<"deny_all_message_but_subscription_from">>), 483: 484: %% Bob and Alice cannot sent to each other now 485: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, Alice XYZ!">>)), 486: escalus_client:send(Alice, escalus_stanza:chat_to(Bob, <<"Hi, Bob XYZ!">>)), 487: 488: ct:sleep(?SLEEP_TIME), 489: %% they received just rejection msgs 490: privacy_helper:gets_error(Alice, <<"service-unavailable">>), 491: escalus_assert:has_no_stanzas(Alice), 492: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 493: escalus_assert:has_no_stanzas(Bob), 494: 495: %% Alice subscribes to Bob 496: subscribe_from_to(Alice, Bob, false), 497: 498: %% Now Alice is subscribed "to" Bob 499: %% And Bob is subscribed "from" Alice 500: 501: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, Alice XYZ!">>)), 502: escalus_assert:is_chat_message(<<"Hi, Alice XYZ!">>, 503: escalus_client:wait_for_stanza(Alice)), 504: 505: escalus_client:send(Alice, escalus_stanza:chat_to(Bob, <<"Hi, Bob XYZ!">>)), 506: escalus_assert:is_chat_message(<<"Hi, Bob XYZ!">>, 507: escalus_client:wait_for_stanza(Bob)) 508: 509: end). 510: 511: allow_subscription_both_message(Config) -> 512: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 513: 514: %% Alice subscribes to Bob 515: subscribe_from_to(Alice, Bob, false), 516: 517: %% deny all message but not from subscribed "to" 518: privacy_helper:set_and_activate(Alice, <<"deny_all_message_but_subscription_both">>), 519: 520: %% deny all message but not from subscribed "from" 521: privacy_helper:set_and_activate(Bob, <<"deny_all_message_but_subscription_both">>), 522: 523: %% Bob and Alice cannot write to each other now 524: %% Even though they are in subscription "to" and "from" respectively 525: escalus_client:send(Bob, escalus_stanza:chat_to( 526: Alice, <<"Hi, Alice XYZ!">>)), 527: escalus_client:send(Alice, escalus_stanza:chat_to( 528: Bob, <<"Hi, Bob XYZ 1!">>)), 529: 530: privacy_helper:gets_error(Alice, <<"service-unavailable">>), 531: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 532: escalus_assert:has_no_stanzas(Alice), 533: escalus_assert:has_no_stanzas(Bob), 534: 535: %% Bob subscribes to Alice 536: subscribe_from_to(Bob, Alice, true), 537: 538: %% Now their subscription is in state "both" 539: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, Alice XYZ!">>)), 540: escalus_assert:is_chat_message(<<"Hi, Alice XYZ!">>, 541: escalus_client:wait_for_stanza(Alice)), 542: 543: escalus_client:send(Alice, escalus_stanza:chat_to(Bob, <<"Hi, Bob XYZ! 2">>)), 544: escalus_assert:is_chat_message(<<"Hi, Bob XYZ! 2">>, 545: escalus_client:wait_for_stanza(Bob)) 546: 547: end). 548: 549: block_all_message(Config) -> 550: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 551: 552: %% Alice should receive message 553: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 554: escalus_assert:is_chat_message(<<"Hi!">>, 555: escalus_client:wait_for_stanza(Alice)), 556: 557: %% set the list on server and make it active 558: privacy_helper:set_and_activate(Alice, <<"deny_all_message">>), 559: 560: %% Alice should NOT receive message 561: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 562: timer:sleep(?SLEEP_TIME), 563: escalus_assert:has_no_stanzas(Alice), 564: privacy_helper:gets_error(Bob, <<"service-unavailable">>) 565: 566: end). 567: 568: block_jid_presence_in(Config) -> 569: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 570: 571: %% Alice should receive presence in 572: Presence1 = escalus_stanza:presence_direct(escalus_utils:get_short_jid(Alice), 573: <<"available">>), 574: escalus_client:send(Bob, Presence1), 575: Received = escalus_client:wait_for_stanza(Alice), 576: escalus:assert(is_presence, Received), 577: escalus_assert:is_stanza_from(Bob, Received), 578: 579: privacy_helper:set_and_activate(Alice, {<<"deny_client_presence_in">>, Bob}), 580: 581: %% Alice should NOT receive presence in 582: Presence2 = escalus_stanza:presence_direct(escalus_utils:get_short_jid(Alice), 583: <<"available">>), 584: escalus_client:send(Bob, Presence2), 585: timer:sleep(?SLEEP_TIME), 586: escalus_assert:has_no_stanzas(Alice), 587: %% and Bob should NOT receive any response 588: escalus_assert:has_no_stanzas(Bob) 589: 590: 591: end). 592: 593: block_jid_presence_out(Config) -> 594: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 595: 596: BobBareJID = escalus_utils:get_short_jid(Bob), 597: 598: %% Bob should receive presence in 599: Presence1 = escalus_stanza:presence_direct(BobBareJID, <<"available">>), 600: escalus_client:send(Alice, Presence1), 601: 602: Received = escalus_client:wait_for_stanza(Bob), 603: escalus:assert(is_presence, Received), 604: escalus_assert:is_stanza_from(Alice, Received), 605: 606: privacy_helper:set_and_activate(Alice, {<<"deny_client_presence_out">>, Bob}), 607: 608: %% Bob should NOT receive presence in 609: Presence2 = escalus_stanza:presence_direct(BobBareJID, <<"available">>), 610: escalus_client:send(Alice, Presence2), 611: 612: %% Alice gets an error back from mod_privacy 613: ErrorPresence = escalus_client:wait_for_stanza(Alice), 614: escalus:assert(is_presence_with_type, [<<"error">>], ErrorPresence), 615: 616: timer:sleep(?SLEEP_TIME), 617: escalus_assert:has_no_stanzas(Bob) 618: 619: end). 620: 621: version_iq(Type, From, To) -> 622: Req = escalus_stanza:iq(Type, [escalus_stanza:query_el(<<"jabber:iq:version">>, [])]), 623: Req1 = escalus_stanza:to(Req, To), 624: Req2= escalus_stanza:from(Req1, From), 625: Req2. 626: 627: iq_reply_doesnt_crash_user_process(Config) -> 628: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 629: 630: QueryWithPrivacyNS = escalus_stanza:query_el(?NS_PRIVACY, []), 631: %% Send IQ reply with privacy ns 632: %% Send message to check user process still alive 633: privacy_helper:does_user_process_crash(Alice, 634: Bob, 635: <<"error">>, 636: QueryWithPrivacyNS, 637: <<"Hello, Bob">>), 638: 639: privacy_helper:does_user_process_crash(Bob, 640: Alice, 641: <<"result">>, 642: QueryWithPrivacyNS, 643: <<"Hello, Alice">>) 644: end). 645: 646: block_jid_iq(Config) -> 647: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 648: 649: LServer = escalus_utils:get_server(Bob), 650: privacy_helper:set_list(Alice, {<<"deny_server_iq">>, LServer}), 651: %% activate it 652: Stanza = escalus_stanza:privacy_activate(<<"deny_server_iq">>), 653: escalus_client:send(Alice, Stanza), 654: timer:sleep(500), %% we must let it sink in 655: 656: %% bob queries for version and gets an error, Alice doesn't receive the query 657: escalus_client:send(Bob, version_iq(<<"get">>, Bob, Alice)), 658: timer:sleep(?SLEEP_TIME), 659: escalus_assert:has_no_stanzas(Alice), 660: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 661: %% this stanza does not make much sense, but is routed and rejected correctly 662: escalus_client:send(Bob, version_iq(<<"set">>, Bob, Alice)), 663: timer:sleep(?SLEEP_TIME), 664: escalus_assert:has_no_stanzas(Alice), 665: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 666: %% but another type, like result, is silently dropped 667: escalus_client:send(Bob, version_iq(<<"result">>, Bob, Alice)), 668: timer:sleep(?SLEEP_TIME), 669: escalus_assert:has_no_stanzas(Alice), 670: escalus_assert:has_no_stanzas(Bob) 671: 672: end). 673: 674: block_jid_all(Config) -> 675: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 676: 677: privacy_helper:set_list(Alice, {<<"deny_jid_all">>, Bob}), 678: 679: %% Alice blocks Bob 680: Stanza = escalus_stanza:privacy_activate(<<"deny_jid_all">>), 681: escalus_client:send(Alice, Stanza), 682: 683: %% IQ response is blocked; 684: %% do magic wait for the request to take effect 685: timer:sleep(200), 686: 687: %% From now on nothing whatsoever sent by Bob should reach Alice. 688: 689: %% Alice should NOT receive message, Bob receives err msg 690: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi!">>)), 691: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 692: 693: %% Alice should NOT receive presence-in from Bob, no err msg 694: AliceBareJID = escalus_utils:get_short_jid(Alice), 695: Presence1 = escalus_stanza:presence_direct(AliceBareJID, 696: <<"available">>), 697: escalus_client:send(Bob, Presence1), 698: timer:sleep(?SLEEP_TIME), 699: escalus_assert:has_no_stanzas(Bob), 700: 701: %% Bob should NOT receive presence-in from Alice, Alice receives err msg 702: BobBareJID = escalus_utils:get_short_jid(Bob), 703: Presence2 = escalus_stanza:presence_direct(BobBareJID, <<"available">>), 704: escalus_client:send(Alice, Presence2), 705: timer:sleep(?SLEEP_TIME), 706: privacy_helper:gets_error(Alice, <<"not-acceptable">>), 707: 708: %% Just set the toy list and en~sure that only 709: %% the notification push comes back. 710: privacy_helper:send_set_list(Alice, {<<"deny_client">>, Bob}), 711: 712: %% verify 713: timer:sleep(?SLEEP_TIME), 714: %% ...that nothing else reached Bob 715: escalus_assert:has_no_stanzas(Bob), 716: %% ...that Alice got a privacy push 717: Responses = escalus_client:wait_for_stanza(Alice), 718: escalus:assert(fun privacy_helper:is_privacy_list_push/1, Responses), 719: %% and Alice didn't get anything else 720: escalus_assert:has_no_stanzas(Alice) 721: 722: end). 723: 724: block_jid_message_but_not_presence(Config) -> 725: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 726: 727: %% Alice should receive message 728: Msg = escalus_stanza:chat_to(Alice, <<"Hi! What's your name?">>), 729: escalus_client:send(Bob, Msg), 730: escalus_assert:is_chat_message(<<"Hi! What's your name?">>, 731: escalus_client:wait_for_stanza(Alice)), 732: 733: %% set the list on server and make it active 734: privacy_helper:set_and_activate(Alice, {<<"deny_client_message">>, Bob}), 735: 736: %% Alice should NOT receive message 737: escalus_client:send(Bob, escalus_stanza:chat_to(Alice, <<"Hi, Alice!">>)), 738: timer:sleep(?SLEEP_TIME), 739: escalus_assert:has_no_stanzas(Alice), 740: privacy_helper:gets_error(Bob, <<"service-unavailable">>), 741: 742: %% ...but should receive presence in 743: escalus_client:send(Bob, 744: escalus_stanza:presence_direct(Alice, <<"available">>)), 745: Received = escalus_client:wait_for_stanza(Alice), 746: escalus:assert(is_presence, Received), 747: escalus_assert:is_stanza_from(Bob, Received) 748: 749: end). 750: 751: newly_blocked_presense_jid_by_new_list(Config) -> 752: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 753: add_sample_contact(Alice, Bob, [<<"My Friends">>], <<"Bobbie">>), 754: subscribe(Bob, Alice), 755: 756: %% Alice gets notification that a roster contact is now subscribed 757: escalus:assert(is_roster_set, escalus_client:wait_for_stanza(Alice)), 758: 759: %% Bob should receive presence in 760: Presence = escalus_stanza:presence_direct(escalus_client:short_jid(Bob), 761: <<"available">>), 762: escalus_client:send(Alice, Presence), 763: Received = escalus_client:wait_for_stanza(Bob), 764: escalus:assert(is_presence, Received), 765: escalus_assert:is_stanza_from(Alice, Received), 766: 767: privacy_helper:set_list( 768: Alice, <<"deny_bob_presence_out">>, 769: [escalus_stanza:privacy_list_jid_item(<<"1">>, <<"deny">>, 770: escalus_client:short_jid(Bob), 771: [<<"presence-out">>])]), 772: privacy_helper:activate_list(Alice, <<"deny_bob_presence_out">>), 773: 774: %% Bob should receive unavailable, per XEP-0016 2.11 775: Received2 = escalus_client:wait_for_stanza(Bob), 776: escalus:assert(is_presence_with_type, [<<"unavailable">>], Received2), 777: escalus_assert:is_stanza_from(Alice, Received2) 778: 779: end). 780: 781: newly_blocked_presense_jid_by_list_change(Config) -> 782: escalus:fresh_story(Config, [{alice, 1}, {bob, 1}], fun(Alice, Bob) -> 783: add_sample_contact(Alice, Bob, [<<"My Friends">>], <<"Bobbie">>), 784: subscribe(Bob, Alice), 785: 786: %% Alice gets notification that a roster contact is now subscribed 787: escalus:assert(is_roster_set, escalus_client:wait_for_stanza(Alice)), 788: 789: %% Alice sets up an initially empty privacy list 790: privacy_helper:set_and_activate(Alice, <<"noop_list">>), 791: 792: %% Bob should receive presence in 793: escalus_client:send(Alice, 794: escalus_stanza:presence_direct(Bob, <<"available">>)), 795: Received = escalus_client:wait_for_stanza(Bob), 796: escalus:assert(is_presence, Received), 797: escalus_assert:is_stanza_from(Alice, Received), 798: 799: %% Alice now adds Bob to her currently active privacy list 800: privacy_helper:set_list( 801: Alice, <<"noop_list">>, 802: [escalus_stanza:privacy_list_jid_item(<<"1">>, <<"deny">>, 803: escalus_client:short_jid(Bob), 804: [<<"presence-out">>])]), 805: 806: %% Bob should receive unavailable, per XEP-0016 2.11 807: Received2 = escalus_client:wait_for_stanza(Bob), 808: escalus:assert(is_presence_with_type, [<<"unavailable">>], Received2), 809: escalus_assert:is_stanza_from(Alice, Received2) 810: 811: end). 812: 813: newly_blocked_presence_not_notify_self(Config) -> 814: escalus:fresh_story(Config, [{alice, 1}], fun(Alice) -> 815: %% Alice sets up an initially empty privacy list 816: privacy_helper:set_and_activate(Alice, 817: <<"deny_not_both_presence_out">>), 818: 819: %% Alice should not receive an 'unavailable' because she's not a 820: %% contact of herself. 821: timer:sleep(?SLEEP_TIME), 822: escalus_assert:has_no_stanzas(Alice) 823: 824: end). 825: 826: %%----------------------------------------------------------------- 827: %% Helpers 828: %%----------------------------------------------------------------- 829: 830: add_sample_contact(Who, Whom, Groups, Nick) -> 831: escalus_client:send(Who, 832: escalus_stanza:roster_add_contact(Whom, 833: Groups, 834: Nick)), 835: Received = escalus_client:wait_for_stanza(Who), 836: escalus_assert:is_roster_set(Received), 837: escalus_client:send(Who, escalus_stanza:iq_result(Received)), 838: escalus:assert(is_iq_result, escalus:wait_for_stanza(Who)). 839: 840: subscribe(Who, Whom) -> 841: % 'Who' sends a subscribe request to 'Whom' 842: escalus:send(Who, escalus_stanza:presence_direct( 843: escalus_client:short_jid(Whom), <<"subscribe">>)), 844: PushReq = escalus:wait_for_stanza(Who), 845: escalus:assert(is_roster_set, PushReq), 846: escalus:send(Who, escalus_stanza:iq_result(PushReq)), 847: 848: %% 'Whom' receives subscription request 849: Received = escalus:wait_for_stanza(Whom), 850: escalus:assert(is_presence_with_type, [<<"subscribe">>], Received), 851: 852: %% 'Whom' adds new contact to their roster 853: escalus:send(Whom, escalus_stanza:roster_add_contact(Who, 854: [<<"enemies">>], 855: <<"Enemy1">>)), 856: PushReq2 = escalus:wait_for_stanza(Whom), 857: escalus:assert(is_roster_set, PushReq2), 858: escalus:send(Whom, escalus_stanza:iq_result(PushReq2)), 859: escalus:assert(is_iq_result, escalus:wait_for_stanza(Whom)), 860: 861: %% 'Whom' sends subscribed presence 862: escalus:send(Whom, escalus_stanza:presence_direct( 863: escalus_client:short_jid(Who), <<"subscribed">>)), 864: 865: %% 'Who' receives subscribed 866: Stanzas = escalus:wait_for_stanzas(Who, 2), 867: 868: check_subscription_stanzas(Stanzas, <<"subscribed">>), 869: escalus:assert(is_presence, escalus:wait_for_stanza(Who)). 870: 871: check_subscription_stanzas(Stanzas, Type) -> 872: IsPresWithType = fun(S) -> 873: escalus_pred:is_presence_with_type(Type, S) 874: end, 875: escalus:assert_many([is_roster_set, IsPresWithType], Stanzas). 876: 877: subscribe_from_to(From, To, IsSecondSubscription) -> 878: %% From subscribes to To 879: ToBareJid = escalus_utils:get_short_jid(To), 880: SubStanza = escalus_stanza:presence_direct(ToBareJid, <<"subscribe">>), 881: escalus_client:send(From, SubStanza), 882: PushReq = escalus_client:wait_for_stanza(From), 883: escalus:assert(is_roster_set, PushReq), 884: Received = escalus_client:wait_for_stanza(To), 885: %% To accepts From 886: FromBareJid = escalus_utils:get_short_jid(From), 887: SubConfirmStanza = escalus_stanza:presence_direct(FromBareJid, <<"subscribed">>), 888: escalus_client:send(To, SubConfirmStanza), 889: case IsSecondSubscription of 890: true -> 891: escalus:assert(is_roster_set, Received), 892: escalus_client:wait_for_stanzas(To, 2); 893: false -> 894: escalus:assert(is_presence_with_type, [<<"subscribe">>], Received), 895: escalus_client:wait_for_stanza(To) 896: end, 897: escalus_client:wait_for_stanzas(From, 3).