parity-sendgrid-api 0.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (99) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +6 -0
  3. data/.rspec +3 -0
  4. data/.travis.yml +3 -0
  5. data/.yardopts +6 -0
  6. data/Gemfile +17 -0
  7. data/Gemfile.lock +67 -0
  8. data/LICENSE +22 -0
  9. data/README.md +261 -0
  10. data/Rakefile +12 -0
  11. data/lib/sendgrid/api.rb +7 -0
  12. data/lib/sendgrid/api/client.rb +43 -0
  13. data/lib/sendgrid/api/entities/category.rb +13 -0
  14. data/lib/sendgrid/api/entities/email.rb +13 -0
  15. data/lib/sendgrid/api/entities/entity.rb +83 -0
  16. data/lib/sendgrid/api/entities/list.rb +30 -0
  17. data/lib/sendgrid/api/entities/marketing_email.rb +20 -0
  18. data/lib/sendgrid/api/entities/profile.rb +14 -0
  19. data/lib/sendgrid/api/entities/response.rb +21 -0
  20. data/lib/sendgrid/api/entities/response_insert.rb +23 -0
  21. data/lib/sendgrid/api/entities/response_remove.rb +23 -0
  22. data/lib/sendgrid/api/entities/schedule.rb +13 -0
  23. data/lib/sendgrid/api/entities/sender_address.rb +13 -0
  24. data/lib/sendgrid/api/entities/stats.rb +14 -0
  25. data/lib/sendgrid/api/newsletter/categories.rb +74 -0
  26. data/lib/sendgrid/api/newsletter/emails.rb +69 -0
  27. data/lib/sendgrid/api/newsletter/lists.rb +64 -0
  28. data/lib/sendgrid/api/newsletter/marketing_emails.rb +72 -0
  29. data/lib/sendgrid/api/newsletter/recipients.rb +55 -0
  30. data/lib/sendgrid/api/newsletter/schedule.rb +70 -0
  31. data/lib/sendgrid/api/newsletter/sender_addresses.rb +80 -0
  32. data/lib/sendgrid/api/newsletter/utils.rb +34 -0
  33. data/lib/sendgrid/api/rest/errors/error.rb +66 -0
  34. data/lib/sendgrid/api/rest/resource.rb +58 -0
  35. data/lib/sendgrid/api/rest/response/parse_error.rb +19 -0
  36. data/lib/sendgrid/api/rest/response/parse_json.rb +24 -0
  37. data/lib/sendgrid/api/service.rb +23 -0
  38. data/lib/sendgrid/api/version.rb +5 -0
  39. data/lib/sendgrid/api/web/mail.rb +44 -0
  40. data/lib/sendgrid/api/web/profile.rb +38 -0
  41. data/lib/sendgrid/api/web/stats.rb +36 -0
  42. data/sendgrid-api.gemspec +23 -0
  43. data/spec/fixtures/categories.json +11 -0
  44. data/spec/fixtures/emails/email.json +6 -0
  45. data/spec/fixtures/emails/emails.json +10 -0
  46. data/spec/fixtures/errors/already_exists.json +3 -0
  47. data/spec/fixtures/errors/bad_request.json +6 -0
  48. data/spec/fixtures/errors/database_error.json +3 -0
  49. data/spec/fixtures/errors/does_not_exist.json +3 -0
  50. data/spec/fixtures/errors/forbidden.json +3 -0
  51. data/spec/fixtures/errors/invalid_fields.json +3 -0
  52. data/spec/fixtures/errors/not_scheduled.json +3 -0
  53. data/spec/fixtures/errors/unauthorized.json +6 -0
  54. data/spec/fixtures/lists/list.json +5 -0
  55. data/spec/fixtures/lists/lists.json +11 -0
  56. data/spec/fixtures/marketing_emails/marketing_email.json +19 -0
  57. data/spec/fixtures/marketing_emails/marketing_emails.json +10 -0
  58. data/spec/fixtures/profile.json +18 -0
  59. data/spec/fixtures/recipients.json +8 -0
  60. data/spec/fixtures/schedule.json +3 -0
  61. data/spec/fixtures/sender_addresses/sender_address.json +11 -0
  62. data/spec/fixtures/sender_addresses/sender_addresses.json +11 -0
  63. data/spec/fixtures/stats.json +50 -0
  64. data/spec/fixtures/success.json +3 -0
  65. data/spec/sendgrid/api/client_spec.rb +38 -0
  66. data/spec/sendgrid/api/entities/category_spec.rb +14 -0
  67. data/spec/sendgrid/api/entities/email_spec.rb +15 -0
  68. data/spec/sendgrid/api/entities/entity_spec.rb +279 -0
  69. data/spec/sendgrid/api/entities/list_spec.rb +34 -0
  70. data/spec/sendgrid/api/entities/marketing_email_spec.rb +31 -0
  71. data/spec/sendgrid/api/entities/profile_spec.rb +26 -0
  72. data/spec/sendgrid/api/entities/response_insert_spec.rb +28 -0
  73. data/spec/sendgrid/api/entities/response_remove_spec.rb +28 -0
  74. data/spec/sendgrid/api/entities/response_spec.rb +28 -0
  75. data/spec/sendgrid/api/entities/schedule_spec.rb +14 -0
  76. data/spec/sendgrid/api/entities/sender_address_spec.rb +21 -0
  77. data/spec/sendgrid/api/entities/stats_spec.rb +25 -0
  78. data/spec/sendgrid/api/newsletter/categories_spec.rb +247 -0
  79. data/spec/sendgrid/api/newsletter/emails_spec.rb +265 -0
  80. data/spec/sendgrid/api/newsletter/lists_spec.rb +307 -0
  81. data/spec/sendgrid/api/newsletter/marketing_emails_spec.rb +306 -0
  82. data/spec/sendgrid/api/newsletter/recipients_spec.rb +252 -0
  83. data/spec/sendgrid/api/newsletter/schedule_spec.rb +263 -0
  84. data/spec/sendgrid/api/newsletter/sender_addresses_spec.rb +300 -0
  85. data/spec/sendgrid/api/rest/errors/error_spec.rb +121 -0
  86. data/spec/sendgrid/api/rest/resource_spec.rb +145 -0
  87. data/spec/sendgrid/api/rest/response/parse_error_spec.rb +39 -0
  88. data/spec/sendgrid/api/rest/response/parse_json_spec.rb +45 -0
  89. data/spec/sendgrid/api/service_spec.rb +44 -0
  90. data/spec/sendgrid/api/version_spec.rb +11 -0
  91. data/spec/sendgrid/api/web/mail_spec.rb +111 -0
  92. data/spec/sendgrid/api/web/profile_spec.rb +110 -0
  93. data/spec/sendgrid/api/web/stats_spec.rb +94 -0
  94. data/spec/spec_helper.rb +23 -0
  95. data/spec/support/helpers.rb +23 -0
  96. data/spec/support/mock.rb +30 -0
  97. data/spec/support/online.rb +114 -0
  98. data/spec/support/shared_examples.rb +104 -0
  99. metadata +225 -0
