test_invisible_separator.rb

 1# frozen_string_literal: true
 2
 3require "test_helper"
 4require_relative "../../sgx-bwmsgsv2"
 5require "rantly/minitest_extensions"
 6require_relative "rantly_extensions/data_extensions"
 7
 8class InvisibleSeparatorPropertyTest < Minitest::Test
 9	def setup
10		reset_stanzas!
11		reset_redis!
12		WebMock.reset!
13	end
14
15	BW_MESSAGES_URL =
16		"https://messaging.bandwidth.com/api/v2/users/account/messages"
17
18	def test_message_containing_invisible_separator_is_rejected
19		property_of {
20			chars = message_body(nil_pct: 0).chars
21			insertions = range(1, 3)
22			insertions.times { chars.insert(range(0, chars.length), "\u2063") }
23			body = chars.join
24
25			dest = nanpa_phone
26			[body, dest]
27		}.check { |body, dest|
28			reset_stanzas!
29			reset_redis!
30			WebMock.reset!
31
32			m = Blather::Stanza::Message.new("#{dest}@component", body)
33			m.from = "test@example.com"
34			process_stanza(m)
35
36			assert_equal 1, written.length,
37			             "Expected exactly one error stanza for body: #{body.inspect}"
38
39			stanza = Blather::XMPPNode.parse(written.first.to_xml)
40			assert stanza.error?,
41			       "Expected error stanza for body: #{body.inspect}"
42
43			error = stanza.find_first("error")
44			assert_equal "wait", error["type"],
45			             "Expected error type 'wait' for body: #{body.inspect}"
46			assert_equal "recipient-unavailable", xmpp_error_name(error),
47			             "Expected 'recipient-unavailable' for body: #{body.inspect}"
48		}
49	end
50	em :test_message_containing_invisible_separator_is_rejected
51
52	def test_message_without_invisible_separator_is_not_rejected_as_unavailable
53		property_of {
54			dest = nanpa_phone
55			[message_body(nil_pct: 0, empty_pct: 0), dest]
56		}.check { |body, dest|
57			reset_stanzas!
58			reset_redis!
59			WebMock.reset!
60
61			m = Blather::Stanza::Message.new("#{dest}@component", body)
62			m.from = "test@example.com"
63
64			# WebMock's JSON parser does ad-hoc conversion to YAML (!!!!)
65			# then returns the parsed YAML object and pretends it's JSON.
66			# The YAML parser chokes on (at least) backslashes. Avoid that
67			# mess when you can.
68			bw_req = stub_request(:post, BW_MESSAGES_URL).with { |req|
69				parsed = ::JSON.parse(req.body)
70				parsed["to"] == dest &&
71					(parsed["text"] == m.body.to_s ||
72					 (parsed["text"] == "" && parsed["media"]))
73			}.to_return(
74				status: 201,
75				body: JSON.dump(id: "bw-msg-stub")
76			)
77
78			process_stanza(m)
79
80			assert_empty written,
81			             "Expected no error stanzas for body: #{body.inspect}"
82			assert_requested bw_req
83		}
84	end
85	em :test_message_without_invisible_separator_is_not_rejected_as_unavailable
86end