madmimi 1.0.16 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (115) hide show
  1. checksums.yaml +7 -0
  2. data/.rspec +2 -0
  3. data/Gemfile +12 -0
  4. data/Gemfile.lock +93 -0
  5. data/README.rdoc +88 -37
  6. data/Rakefile +2 -30
  7. data/VERSION +1 -1
  8. data/config/paths.yml +23 -0
  9. data/lib/madmimi.rb +210 -123
  10. data/madmimi.gemspec +130 -22
  11. data/spec/cassettes/add_to_list/success.yml +54 -0
  12. data/spec/cassettes/add_to_list/user_does_not_exist.yml +165 -0
  13. data/spec/cassettes/add_to_list/user_existed.yml +54 -0
  14. data/spec/cassettes/add_to_list/user_exists.yml +171 -0
  15. data/spec/cassettes/add_to_list/user_updated.yml +174 -0
  16. data/spec/cassettes/add_user/user_did_not_exist.yml +54 -0
  17. data/spec/cassettes/add_user/user_exist.yml +303 -0
  18. data/spec/cassettes/add_user/user_existed.yml +54 -0
  19. data/spec/cassettes/add_user/user_missing.yml +138 -0
  20. data/spec/cassettes/add_user/user_updated.yml +153 -0
  21. data/spec/cassettes/add_users/users_did_not_exist.yml +54 -0
  22. data/spec/cassettes/add_users/users_exist.yml +326 -0
  23. data/spec/cassettes/add_users/users_existed.yml +54 -0
  24. data/spec/cassettes/add_users/users_missing.yml +305 -0
  25. data/spec/cassettes/add_users/users_updated.yml +327 -0
  26. data/spec/cassettes/add_users_to_list/gained_membership.yml +107 -0
  27. data/spec/cassettes/add_users_to_list/missing_membership.yml +174 -0
  28. data/spec/cassettes/add_users_to_list/users_did_not_exist.yml +54 -0
  29. data/spec/cassettes/add_users_to_list/users_exist.yml +365 -0
  30. data/spec/cassettes/add_users_to_list/users_existed.yml +54 -0
  31. data/spec/cassettes/add_users_to_list/users_missing.yml +341 -0
  32. data/spec/cassettes/add_users_to_list/users_updated.yml +365 -0
  33. data/spec/cassettes/audience_search/does_not_include_suppressed_users.yml +76 -0
  34. data/spec/cassettes/audience_search/includes_suppressed_users.yml +86 -0
  35. data/spec/cassettes/csv_import/success.yml +54 -0
  36. data/spec/cassettes/csv_import/users_exist.yml +273 -0
  37. data/spec/cassettes/csv_import/users_missing.yml +381 -0
  38. data/spec/cassettes/delete_list/exists.yml +57 -0
  39. data/spec/cassettes/delete_list/fail.yml +54 -0
  40. data/spec/cassettes/delete_list/not_exists.yml +56 -0
  41. data/spec/cassettes/delete_list/success.yml +54 -0
  42. data/spec/cassettes/delete_list/users_exist.yml +129 -0
  43. data/spec/cassettes/list_members/multiple.yml +68 -0
  44. data/spec/cassettes/list_members/single.yml +68 -0
  45. data/spec/cassettes/lists/multiple.yml +56 -0
  46. data/spec/cassettes/lists/single.yml +55 -0
  47. data/spec/cassettes/mailing_stats/mailing_does_not_exist.yml +50 -0
  48. data/spec/cassettes/mailing_stats/promotion_and_mailing_exist.yml +57 -0
  49. data/spec/cassettes/mailing_stats/promotion_does_not_exist.yml +50 -0
  50. data/spec/cassettes/members/multiple.yml +174 -0
  51. data/spec/cassettes/members/single.yml +61 -0
  52. data/spec/cassettes/memberships/multiple.yml +56 -0
  53. data/spec/cassettes/memberships/single.yml +108 -0
  54. data/spec/cassettes/new_list/exists.yml +57 -0
  55. data/spec/cassettes/new_list/fail.yml +52 -0
  56. data/spec/cassettes/new_list/not_exists.yml +56 -0
  57. data/spec/cassettes/new_list/success.yml +52 -0
  58. data/spec/cassettes/promotions/multiple.yml +63 -0
  59. data/spec/cassettes/promotions/single.yml +61 -0
  60. data/spec/cassettes/remove_from_all_list/user_does_not_have_memberships.yml +60 -0
  61. data/spec/cassettes/remove_from_all_lists/user_has_memberships.yml +113 -0
  62. data/spec/cassettes/remove_from_all_lists/user_with_memberships.yml +49 -0
  63. data/spec/cassettes/remove_from_list/user_does_not_exist.yml +49 -0
  64. data/spec/cassettes/remove_from_list/user_in_list_does_not_exist.yml +62 -0
  65. data/spec/cassettes/remove_from_list/user_in_list_exists.yml +68 -0
  66. data/spec/cassettes/remove_from_list/user_in_the_list.yml +49 -0
  67. data/spec/cassettes/remove_from_list/user_not_in_the_list.yml +49 -0
  68. data/spec/cassettes/save_promotion/only_plain_text.yml +56 -0
  69. data/spec/cassettes/save_promotion/only_raw_html.yml +56 -0
  70. data/spec/cassettes/save_promotion/promotion_exists.yml +65 -0
  71. data/spec/cassettes/save_promotion/promotion_missing.yml +63 -0
  72. data/spec/cassettes/save_promotion/raw_html_and_plain_text.yml +56 -0
  73. data/spec/cassettes/send_html/promotion_does_not_exist.yml +56 -0
  74. data/spec/cassettes/send_html/send_single.yml +53 -0
  75. data/spec/cassettes/send_html/send_to_all.yml +56 -0
  76. data/spec/cassettes/send_html/send_to_list.yml +56 -0
  77. data/spec/cassettes/send_mail/promotion_does_not_exist.yml +54 -0
  78. data/spec/cassettes/send_mail/send_single.yml +53 -0
  79. data/spec/cassettes/send_mail/send_to_all.yml +56 -0
  80. data/spec/cassettes/send_mail/send_to_list.yml +56 -0
  81. data/spec/cassettes/send_plaintext/promotion_does_not_exist.yml +56 -0
  82. data/spec/cassettes/send_plaintext/send_single.yml +53 -0
  83. data/spec/cassettes/send_plaintext/send_to_all.yml +56 -0
  84. data/spec/cassettes/send_plaintext/send_to_list.yml +56 -0
  85. data/spec/cassettes/send_plaintext/tracking_beacon_missing.yml +56 -0
  86. data/spec/cassettes/status/transactional_mail_does_not_exist.yml +51 -0
  87. data/spec/cassettes/status/transactional_mail_exists.yml +53 -0
  88. data/spec/cassettes/suppress_email/already_suppressed.yml +51 -0
  89. data/spec/cassettes/suppress_email/not_suppressed.yml +102 -0
  90. data/spec/cassettes/suppress_email/user_does_not_exist.yml +100 -0
  91. data/spec/cassettes/suppress_email/user_is_now_suppressed.yml +51 -0
  92. data/spec/cassettes/suppress_email/user_not_suppressed.yml +51 -0
  93. data/spec/cassettes/suppressed/member_does_not_exist.yml +49 -0
  94. data/spec/cassettes/suppressed/member_is_not_suppressed.yml +51 -0
  95. data/spec/cassettes/suppressed/member_is_suppressed.yml +51 -0
  96. data/spec/cassettes/suppressed_since/members_exist.yml +56 -0
  97. data/spec/cassettes/suppressed_since/no_members.yml +56 -0
  98. data/spec/cassettes/unsuppress_email/already_suppressed.yml +100 -0
  99. data/spec/cassettes/unsuppress_email/not_suppressed.yml +99 -0
  100. data/spec/cassettes/unsuppress_email/user_does_not_exist.yml +99 -0
  101. data/spec/cassettes/unsuppress_email/user_is_now_unsuppressed.yml +49 -0
  102. data/spec/cassettes/unsuppress_email/user_suppressed.yml +51 -0
  103. data/spec/cassettes/update_email/user_does_not_have_permission.yml +52 -0
  104. data/spec/cassettes/update_email/user_existed.yml +54 -0
  105. data/spec/cassettes/update_email/user_missing.yml +52 -0
  106. data/spec/cassettes/update_email/user_with_new_email.yml +345 -0
  107. data/spec/cassettes/update_email/user_with_old_email.yml +345 -0
  108. data/spec/madmimi_spec.rb +1166 -0
  109. data/spec/spec_helper.rb +15 -0
  110. metadata +210 -96
  111. data/test/fixtures/lists.xml +0 -7
  112. data/test/fixtures/promotions.xml +0 -10
  113. data/test/fixtures/search.xml +0 -38
  114. data/test/helper.rb +0 -43
  115. data/test/test_madmimi.rb +0 -63