@@ -0,0 +1,306 @@
1
+ require 'spec_helper'
2
+
3
+ module Sendgrid
4
+ module API
5
+ module Newsletter
6
+ module MarketingEmails
7
+ describe Services do
8
+
9
+ subject { service }
10
+ let(:service) { described_class.new(resource) }
11
+ let(:resource) { REST::Resource.new(user, key) }
12
+ let(:user) { 'my_user' }
13
+ let(:key) { 'my_key' }
14
+ let(:sg_mock) { Sendgrid::Mock.new(user, key) }
15
+
16
+ let(:marketing_email) do
17
+ Entities::MarketingEmail.new(:identity => identity, :name => name, :subject => email_subject, :text => text, :html => html)
18
+ end
19
+ let(:identity) { 'my identity' }
20
+ let(:name) { 'my name' }
21
+ let(:email_subject) { 'my subject' }
22
+ let(:text) { 'my text' }
23
+ let(:html) { 'my html' }
24
+
25
+ describe '#add' do
26
+ let(:url) { 'newsletter/add.json' }
27
+ let(:stub_post) { sg_mock.stub_post(url, marketing_email.as_json) }
28
+ subject { service.add(marketing_email) }
29
+
30
+ context 'when add a marketing email successfully' do
31
+ it_behaves_like 'a success response'
32
+ end
33
+
34
+ context 'when the marketing email is not valid' do
35
+ it_behaves_like 'an invalid fields response'
36
+ end
37
+
38
+ context 'when a marketing email already exists' do
39
+ it_behaves_like 'an already exists unauthorized response'
40
+ end
41
+
42
+ context 'when permission failed' do
43
+ it_behaves_like 'a forbidden response'
44
+ end
45
+ end
46
+
47
+ describe '#edit' do
48
+ let(:url) { 'newsletter/edit.json' }
49
+ let(:stub_post) { sg_mock.stub_post(url, marketing_email.as_json) }
50
+ subject { service.edit(marketing_email) }
51
+
52
+ context 'when edit a marketing email successfully' do
53
+ it_behaves_like 'a success response'
54
+ end
55
+
56
+ context 'when edit a marketing email name successfully' do
57
+ it_behaves_like 'a success response'
58
+ end
59
+
60
+ context 'when a new marketing email name already exists' do
61
+ let(:newname) { 'my new name' }
62
+ let(:stub_post) { sg_mock.stub_post(url, marketing_email.as_json.merge(:newname => newname)) }
63
+ subject { service.edit(marketing_email, newname) }
64
+ it_behaves_like 'a success response'
65
+ end
66
+
67
+ context 'when the marketing email is not found' do
68
+ it_behaves_like 'a does not exist response'
69
+ end
70
+
71
+ context 'when permission failed' do
72
+ it_behaves_like 'a forbidden response'
73
+ end
74
+ end
75
+
76
+ describe '#get' do
77
+ let(:url) { 'newsletter/get.json' }
78
+ let(:stub_post) { sg_mock.stub_post(url, :name => name) }
79
+ subject { service.get(marketing_email) }
80
+
81
+ context 'when get a marketing email successfully' do
82
+ before do
83
+ stub_post.to_return(:body => fixture('marketing_emails/marketing_email.json'))
84
+ end
85
+
86
+ context 'with name' do
87
+ subject { service.get(name) }
88
+ its(:name) { should == 'sendgrid tutorial' }
89
+ its(:subject) { should == 'SendGrid Email Marketing Service Tutorial' }
90
+ end
91
+
92
+ context 'with object' do
93
+ its(:name) { should == 'sendgrid tutorial' }
94
+ its(:subject) { should == 'SendGrid Email Marketing Service Tutorial' }
95
+ end
96
+ end
97
+
98
+ context 'when the marketing email is not found' do
99
+ it_behaves_like 'a does not exist response'
100
+ end
101
+
102
+ context 'when permission failed' do
103
+ it_behaves_like 'a forbidden response'
104
+ end
105
+ end
106
+
107
+ describe '#list' do
108
+ let(:url) { 'newsletter/list.json' }
109
+ let(:stub_post) { sg_mock.stub_post(url) }
110
+ subject { service.list }
111
+
112
+ context 'when get all marketing emails successfully' do
113
+ before do
114
+ stub_post.to_return(:body => fixture('marketing_emails/marketing_emails.json'))
115
+ end
116
+ it { should have(2).items }
117
+
118
+ describe 'first item' do
119
+ subject { service.list.first }
120
+ its(:name) { should == 'Sendgrid Tutorial' }
121
+ its(:newsletter_id) { should == 123456 }
122
+ end
123
+ end
124
+
125
+ context 'when permission failed' do
126
+ it_behaves_like 'a forbidden response'
127
+ end
128
+ end
129
+
130
+ describe '#delete' do
131
+ let(:url) { 'newsletter/delete.json' }
132
+ let(:stub_post) { sg_mock.stub_post(url, :name => name) }
133
+ subject { service.delete(marketing_email) }
134
+
135
+ context 'when delete a marketing email successfully' do
136
+ context 'with name' do
137
+ subject { service.delete(name) }
138
+ it_behaves_like 'a success response'
139
+ end
140
+
141
+ context 'with object' do
142
+ it_behaves_like 'a success response'
143
+ end
144
+ end
145
+
146
+ context 'when the marketing email is not found' do
147
+ it_behaves_like 'a does not exist response'
148
+ end
149
+
150
+ context 'when permission failed' do
151
+ it_behaves_like 'a forbidden response'
152
+ end
153
+ end
154
+
155
+ describe 'online tests', :online => true do
156
+ include_examples 'online tests'
157
+ let(:online) { Online.new(env_user, env_key) }
158
+ let(:marketing_email) { online.marketing_email_example }
159
+ let(:sender_address) { online.sender_address_example }
160
+ let(:client) { online.client }
161
+
162
+ context 'when credentials are valid' do
163
+ let(:resource) { REST::Resource.new(env_user, env_key) }
164
+
165
+ before do
166
+ client.sender_addresses.add(sender_address)
167
+ end
168
+ after do
169
+ client.sender_addresses.delete(sender_address)
170
+ end
171
+
172
+ describe '#add' do
173
+ context 'when add a marketing email successfully' do
174
+ after do
175
+ subject.delete(marketing_email)
176
+ end
177
+ it 'adds the marketing email' do
178
+ subject.add(marketing_email).success?.should be_true
179
+ end
180
+ end
181
+
182
+ context 'when the marketing email is not valid' do
183
+ it 'raises an error' do
184
+ marketing_email.subject = nil
185
+ expect { subject.add(marketing_email) }.to raise_error(REST::Errors::BadRequest)
186
+ end
187
+ end
188
+
189
+ context 'when a marketing email already exists' do
190
+ before do
191
+ subject.add(marketing_email)
192
+ end
193
+ after do
194
+ subject.delete(marketing_email)
195
+ end
196
+ it 'raises an error' do
197
+ expect { subject.add(marketing_email) }.to raise_error(REST::Errors::Unauthorized)
198
+ end
199
+ end
200
+ end
201
+
202
+ describe '#edit' do
203
+ context 'when edit a marketing email successfully' do
204
+ before do
205
+ subject.add(marketing_email)
206
+ end
207
+ after do
208
+ subject.delete(marketing_email)
209
+ end
210
+ it 'edits the marketing email' do
211
+ subject.edit(marketing_email).success?.should be_true
212
+ end
213
+ end
214
+
215
+ context 'when the marketing email is not found' do
216
+ it 'raises an error' do
217
+ expect { subject.edit(marketing_email) }.to raise_error(REST::Errors::Unauthorized)
218
+ end
219
+ end
220
+ end
221
+
222
+ describe '#get' do
223
+ context 'when get a marketing email successfully' do
224
+ before do
225
+ subject.add(marketing_email)
226
+ end
227
+ after do
228
+ subject.delete(marketing_email)
229
+ end
230
+ it 'gets the marketing email' do
231
+ response = subject.get(marketing_email)
232
+ response.name.should == marketing_email.name
233
+ end
234
+ end
235
+
236
+ context 'when the marketing email is not found' do
237
+ it 'raises an error' do
238
+ expect { subject.get(marketing_email) }.to raise_error(REST::Errors::Unauthorized)
239
+ end
240
+ end
241
+ end
242
+
243
+ describe '#list' do
244
+ context 'when get all marketing emails successfully' do
245
+ it 'get all the marketing emails' do
246
+ subject.list.should_not be_empty
247
+ end
248
+ end
249
+ end
250
+
251
+ describe '#delete' do
252
+ context 'when delete a marketing email successfully' do
253
+ before do
254
+ subject.add(marketing_email)
255
+ end
256
+ it 'deletes the marketing email' do
257
+ subject.delete(marketing_email).success?.should be_true
258
+ end
259
+ end
260
+
261
+ context 'when the marketing email is not found' do
262
+ it 'raises an error' do
263
+ expect { subject.delete(marketing_email) }.to raise_error(REST::Errors::Unauthorized)
264
+ end
265
+ end
266
+ end
267
+ end
268
+
269
+ context 'when credentials are invalid' do
270
+ describe '#add' do
271
+ it 'raises an error' do
272
+ expect { subject.add(marketing_email) }.to raise_error(REST::Errors::Forbidden)
273
+ end
274
+ end
275
+
276
+ describe '#edit' do
277
+ it 'raises an error' do
278
+ expect { subject.edit(marketing_email) }.to raise_error(REST::Errors::Forbidden)
279
+ end
280
+ end
281
+
282
+ describe '#get' do
283
+ it 'raises an error' do
284
+ expect { subject.get(marketing_email) }.to raise_error(REST::Errors::Forbidden)
285
+ end
286
+ end
287
+
288
+ describe '#list' do
289
+ it 'raises an error' do
290
+ expect { subject.list }.to raise_error(REST::Errors::Forbidden)
291
+ end
292
+ end
293
+
294
+ describe '#delete' do
295
+ it 'raises an error' do
296
+ expect { subject.delete(marketing_email) }.to raise_error(REST::Errors::Forbidden)
297
+ end
298
+ end
299
+ end
300
+ end
301
+
302
+ end
303
+ end
304
+ end
305
+ end
306
+ end
@@ -0,0 +1,252 @@
1
+ require 'spec_helper'
2
+
3
+ module Sendgrid
4
+ module API
5
+ module Newsletter
6
+ module Recipients
7
+ describe Services do
8
+
9
+ subject { service }
10
+ let(:service) { described_class.new(resource) }
11
+ let(:resource) { REST::Resource.new(user, key) }
12
+ let(:user) { 'my_user' }
13
+ let(:key) { 'my_key' }
14
+ let(:sg_mock) { Sendgrid::Mock.new(user, key) }
15
+
16
+ let(:marketing_email_name) { 'my marketing email' }
17
+ let(:listname) { 'my list' }
18
+ let(:marketing_email) { Entities::MarketingEmail.new(:name => marketing_email_name) }
19
+ let(:list) { Entities::List.new(:list => listname) }
20
+
21
+ describe '#add' do
22
+ let(:url) { 'newsletter/recipients/add.json' }
23
+ let(:stub_post) { sg_mock.stub_post(url, :name => marketing_email_name, :list => listname) }
24
+ subject { service.add(list, marketing_email) }
25
+
26
+ context 'when add a recipient list successfully' do
27
+ context 'with object' do
28
+ it_behaves_like 'a success response'
29
+ end
30
+
31
+ context 'with name' do
32
+ subject { service.add(listname, marketing_email_name) }
33
+ it_behaves_like 'a success response'
34
+ end
35
+ end
36
+
37
+ context 'when the list does not exist' do
38
+ it_behaves_like 'a database error response'
39
+ end
40
+
41
+ context 'when the marketing email does not exist' do
42
+ it_behaves_like 'a does not exist response'
43
+ end
44
+
45
+ context 'when permission failed' do
46
+ it_behaves_like 'a forbidden response'
47
+ end
48
+ end
49
+
50
+ describe '#get' do
51
+ let(:url) { 'newsletter/recipients/get.json' }
52
+ let(:stub_post) { sg_mock.stub_post(url, :name => marketing_email_name) }
53
+ subject { service.get(marketing_email) }
54
+
55
+ context 'when get the recipient lists successfully' do
56
+ before do
57
+ stub_post.to_return(:body => fixture('recipients.json'))
58
+ end
59
+
60
+ context 'with object' do
61
+ it { should have(2).items }
62
+
63
+ describe 'first item' do
64
+ subject { service.get(marketing_email).first }
65
+ its(:list) { should == 'list 1' }
66
+ end
67
+ end
68
+
69
+ context 'with name' do
70
+ subject { service.get(marketing_email_name) }
71
+
72
+ it { should have(2).items }
73
+ end
74
+ end
75
+
76
+ context 'when the marketing email does not exist' do
77
+ it_behaves_like 'a does not exist response'
78
+ end
79
+
80
+ context 'when permission failed' do
81
+ it_behaves_like 'a forbidden response'
82
+ end
83
+ end
84
+
85
+ describe '#delete' do
86
+ let(:url) { 'newsletter/recipients/delete.json' }
87
+ let(:stub_post) { sg_mock.stub_post(url, :name => marketing_email_name, :list => listname) }
88
+ subject { service.delete(list, marketing_email) }
89
+
90
+ context 'when delete a recipient list successfully' do
91
+ context 'with object' do
92
+ it_behaves_like 'a success response'
93
+ end
94
+
95
+ context 'with name' do
96
+ subject { service.delete(listname, marketing_email_name) }
97
+ it_behaves_like 'a success response'
98
+ end
99
+ end
100
+
101
+ context 'when the list does not exist' do
102
+ it_behaves_like 'a database error response'
103
+ end
104
+
105
+ context 'when the marketing email does not exist' do
106
+ it_behaves_like 'a does not exist response'
107
+ end
108
+
109
+ context 'when permission failed' do
110
+ it_behaves_like 'a forbidden response'
111
+ end
112
+ end
113
+
114
+ describe 'online tests', :online => true do
115
+ include_examples 'online tests'
116
+ let(:online) { Online.new(env_user, env_key) }
117
+ let(:marketing_email) { online.marketing_email_example }
118
+ let(:list) { online.list_example }
119
+ let(:client) { online.client }
120
+
121
+ context 'when credentials are valid' do
122
+ let(:resource) { REST::Resource.new(env_user, env_key) }
123
+
124
+ describe '#add' do
125
+ context 'when add a recipient list successfully' do
126
+ before do
127
+ online.add_marketing_email
128
+ online.add_list
129
+ end
130
+ after do
131
+ online.delete_marketing_email
132
+ online.delete_list
133
+ end
134
+
135
+ it 'adds the recipient list' do
136
+ online.add_recipient_list.should be_true
137
+ end
138
+ end
139
+
140
+ context 'when the list does not exist' do
141
+ before do
142
+ online.add_marketing_email
143
+ end
144
+ after do
145
+ online.delete_marketing_email
146
+ end
147
+ it 'raises an error' do
148
+ expect { subject.add(list, marketing_email) }.to raise_error(REST::Errors::Unknown)
149
+ end
150
+ end
151
+
152
+ context 'when the marketing email does not exist' do
153
+ before do
154
+ online.add_list
155
+ end
156
+ after do
157
+ online.delete_list
158
+ end
159
+ it 'raises an error' do
160
+ expect { subject.add(list, marketing_email) }.to raise_error(REST::Errors::Unauthorized)
161
+ end
162
+ end
163
+ end
164
+
165
+ describe '#get' do
166
+ context 'when get the recipient lists successfully' do
167
+ before do
168
+ online.add_marketing_email
169
+ end
170
+ after do
171
+ online.delete_marketing_email
172
+ end
173
+ it 'gets the recipient lists' do
174
+ expect { subject.get(marketing_email) }.to_not raise_error
175
+ end
176
+ end
177
+
178
+ context 'when the marketing email does not exist' do
179
+ it 'raises an error' do
180
+ expect { subject.get(marketing_email) }.to raise_error(REST::Errors::Unauthorized)
181
+ end
182
+ end
183
+ end
184
+
185
+ describe '#delete' do
186
+ context 'when delete a recipient list successfully' do
187
+ before do
188
+ online.add_marketing_email
189
+ online.add_list
190
+ online.add_recipient_list
191
+ end
192
+ after do
193
+ online.delete_marketing_email
194
+ online.delete_list
195
+ end
196
+
197
+ it 'deletes the recipient list' do
198
+ subject.delete(list, marketing_email).success?.should be_true
199
+ end
200
+ end
201
+
202
+ context 'when the list does not exist' do
203
+ before do
204
+ online.add_marketing_email
205
+ end
206
+ after do
207
+ online.delete_marketing_email
208
+ end
209
+ it 'raises an error' do
210
+ expect { subject.delete(list, marketing_email) }.to raise_error(REST::Errors::Unknown)
211
+ end
212
+ end
213
+
214
+ context 'when the marketing email does not exist' do
215
+ before do
216
+ online.add_list
217
+ end
218
+ after do
219
+ online.delete_list
220
+ end
221
+ it 'raises an error' do
222
+ expect { subject.delete(list, marketing_email) }.to raise_error(REST::Errors::Unauthorized)
223
+ end
224
+ end
225
+ end
226
+ end
227
+
228
+ context 'when credentials are invalid' do
229
+ describe '#add' do
230
+ it 'raises an error' do
231
+ expect { subject.add(list, marketing_email) }.to raise_error(REST::Errors::Forbidden)
232
+ end
233
+ end
234
+
235
+ describe '#get' do
236
+ it 'raises an error' do
237
+ expect { subject.get(marketing_email) }.to raise_error(REST::Errors::Forbidden)
238
+ end
239
+ end
240
+
241
+ describe '#delete' do
242
+ it 'raises an error' do
243
+ expect { subject.delete(list, marketing_email) }.to raise_error(REST::Errors::Forbidden)
244
+ end
245
+ end
246
+ end
247
+ end
248
+ end
249
+ end
250
+ end
251
+ end
252
+ end