@@ -0,0 +1,1166 @@
1
+ require 'spec_helper'
2
+
3
+ describe MadMimi do
4
+
5
+ let(:default_mad_mimi) {
6
+ MadMimi.new('test@example.com', 'TEST_API_KEY')
7
+ }
8
+
9
+ let(:mad_mimi) {
10
+ default_mad_mimi.tap{ |m| m.raise_exceptions = false }
11
+ }
12
+
13
+ context "#initialize" do
14
+ context 'using default settings' do
15
+ subject { MadMimi.new('USERNAME', 'APIKEY') }
16
+
17
+ it 'sets username and api key' do
18
+ expect(subject.username).to eq('USERNAME')
19
+ expect(subject.api_key).to eq('APIKEY')
20
+ end
21
+
22
+ it 'sets verify_ssl to true' do
23
+ expect(subject.verify_ssl?).to be_truthy
24
+ end
25
+
26
+ it 'sets raise_exceptions to false' do
27
+ expect(subject.raise_exceptions?).to be_falsy
28
+ end
29
+ end
30
+
31
+ context 'using custom options' do
32
+ subject { MadMimi.new('USERNAME', 'APIKEY', { raise_exceptions: true, verify_ssl: false }) }
33
+
34
+ it 'sets correctly verify_ssl flag' do
35
+ expect(subject.verify_ssl?).to be_falsy
36
+ end
37
+
38
+ it 'sets correctly raise_exceptions flag' do
39
+ expect(subject.raise_exceptions?).to be_truthy
40
+ end
41
+ end
42
+ end
43
+
44
+ context '#lists', :vcr => { :cassette_name => 'lists' } do
45
+ subject { mad_mimi.lists }
46
+
47
+ context 'when there is a single list', :vcr => { :cassette_name => 'lists/single' } do
48
+ it 'returns an array of hashes' do
49
+ expect(subject['lists']['list']).to be_an(Array)
50
+ end
51
+ end
52
+
53
+ context 'when there are multiple lists', :vcr => { :cassette_name => 'lists/multiple' } do
54
+ it 'returns an array of hashes' do
55
+ expect(subject['lists']['list']).to be_an(Array)
56
+ end
57
+ end
58
+ end
59
+
60
+ context '#memberships', :vcr => { :cassette_name => 'memberships' } do
61
+ subject { mad_mimi.memberships('new_test1@example.com') }
62
+
63
+ context 'when there is a single membership', :vcr => { :cassette_name => 'memberships/single' } do
64
+ it 'returns an array of hashes' do
65
+ expect(subject['lists']['list']).to be_an(Array)
66
+ end
67
+ end
68
+
69
+ context 'when there are multiple memberships', :vcr => { :cassette_name => 'memberships/multiple' } do
70
+ it 'returns an array of hashes' do
71
+ expect(subject['lists']['list']).to be_an(Array)
72
+ end
73
+ end
74
+ end
75
+
76
+ context '#new_list', :vcr => { :cassette_name => 'new_list' } do
77
+ subject { mad_mimi.new_list('new list 1') }
78
+
79
+ context 'when there is no such list', :vcr => { :cassette_name => 'new_list/success' } do
80
+ it 'returns a success response' do
81
+ expect(subject['success']).to be_truthy
82
+ end
83
+
84
+ it 'creates a new list' do
85
+ VCR.use_cassette('new_list/not_exists') do
86
+ expect(mad_mimi.lists['lists']['list'].any?{ |l| l['name'] == 'new list 1' }).to be_falsy
87
+ end
88
+
89
+ subject
90
+
91
+ VCR.use_cassette('new_list/exists') do
92
+ expect(mad_mimi.lists['lists']['list'].any?{ |l| l['name'] == 'new list 1' }).to be_truthy
93
+ end
94
+ end
95
+ end
96
+
97
+ context 'when there is already the list', :vcr => { :cassette_name => 'new_list/fail' } do
98
+ it 'returns a falsy response' do
99
+ expect(subject['success']).to be_falsy
100
+ end
101
+
102
+ it 'returns an error message' do
103
+ expect(subject['error']).to include('already been taken')
104
+ end
105
+ end
106
+ end
107
+
108
+ context '#delete_list', :vcr => { :cassette_name => 'delete_list' } do
109
+ subject { mad_mimi.delete_list('new list 1') }
110
+
111
+ context 'when list exists', :vcr => { :cassette_name => 'delete_list/success' } do
112
+ it 'returns an empty response' do
113
+ expect(subject).to eq(' ')
114
+ end
115
+
116
+ it 'deletes the list' do
117
+ VCR.use_cassette('delete_list/exists') do
118
+ expect(mad_mimi.lists['lists']['list'].any?{ |l| l['name'] == 'new list 1' }).to be_truthy
119
+ end
120
+
121
+ subject
122
+
123
+ VCR.use_cassette('delete_list/not_exists') do
124
+ expect(mad_mimi.lists['lists']['list'].any?{ |l| l['name'] == 'new list 1' }).to be_falsy
125
+ end
126
+ end
127
+ end
128
+
129
+ context 'when list does not exist', :vcr => { :cassette_name => 'delete_list/fail' } do
130
+ it 'returns an empty response' do
131
+ expect(subject).to eq(' ')
132
+ end
133
+ end
134
+ end
135
+
136
+ context '#csv_import', :vcr => { :cassette_name => 'csv_import/success' } do
137
+ subject { mad_mimi.csv_import("email,firstname,lastname\ncsv_test@example.com,test,csv\ncsv_test2@example.com,test2,csv2\n") }
138
+
139
+ it 'returns an id of import' do
140
+ expect(subject).to be_present
141
+ expect(subject.to_i).to be > 0
142
+ end
143
+
144
+ it 'imports the list' do
145
+ VCR.use_cassette('csv_import/users_missing') do
146
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'csv_test@example.com' }).to be_falsy
147
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'csv_test2@example.com' }).to be_falsy
148
+ end
149
+
150
+ subject
151
+
152
+ VCR.use_cassette('csv_import/users_exist') do
153
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'csv_test@example.com' }).to be_truthy
154
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'csv_test2@example.com' }).to be_truthy
155
+ end
156
+ end
157
+ end
158
+
159
+ context '#add_user' do
160
+ subject {
161
+ mad_mimi.add_user({
162
+ :email => 'add_user@example.com',
163
+ :firstname => 'AddUser',
164
+ :custom_value_1 => 'add_user'
165
+ })
166
+ }
167
+
168
+ context 'when user does not exist', :vcr => { :cassette_name => 'add_user/user_did_not_exist' } do
169
+ it 'returns an id of import' do
170
+ expect(subject).to be_present
171
+ expect(subject.to_i).to be > 0
172
+ end
173
+
174
+ it 'creates a user' do
175
+ VCR.use_cassette('add_user/user_missing') do
176
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
177
+ m['email'] == 'add_user@example.com' &&
178
+ m['first_name'] == 'AddUser' &&
179
+ m['custom_value_1'] == 'add_user'
180
+ }).to be_falsy
181
+ end
182
+
183
+ subject
184
+
185
+ VCR.use_cassette('add_user/user_exist') do
186
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
187
+ m['email'] == 'add_user@example.com' &&
188
+ m['first_name'] == 'AddUser' &&
189
+ m['custom_value_1'] == 'add_user'
190
+ }).to be_truthy
191
+ end
192
+ end
193
+ end
194
+
195
+ context 'when user exists', :vcr => { :cassette_name => 'add_user/user_existed' } do
196
+ subject {
197
+ mad_mimi.add_user({
198
+ :email => 'add_user@example.com',
199
+ :firstname => 'AddUser',
200
+ :custom_value_1 => 'updated'
201
+ })
202
+ }
203
+
204
+ it 'returns an id of import' do
205
+ expect(subject).to be_present
206
+ expect(subject.to_i).to be > 0
207
+ end
208
+
209
+ it 'updates user' do
210
+ VCR.use_cassette('add_user/user_exist') do
211
+ member = mad_mimi.members['audience']['member'].select{ |m|
212
+ m['email'] == 'add_user@example.com' &&
213
+ m['first_name'] == 'AddUser'
214
+ }.first
215
+
216
+ expect(member).to be_present
217
+ expect(member['custom_value_1']).to eq('add_user')
218
+ end
219
+
220
+ subject
221
+
222
+ VCR.use_cassette('add_user/user_updated') do
223
+ member = mad_mimi.members['audience']['member'].select{ |m|
224
+ m['email'] == 'add_user@example.com' &&
225
+ m['first_name'] == 'AddUser'
226
+ }.first
227
+
228
+ expect(member).to be_present
229
+ expect(member['custom_value_1']).to eq('updated')
230
+ end
231
+ end
232
+ end
233
+ end
234
+
235
+ context '#add_users' do
236
+ subject {
237
+ mad_mimi.add_users([
238
+ {
239
+ :email => 'add_users1@example.com',
240
+ :firstname => 'AddUsers1',
241
+ :custom_value_1 => 'add_users1'
242
+ },
243
+ {
244
+ :email => 'add_users2@example.com',
245
+ :firstname => 'AddUsers2',
246
+ :custom_value_2 => 'add_users2'
247
+ }
248
+ ])
249
+ }
250
+
251
+ context 'when user does not exist', :vcr => { :cassette_name => 'add_users/users_did_not_exist' } do
252
+ it 'returns an id of import' do
253
+ expect(subject).to be_present
254
+ expect(subject.to_i).to be > 0
255
+ end
256
+
257
+ it 'creates users' do
258
+ VCR.use_cassette('add_users/users_missing') do
259
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
260
+ m['email'] == 'add_users1@example.com' &&
261
+ m['first_name'] == 'AddUsers1' &&
262
+ m['custom_value_1'] == 'add_users1'
263
+ }).to be_falsy
264
+
265
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
266
+ m['email'] == 'add_users2@example.com' &&
267
+ m['first_name'] == 'AddUsers2' &&
268
+ m['custom_value_2'] == 'add_users2'
269
+ }).to be_falsy
270
+ end
271
+
272
+ subject
273
+
274
+ VCR.use_cassette('add_users/users_exist') do
275
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
276
+ m['email'] == 'add_users1@example.com' &&
277
+ m['first_name'] == 'AddUsers1' &&
278
+ m['custom_value_1'] == 'add_users1'
279
+ }).to be_truthy
280
+
281
+ expect(mad_mimi.members['audience']['member'].any?{ |m|
282
+ m['email'] == 'add_users2@example.com' &&
283
+ m['first_name'] == 'AddUsers2' &&
284
+ m['custom_value_2'] == 'add_users2'
285
+ }).to be_truthy
286
+ end
287
+ end
288
+ end
289
+
290
+ context 'when users exist', :vcr => { :cassette_name => 'add_users/users_existed' } do
291
+ subject {
292
+ mad_mimi.add_users([
293
+ {
294
+ :email => 'add_users1@example.com',
295
+ :firstname => 'AddUsers1',
296
+ :custom_value_1 => 'updated1'
297
+ },
298
+ {
299
+ :email => 'add_users2@example.com',
300
+ :firstname => 'AddUsers2',
301
+ :custom_value_2 => 'updated2'
302
+ }
303
+ ])
304
+ }
305
+
306
+ it 'returns an id of import' do
307
+ expect(subject).to be_present
308
+ expect(subject.to_i).to be > 0
309
+ end
310
+
311
+ it 'updates user' do
312
+ VCR.use_cassette('add_users/users_exist') do
313
+ member1 = mad_mimi.members['audience']['member'].select{ |m|
314
+ m['email'] == 'add_users1@example.com' &&
315
+ m['first_name'] == 'AddUsers1'
316
+ }.first
317
+
318
+ expect(member1).to be_present
319
+ expect(member1['custom_value_1']).to eq('add_users1')
320
+
321
+ member2 = mad_mimi.members['audience']['member'].select{ |m|
322
+ m['email'] == 'add_users2@example.com' &&
323
+ m['first_name'] == 'AddUsers2'
324
+ }.first
325
+
326
+ expect(member2).to be_present
327
+ expect(member2['custom_value_2']).to eq('add_users2')
328
+ end
329
+
330
+ subject
331
+
332
+ VCR.use_cassette('add_users/users_updated') do
333
+ member1 = mad_mimi.members['audience']['member'].select{ |m|
334
+ m['email'] == 'add_users1@example.com' &&
335
+ m['first_name'] == 'AddUsers1'
336
+ }.first
337
+
338
+ expect(member1).to be_present
339
+ expect(member1['custom_value_1']).to eq('updated1')
340
+
341
+ member2 = mad_mimi.members['audience']['member'].select{ |m|
342
+ m['email'] == 'add_users2@example.com' &&
343
+ m['first_name'] == 'AddUsers2'
344
+ }.first
345
+
346
+ expect(member2).to be_present
347
+ expect(member2['custom_value_2']).to eq('updated2')
348
+ end
349
+ end
350
+ end
351
+ end
352
+
353
+ context '#add_to_list' do
354
+ subject { mad_mimi.add_to_list('test@example.com', 'list 1', { :custom_value => 'new value' }) }
355
+
356
+ context 'when user does not exist', :vcr => { :cassette_name => 'add_to_list/success' } do
357
+ it "creates user" do
358
+ VCR.use_cassette('add_to_list/user_does_not_exist') do
359
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_falsy
360
+ end
361
+
362
+ subject
363
+
364
+ VCR.use_cassette('add_to_list/user_exists') do
365
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_truthy
366
+ end
367
+ end
368
+ end
369
+
370
+ context 'when user exists', :vcr => { :cassette_name => 'add_to_list/user_existed'} do
371
+ subject { mad_mimi.add_to_list('test@example.com', 'list 1', { :custom_value => 'updated value' }) }
372
+
373
+ it "updates user" do
374
+ VCR.use_cassette('add_to_list/user_exists') do
375
+ member = mad_mimi.members['audience']['member'].select{ |m| m['email'] == 'test@example.com' }.first
376
+ expect(member['custom_value']).to eq('new value')
377
+ end
378
+
379
+ subject
380
+
381
+ VCR.use_cassette('add_to_list/user_updated') do
382
+ member = mad_mimi.members['audience']['member'].select{ |m| m['email'] == 'test@example.com' }.first
383
+ expect(member['custom_value']).to eq('updated value')
384
+ end
385
+ end
386
+ end
387
+ end
388
+
389
+ context '#remove_from_list' do
390
+ subject { mad_mimi.remove_from_list('test@example.com', 'list 1') }
391
+
392
+ context 'when user is in the list', :vcr => { :cassette_name => 'remove_from_list/user_in_the_list' } do
393
+ it "returns empty response" do
394
+ expect(subject).to be_nil
395
+ end
396
+
397
+ it "removes user from list" do
398
+ VCR.use_cassette('remove_from_list/user_in_list_exists') do
399
+ expect(mad_mimi.list_members('list 1')['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_truthy
400
+ end
401
+
402
+ subject
403
+
404
+ VCR.use_cassette('remove_from_list/user_in_list_does_not_exist') do
405
+ expect(mad_mimi.list_members('list 1')['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_falsy
406
+ end
407
+ end
408
+ end
409
+
410
+ context 'when user is not in the list', :vcr => { :cassette_name => 'remove_from_list/user_not_in_the_list' } do
411
+ it "returns empty response" do
412
+ expect(subject).to be_nil
413
+ end
414
+ end
415
+
416
+ context 'when user does not exist', :vcr => { :cassette_name => 'remove_from_list/user_does_not_exist' } do
417
+ subject { mad_mimi.remove_from_list('wrong@example.com', 'list 1') }
418
+
419
+ it "returns empty response" do
420
+ expect(subject).to be_nil
421
+ end
422
+ end
423
+ end
424
+
425
+ context '#remove_from_all_lists' do
426
+ subject { mad_mimi.remove_from_all_lists('test@example.com') }
427
+
428
+ context 'when user has memberships', :vcr => { :cassette_name => 'remove_from_all_lists/user_with_memberships' } do
429
+ it "removes user from all lists" do
430
+ VCR.use_cassette('remove_from_all_lists/user_has_memberships') do
431
+ expect(mad_mimi.memberships('test@example.com')['lists']['list']).not_to be_empty
432
+ end
433
+
434
+ subject
435
+
436
+ VCR.use_cassette('remove_from_all_list/user_does_not_have_memberships') do
437
+ expect(mad_mimi.memberships('test@example.com')['lists']).to be_nil
438
+ end
439
+ end
440
+ end
441
+ end
442
+
443
+ context '#update_email' do
444
+ subject { mad_mimi.update_email('test@example.com', 'updated@example.com') }
445
+
446
+ context 'when user has permission' do
447
+ context 'when user exists', :vcr => { :cassette_name => 'update_email/user_existed' } do
448
+ it "updates email" do
449
+ VCR.use_cassette('update_email/user_with_old_email') do
450
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_truthy
451
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'updated@example.com' }).to be_falsy
452
+ end
453
+
454
+ subject
455
+
456
+ VCR.use_cassette('update_email/user_with_new_email') do
457
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_falsy
458
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'updated@example.com' }).to be_truthy
459
+ end
460
+ end
461
+ end
462
+
463
+ context 'when user does not exist', :vcr => { :cassette_name => 'update_email/user_missing' } do
464
+ it "returns empty response" do
465
+ expect(subject).to include('does not exist')
466
+ end
467
+ end
468
+ end
469
+
470
+ context 'when user does not have permission', :vcr => { :cassette_name => 'update_email/user_does_not_have_permission' } do
471
+ context 'if should raise exception' do
472
+ before(:each) { mad_mimi.raise_exceptions = true }
473
+
474
+ it "raises an error" do
475
+ expect{ subject }.to raise_error(Net::HTTPServerException)
476
+ end
477
+ end
478
+
479
+ context 'if should not raise exception' do
480
+ before(:each) { mad_mimi.raise_exceptions = false }
481
+
482
+ it "returns an error" do
483
+ expect(subject).to eq('You do not have the rights to use this API')
484
+ end
485
+ end
486
+ end
487
+ end
488
+
489
+ context '#members' do
490
+ subject { mad_mimi.members }
491
+
492
+ context 'when there is only one member', :vcr => { :cassette_name => 'members/single' } do
493
+ it 'returns count equal to one' do
494
+ expect(subject['audience']['count'].to_i).to eq(1)
495
+ end
496
+
497
+ it 'returns an array of hashes' do
498
+ expect(subject['audience']['member']).to be_an(Array)
499
+ end
500
+ end
501
+
502
+ context 'when there are multiple members', :vcr => { :cassette_name => 'members/multiple' } do
503
+ it 'returns count greater than one' do
504
+ expect(subject['audience']['count'].to_i).to be > 1
505
+ end
506
+
507
+ it 'returns an array of hashes' do
508
+ expect(subject['audience']['member']).to be_an(Array)
509
+ end
510
+ end
511
+ end
512
+
513
+ context '#list_members' do
514
+ subject { mad_mimi.list_members('list 1') }
515
+
516
+ context 'when there is only one member', :vcr => { :cassette_name => 'list_members/single' } do
517
+ it 'returns count equal to one' do
518
+ expect(subject['audience']['count'].to_i).to eq(1)
519
+ end
520
+
521
+ it 'returns an array of hashes' do
522
+ expect(subject['audience']['member']).to be_an(Array)
523
+ end
524
+ end
525
+
526
+ context 'when there are multiple members', :vcr => { :cassette_name => 'list_members/multiple' } do
527
+ it 'returns count greater than one' do
528
+ expect(subject['audience']['count'].to_i).to be > 1
529
+ end
530
+
531
+ it 'returns an array of hashes' do
532
+ expect(subject['audience']['member']).to be_an(Array)
533
+ end
534
+ end
535
+ end
536
+
537
+ context '#suppressed_since' do
538
+ subject { mad_mimi.suppressed_since(1409512823) }
539
+
540
+ context 'when there is no suppressed members', :vcr => { :cassette_name => 'suppressed_since/no_members' } do
541
+ it 'returns an empty response' do
542
+ expect(subject).to eq("\n")
543
+ end
544
+ end
545
+
546
+ context 'when there are suppressed members', :vcr => { :cassette_name => 'suppressed_since/members_exist' } do
547
+ it 'returns an email' do
548
+ expect(subject).to include("new_test1@example.com")
549
+ end
550
+ end
551
+ end
552
+
553
+ context '#suppress_email' do
554
+ subject { mad_mimi.suppress_email('test@example.com') }
555
+
556
+ context 'when user is already suppressed', :vcr => { :cassette_name => 'suppress_email/already_suppressed' } do
557
+ it 'user is suppressed' do
558
+ expect(mad_mimi.suppressed?('test@example.com')).to be_truthy
559
+ end
560
+
561
+ it 'returns empty response' do
562
+ expect(subject).to eq('')
563
+ end
564
+ end
565
+
566
+ context 'when user is not suppressed', :vcr => { :cassette_name => 'suppress_email/not_suppressed' } do
567
+ it 'user is not suppressed' do
568
+ expect(mad_mimi.suppressed?('test@example.com')).to be_falsy
569
+ end
570
+
571
+ it 'suppresses user' do
572
+ VCR.use_cassette('suppress_email/user_not_suppressed') do
573
+ expect(mad_mimi.suppressed?('test@example.com')).to be_falsy
574
+ end
575
+
576
+ subject
577
+
578
+ VCR.use_cassette('suppress_email/user_is_now_suppressed') do
579
+ expect(mad_mimi.suppressed?('test@example.com')).to be_truthy
580
+ end
581
+ end
582
+ end
583
+
584
+ context 'when user does not exist', :vcr => { :cassette_name => 'suppress_email/user_does_not_exist' } do
585
+ it 'returns an error' do
586
+ expect(subject).to include("Couldn't find AudienceMember")
587
+ end
588
+ end
589
+ end
590
+
591
+ context '#unsuppress_email' do
592
+ subject { mad_mimi.unsuppress_email('test@example.com') }
593
+
594
+ context 'when user is already suppressed', :vcr => { :cassette_name => 'unsuppress_email/already_suppressed' } do
595
+ it 'user is suppressed' do
596
+ expect(mad_mimi.suppressed?('test@example.com')).to be_truthy
597
+ end
598
+
599
+ it 'returns empty response' do
600
+ expect(subject).to eq('')
601
+ end
602
+ end
603
+
604
+ context 'when user is not suppressed', :vcr => { :cassette_name => 'unsuppress_email/not_suppressed' } do
605
+ it 'suppresses user' do
606
+ VCR.use_cassette('unsuppress_email/user_suppressed') do
607
+ expect(mad_mimi.suppressed?('test@example.com')).to be_truthy
608
+ end
609
+
610
+ subject
611
+
612
+ VCR.use_cassette('unsuppress_email/user_is_now_unsuppressed') do
613
+ expect(mad_mimi.suppressed?('test@example.com')).to be_falsy
614
+ end
615
+ end
616
+ end
617
+
618
+ context 'when user does not exist', :vcr => { :cassette_name => 'unsuppress_email/user_does_not_exist' } do
619
+ it 'returns an empty response' do
620
+ expect(subject).to eq('')
621
+ end
622
+ end
623
+ end
624
+
625
+ context '#suppressed?' do
626
+ subject { mad_mimi.suppressed?('test@example.com') }
627
+
628
+ context 'when user is suppressed', :vcr => { :cassette_name => 'suppressed/member_is_suppressed' } do
629
+ it 'returns true' do
630
+ expect(subject).to be_truthy
631
+ end
632
+ end
633
+
634
+ context 'when user is not suppressed', :vcr => { :cassette_name => 'suppressed/member_is_not_suppressed' } do
635
+ it 'returns false' do
636
+ expect(subject).to be_falsy
637
+ end
638
+ end
639
+
640
+ context 'when user does not exist', :vcr => { :cassette_name => 'suppressed/member_does_not_exist' } do
641
+ it 'returns false' do
642
+ expect(subject).to be_falsy
643
+ end
644
+ end
645
+ end
646
+
647
+ context '#audience_search' do
648
+ context 'when does not include suppressed users', :vcr => { :cassette_name => 'audience_search/does_not_include_suppressed_users' } do
649
+ subject { mad_mimi.audience_search('test', false) }
650
+
651
+ it 'returns array' do
652
+ expect(subject['audience']['member']).to be_an(Array)
653
+ end
654
+
655
+ it 'does not include suppressed member' do
656
+ expect(subject['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_falsy
657
+ end
658
+ end
659
+
660
+ context 'when includes suppressed users', :vcr => { :cassette_name => 'audience_search/includes_suppressed_users' } do
661
+ subject { mad_mimi.audience_search('test', true) }
662
+
663
+ it 'returns array' do
664
+ expect(subject['audience']['member']).to be_an(Array)
665
+ end
666
+
667
+ it 'includes suppressed member' do
668
+ expect(subject['audience']['member'].any?{ |m| m['email'] == 'test@example.com' }).to be_truthy
669
+ end
670
+ end
671
+ end
672
+
673
+ context '#add_users_to_list' do
674
+ subject {
675
+ mad_mimi.add_users_to_list('list 1', [
676
+ { :email => 'add_users_to_list1@example.com' },
677
+ { :email => 'add_users_to_list2@example.com' }
678
+ ])
679
+ }
680
+
681
+ context 'when user does not exist', :vcr => { :cassette_name => 'add_users_to_list/users_did_not_exist' } do
682
+ it 'returns an id of import' do
683
+ expect(subject).to be_present
684
+ expect(subject.to_i).to be > 0
685
+ end
686
+
687
+ it 'creates users' do
688
+ VCR.use_cassette('add_users_to_list/users_missing') do
689
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'add_users_to_list1@example.com' }).to be_falsy
690
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'add_users_to_list2@example.com' }).to be_falsy
691
+ end
692
+
693
+ subject
694
+
695
+ VCR.use_cassette('add_users_to_list/users_exist') do
696
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'add_users_to_list1@example.com' }).to be_truthy
697
+ expect(mad_mimi.members['audience']['member'].any?{ |m| m['email'] == 'add_users_to_list2@example.com' }).to be_truthy
698
+ end
699
+ end
700
+
701
+ it 'adds users to the list' do
702
+ VCR.use_cassette('add_users_to_list/missing_membership') do
703
+ expect(mad_mimi.memberships('add_users_to_list1@example.com')['lists']).to be_nil
704
+ expect(mad_mimi.memberships('add_users_to_list2@example.com')['lists']).to be_nil
705
+ end
706
+
707
+ subject
708
+
709
+ VCR.use_cassette('add_users_to_list/gained_membership') do
710
+ expect(mad_mimi.memberships('add_users_to_list1@example.com')['lists']['list'].any?{ |l| l['name'] == 'list 1' }).to be_truthy
711
+ expect(mad_mimi.memberships('add_users_to_list2@example.com')['lists']['list'].any?{ |l| l['name'] == 'list 1' }).to be_truthy
712
+ end
713
+ end
714
+ end
715
+
716
+ context 'when users exist', :vcr => { :cassette_name => 'add_users_to_list/users_existed' } do
717
+ subject {
718
+ mad_mimi.add_users_to_list('list 1', [
719
+ { :email => 'add_users_to_list1@example.com', :first_name => 'First' },
720
+ { :email => 'add_users_to_list2@example.com', :first_name => 'Second' }
721
+ ])
722
+ }
723
+
724
+ it 'returns an id of import' do
725
+ expect(subject).to be_present
726
+ expect(subject.to_i).to be > 0
727
+ end
728
+
729
+ it 'updates user' do
730
+ VCR.use_cassette('add_users_to_list/users_exist') do
731
+ member1 = mad_mimi.members['audience']['member'].select{ |m|
732
+ m['email'] == 'add_users_to_list1@example.com'
733
+ }.first
734
+
735
+ expect(member1).to be_present
736
+ expect(member1['first_name']).to be_nil
737
+
738
+ member2 = mad_mimi.members['audience']['member'].select{ |m|
739
+ m['email'] == 'add_users_to_list2@example.com'
740
+ }.first
741
+
742
+ expect(member2).to be_present
743
+ expect(member2['first_name']).to be_nil
744
+ end
745
+
746
+ subject
747
+
748
+ VCR.use_cassette('add_users_to_list/users_updated') do
749
+ member1 = mad_mimi.members['audience']['member'].select{ |m|
750
+ m['email'] == 'add_users_to_list1@example.com'
751
+ }.first
752
+
753
+ expect(member1).to be_present
754
+ expect(member1['first_name']).to eq('First')
755
+
756
+ member2 = mad_mimi.members['audience']['member'].select{ |m|
757
+ m['email'] == 'add_users_to_list2@example.com'
758
+ }.first
759
+
760
+ expect(member2).to be_present
761
+ expect(member2['first_name']).to eq('Second')
762
+ end
763
+ end
764
+
765
+ it 'adds users to the list' do
766
+ VCR.use_cassette('add_users_to_list/missing_membership') do
767
+ expect(mad_mimi.memberships('add_users_to_list1@example.com')['lists']).to be_nil
768
+ expect(mad_mimi.memberships('add_users_to_list2@example.com')['lists']).to be_nil
769
+ end
770
+
771
+ subject
772
+
773
+ VCR.use_cassette('add_users_to_list/gained_membership') do
774
+ expect(mad_mimi.memberships('add_users_to_list1@example.com')['lists']['list'].any?{ |l| l['name'] == 'list 1' }).to be_truthy
775
+ expect(mad_mimi.memberships('add_users_to_list2@example.com')['lists']['list'].any?{ |l| l['name'] == 'list 1' }).to be_truthy
776
+ end
777
+ end
778
+ end
779
+ end
780
+
781
+ context '#promotions' do
782
+ subject { mad_mimi.promotions }
783
+
784
+ context 'when there is a single promotion', :vcr => { :cassette_name => 'promotions/single' } do
785
+ it 'returns an array' do
786
+ expect(subject['promotions']['promotion']).to be_an(Array)
787
+ end
788
+ end
789
+
790
+ context 'when there are multiple promotions', :vcr => { :cassette_name => 'promotions/multiple' } do
791
+ it 'returns an array' do
792
+ expect(subject['promotions']['promotion']).to be_an(Array)
793
+ end
794
+ end
795
+ end
796
+
797
+ context '#save_promotion' do
798
+ let(:raw_html) { '<html><body>Test [[tracking_beacon]][[opt_out]]</body></html>' }
799
+ let(:plain_text) { 'Test [[opt_out]]' }
800
+
801
+ subject {
802
+ mad_mimi.save_promotion(
803
+ 'Test promotion',
804
+ raw_html,
805
+ plain_text
806
+ )
807
+ }
808
+
809
+ context 'when only raw_html specified', :vcr => { :cassette_name => 'save_promotion/only_raw_html' } do
810
+ let(:plain_text) { nil }
811
+
812
+ context 'when tracking beacon and opt out are present' do
813
+ it 'saves promotions' do
814
+ VCR.use_cassette('save_promotion/promotion_missing') do
815
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_falsy
816
+ end
817
+
818
+ subject
819
+
820
+ VCR.use_cassette('save_promotion/promotion_exists') do
821
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_truthy
822
+ end
823
+ end
824
+
825
+ it 'returns success response' do
826
+ expect(subject).to include('Saved Test promotion')
827
+ end
828
+ end
829
+
830
+ context 'when tracking beacon is missing' do
831
+ let(:raw_html) { '<html><body>Test [[opt_out]]</body></html>' }
832
+
833
+ it 'raises a MadMimiError' do
834
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
835
+ end
836
+ end
837
+
838
+ context 'when opt out is missing' do
839
+ let(:raw_html) { '<html><body>Test [[tracking_beacon]]</body></html>' }
840
+
841
+ it 'raises a MadMimiError' do
842
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
843
+ end
844
+ end
845
+ end
846
+
847
+ context 'when only plain_text specified', :vcr => { :cassette_name => 'save_promotion/only_plain_text' } do
848
+ let(:raw_html) { nil }
849
+
850
+ context 'when opt out is present' do
851
+ it 'saves promotions' do
852
+ VCR.use_cassette('save_promotion/promotion_missing') do
853
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_falsy
854
+ end
855
+
856
+ subject
857
+
858
+ VCR.use_cassette('save_promotion/promotion_exists') do
859
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_truthy
860
+ end
861
+ end
862
+
863
+ it 'returns success response' do
864
+ expect(subject).to include('Saved Test promotion')
865
+ end
866
+ end
867
+
868
+ context 'when opt out is missing' do
869
+ let(:plain_text) { 'Test' }
870
+
871
+ it 'raises a MadMimiError' do
872
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
873
+ end
874
+ end
875
+ end
876
+
877
+ context 'when both raw_html and plain_text are specified', :vcr => { :cassette_name => 'save_promotion/raw_html_and_plain_text' } do
878
+ it 'saves promotions' do
879
+ VCR.use_cassette('save_promotion/promotion_missing') do
880
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_falsy
881
+ end
882
+
883
+ subject
884
+
885
+ VCR.use_cassette('save_promotion/promotion_exists') do
886
+ expect(mad_mimi.promotions['promotions']['promotion'].any?{ |p| p['name'] == 'Test promotion' }).to be_truthy
887
+ end
888
+ end
889
+
890
+ it 'returns success response' do
891
+ expect(subject).to include('Saved Test promotion')
892
+ end
893
+ end
894
+ end
895
+
896
+ context '#mailing_stats' do
897
+ context 'when promotion and mailing exists', :vcr => { :cassette_name => 'mailing_stats/promotion_and_mailing_exist' } do
898
+ subject { mad_mimi.mailing_stats(5510034, 122026332) }
899
+
900
+ it 'returns correct stats' do
901
+ expect(subject['mailing']['untraced']).to eq('1')
902
+ end
903
+ end
904
+
905
+ context 'when promotion does not exist', :vcr => { :cassette_name => 'mailing_stats/promotion_does_not_exist' } do
906
+ subject { mad_mimi.mailing_stats(0, 122026332) }
907
+
908
+ it 'returns an empty hash' do
909
+ expect(subject).to eq({})
910
+ end
911
+ end
912
+
913
+ context 'when promotion does not exist', :vcr => { :cassette_name => 'mailing_stats/mailing_does_not_exist' } do
914
+ subject { mad_mimi.mailing_stats(5510034, 0) }
915
+
916
+ it 'returns an empty hash' do
917
+ expect(subject).to eq({})
918
+ end
919
+ end
920
+ end
921
+
922
+ context '#send_mail' do
923
+ context 'when options are correct' do
924
+ let(:default_options) {
925
+ {
926
+ :promotion_name => 'Transactional Promotion',
927
+ :from => 'maxim+1@madmimi.com',
928
+ :subject => 'Test'
929
+ }
930
+ }
931
+
932
+ context 'when sending to list', :vcr => { :cassette_name => 'send_mail/send_to_list' } do
933
+ subject {
934
+ mad_mimi.send_mail(default_options.merge(:list_name => 'list 1'), {})
935
+ }
936
+
937
+ it "returns mailing id" do
938
+ expect(subject).to match(/\d{9}/)
939
+ end
940
+ end
941
+
942
+ context 'when sending to all', :vcr => { :cassette_name => 'send_mail/send_to_all' } do
943
+ subject {
944
+ mad_mimi.send_mail(default_options.merge(:to_all => true), {})
945
+ }
946
+
947
+ it "returns mailing id" do
948
+ expect(subject).to match(/\d{9}/)
949
+ end
950
+ end
951
+
952
+ context 'when sending to single recipient', :vcr => { :cassette_name => 'send_mail/send_single' } do
953
+ subject {
954
+ mad_mimi.send_mail(default_options.merge(:recipient => 'Test Example <test@example.com>'), {})
955
+ }
956
+
957
+ it "returns transaction id" do
958
+ expect(subject).to match(/\d{20}/)
959
+ end
960
+ end
961
+ end
962
+
963
+ context 'when promotion does not exist', :vcr => { :cassette_name => 'send_mail/promotion_does_not_exist' } do
964
+ subject {
965
+ mad_mimi.send_mail({
966
+ :promotion_name => 'Unknown Promotion',
967
+ :from => 'maxim+1@madmimi.com',
968
+ :subject => 'Test',
969
+ :to_all => true
970
+ }, {})
971
+ }
972
+
973
+ it "returns an error" do
974
+ expect(subject).to eq('You do not have a promotion named Unknown Promotion.')
975
+ end
976
+ end
977
+ end
978
+
979
+ context '#send_html' do
980
+ let(:raw_html) { '<html><body>Test [[tracking_beacon]] [[opt_out]]</body></html>' }
981
+
982
+ context 'when options are correct' do
983
+ let(:default_options) {
984
+ {
985
+ :promotion_name => 'Transactional Promotion',
986
+ :from => 'maxim+1@madmimi.com',
987
+ :subject => 'Test'
988
+ }
989
+ }
990
+
991
+ context 'when sending to list', :vcr => { :cassette_name => 'send_html/send_to_list' } do
992
+ subject {
993
+ mad_mimi.send_html(default_options.merge(:list_name => 'list 1'), raw_html)
994
+ }
995
+
996
+ it "returns mailing id" do
997
+ expect(subject).to match(/\d{9}/)
998
+ end
999
+ end
1000
+
1001
+ context 'when sending to all', :vcr => { :cassette_name => 'send_html/send_to_all' } do
1002
+ subject {
1003
+ mad_mimi.send_html(default_options.merge(:to_all => true), raw_html)
1004
+ }
1005
+
1006
+ it "returns mailing id" do
1007
+ expect(subject).to match(/\d{9}/)
1008
+ end
1009
+ end
1010
+
1011
+ context 'when sending to single recipient', :vcr => { :cassette_name => 'send_html/send_single' } do
1012
+ subject {
1013
+ mad_mimi.send_html(default_options.merge(:recipient => 'Test Example <test@example.com>'), raw_html)
1014
+ }
1015
+
1016
+ it "returns transaction id" do
1017
+ expect(subject).to match(/\d{20}/)
1018
+ end
1019
+ end
1020
+ end
1021
+
1022
+ context 'when promotion does not exist', :vcr => { :cassette_name => 'send_html/promotion_does_not_exist' } do
1023
+ subject {
1024
+ mad_mimi.send_html({
1025
+ :promotion_name => 'Unknown Promotion',
1026
+ :from => 'maxim+1@madmimi.com',
1027
+ :subject => 'Test',
1028
+ :to_all => true
1029
+ }, raw_html)
1030
+ }
1031
+
1032
+ it "returns mailing id" do
1033
+ expect(subject).to match(/\d{9}/)
1034
+ end
1035
+ end
1036
+
1037
+ context 'when tracking beacon is missing', :vcr => { :cassette_name => 'send_html/tracking_beacon_missing' } do
1038
+ let(:raw_html) { '<html><body>Test [[opt_out]]</body></html>' }
1039
+
1040
+ subject {
1041
+ mad_mimi.send_html({
1042
+ :promotion_name => 'Unknown Promotion',
1043
+ :from => 'maxim+1@madmimi.com',
1044
+ :subject => 'Test',
1045
+ :to_all => true
1046
+ }, raw_html)
1047
+ }
1048
+
1049
+ it "raises MadMimiError" do
1050
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
1051
+ end
1052
+ end
1053
+
1054
+ context 'when opt_out is missing', :vcr => { :cassette_name => 'send_html/opt_out_missing' } do
1055
+ let(:raw_html) { '<html><body>Test [[tracking_beacon]]</body></html>' }
1056
+
1057
+ subject {
1058
+ mad_mimi.send_html({
1059
+ :promotion_name => 'Unknown Promotion',
1060
+ :from => 'maxim+1@madmimi.com',
1061
+ :subject => 'Test',
1062
+ :to_all => true
1063
+ }, raw_html)
1064
+ }
1065
+
1066
+ it "raises MadMimiError" do
1067
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
1068
+ end
1069
+ end
1070
+ end
1071
+
1072
+ context '#send_plaintext' do
1073
+ let(:plain_text) { 'Test [[tracking_beacon]] [[opt_out]]' }
1074
+
1075
+ context 'when options are correct' do
1076
+ let(:default_options) {
1077
+ {
1078
+ :promotion_name => 'Transactional Promotion',
1079
+ :from => 'maxim+1@madmimi.com',
1080
+ :subject => 'Test'
1081
+ }
1082
+ }
1083
+
1084
+ context 'when sending to list', :vcr => { :cassette_name => 'send_plaintext/send_to_list' } do
1085
+ subject {
1086
+ mad_mimi.send_plaintext(default_options.merge(:list_name => 'list 1'), plain_text)
1087
+ }
1088
+
1089
+ it "returns mailing id" do
1090
+ expect(subject).to match(/\d{9}/)
1091
+ end
1092
+ end
1093
+
1094
+ context 'when sending to all', :vcr => { :cassette_name => 'send_plaintext/send_to_all' } do
1095
+ subject {
1096
+ mad_mimi.send_plaintext(default_options.merge(:to_all => true), plain_text)
1097
+ }
1098
+
1099
+ it "returns mailing id" do
1100
+ expect(subject).to match(/\d{9}/)
1101
+ end
1102
+ end
1103
+
1104
+ context 'when sending to single recipient', :vcr => { :cassette_name => 'send_plaintext/send_single' } do
1105
+ subject {
1106
+ mad_mimi.send_plaintext(default_options.merge(:recipient => 'Test Example <test@example.com>'), plain_text)
1107
+ }
1108
+
1109
+ it "returns transaction id" do
1110
+ expect(subject).to match(/\d{20}/)
1111
+ end
1112
+ end
1113
+ end
1114
+
1115
+ context 'when promotion does not exist', :vcr => { :cassette_name => 'send_plaintext/promotion_does_not_exist' } do
1116
+ subject {
1117
+ mad_mimi.send_plaintext({
1118
+ :promotion_name => 'Unknown Promotion',
1119
+ :from => 'maxim+1@madmimi.com',
1120
+ :subject => 'Test',
1121
+ :to_all => true
1122
+ }, plain_text)
1123
+ }
1124
+
1125
+ it "returns mailing id" do
1126
+ expect(subject).to match(/\d{9}/)
1127
+ end
1128
+ end
1129
+
1130
+ context 'when opt_out is missing', :vcr => { :cassette_name => 'send_plaintext/opt_out_missing' } do
1131
+ let(:plain_text) { 'Test [[tracking_beacon]]' }
1132
+
1133
+ subject {
1134
+ mad_mimi.send_html({
1135
+ :promotion_name => 'Unknown Promotion',
1136
+ :from => 'maxim+1@madmimi.com',
1137
+ :subject => 'Test',
1138
+ :to_all => true
1139
+ }, plain_text)
1140
+ }
1141
+
1142
+ it "raises MadMimiError" do
1143
+ expect{ subject }.to raise_error(MadMimi::MadMimiError)
1144
+ end
1145
+ end
1146
+ end
1147
+
1148
+ context '#status' do
1149
+ context 'when transactional email exists', :vcr => { :cassette_name => 'status/transactional_mail_exists' } do
1150
+ subject { mad_mimi.status(10199217171363888473) }
1151
+
1152
+ it 'returns a correct status' do
1153
+ expect(subject).to eq('received')
1154
+ end
1155
+ end
1156
+
1157
+ context 'when transactional email does not exist', :vcr => { :cassette_name => 'status/transactional_mail_does_not_exist' } do
1158
+ subject { mad_mimi.status(0) }
1159
+
1160
+ it 'returns an error' do
1161
+ expect(subject).to eq('Not Found')
1162
+ end
1163
+ end
1164
+ end
1165
+
1166
+ end