1 # Patchwork - automated patch tracking system
2 # Copyright (C) 2010 Jeremy Kerr <jk@ozlabs.org>
4 # This file is part of the Patchwork package.
6 # Patchwork is free software; you can redistribute it and/or modify
7 # it under the terms of the GNU General Public License as published by
8 # the Free Software Foundation; either version 2 of the License, or
9 # (at your option) any later version.
11 # Patchwork is distributed in the hope that it will be useful,
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 # GNU General Public License for more details.
16 # You should have received a copy of the GNU General Public License
17 # along with Patchwork; if not, write to the Free Software
18 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 from django.test import TestCase
22 from django.core import mail
23 from django.core.urlresolvers import reverse
24 from patchwork.models import EmailOptout, EmailConfirmation, Person
25 from patchwork.tests.utils import create_user, error_strings
27 class MailSettingsTest(TestCase):
28 view = 'patchwork.views.mail.settings'
31 def testMailSettingsGET(self):
32 response = self.client.get(self.url)
33 self.assertEquals(response.status_code, 200)
34 self.assertTrue(response.context['form'])
36 def testMailSettingsPOST(self):
37 email = u'foo@example.com'
38 response = self.client.post(self.url, {'email': email})
39 self.assertEquals(response.status_code, 200)
40 self.assertTemplateUsed(response, 'patchwork/mail-settings.html')
41 self.assertEquals(response.context['email'], email)
43 def testMailSettingsPOSTEmpty(self):
44 response = self.client.post(self.url, {'email': ''})
45 self.assertEquals(response.status_code, 200)
46 self.assertTemplateUsed(response, 'patchwork/mail-form.html')
47 self.assertFormError(response, 'form', 'email',
48 'This field is required.')
50 def testMailSettingsPOSTInvalid(self):
51 response = self.client.post(self.url, {'email': 'foo'})
52 self.assertEquals(response.status_code, 200)
53 self.assertTemplateUsed(response, 'patchwork/mail-form.html')
54 self.assertFormError(response, 'form', 'email', error_strings['email'])
56 def testMailSettingsPOSTOptedIn(self):
57 email = u'foo@example.com'
58 response = self.client.post(self.url, {'email': email})
59 self.assertEquals(response.status_code, 200)
60 self.assertTemplateUsed(response, 'patchwork/mail-settings.html')
61 self.assertEquals(response.context['is_optout'], False)
62 self.assertTrue('<strong>may</strong>' in response.content)
63 optout_url = reverse('patchwork.views.mail.optout')
64 self.assertTrue(('action="%s"' % optout_url) in response.content)
66 def testMailSettingsPOSTOptedOut(self):
67 email = u'foo@example.com'
68 EmailOptout(email = email).save()
69 response = self.client.post(self.url, {'email': email})
70 self.assertEquals(response.status_code, 200)
71 self.assertTemplateUsed(response, 'patchwork/mail-settings.html')
72 self.assertEquals(response.context['is_optout'], True)
73 self.assertTrue('<strong>may not</strong>' in response.content)
74 optin_url = reverse('patchwork.views.mail.optin')
75 self.assertTrue(('action="%s"' % optin_url) in response.content)
77 class OptoutRequestTest(TestCase):
78 view = 'patchwork.views.mail.optout'
81 def testOptOutRequestGET(self):
82 response = self.client.get(self.url)
83 self.assertRedirects(response, reverse('patchwork.views.mail.settings'))
85 def testOptoutRequestValidPOST(self):
86 email = u'foo@example.com'
87 response = self.client.post(self.url, {'email': email})
89 # check for a confirmation object
90 self.assertEquals(EmailConfirmation.objects.count(), 1)
91 conf = EmailConfirmation.objects.get(email = email)
93 # check confirmation page
94 self.assertEquals(response.status_code, 200)
95 self.assertEquals(response.context['confirmation'], conf)
96 self.assertTrue(email in response.content)
99 url = reverse('patchwork.views.confirm', kwargs = {'key': conf.key})
100 self.assertEquals(len(mail.outbox), 1)
102 self.assertEquals(msg.to, [email])
103 self.assertEquals(msg.subject, 'Patchwork opt-out confirmation')
104 self.assertTrue(url in msg.body)
106 def testOptoutRequestInvalidPOSTEmpty(self):
107 response = self.client.post(self.url, {'email': ''})
108 self.assertEquals(response.status_code, 200)
109 self.assertFormError(response, 'form', 'email',
110 'This field is required.')
111 self.assertTrue(response.context['error'])
112 self.assertTrue('email_sent' not in response.context)
113 self.assertEquals(len(mail.outbox), 0)
115 def testOptoutRequestInvalidPOSTNonEmail(self):
116 response = self.client.post(self.url, {'email': 'foo'})
117 self.assertEquals(response.status_code, 200)
118 self.assertFormError(response, 'form', 'email', error_strings['email'])
119 self.assertTrue(response.context['error'])
120 self.assertTrue('email_sent' not in response.context)
121 self.assertEquals(len(mail.outbox), 0)
123 class OptoutTest(TestCase):
124 view = 'patchwork.views.mail.optout'
128 self.email = u'foo@example.com'
129 self.conf = EmailConfirmation(type = 'optout', email = self.email)
132 def testOptoutValidHash(self):
133 url = reverse('patchwork.views.confirm',
134 kwargs = {'key': self.conf.key})
135 response = self.client.get(url)
137 self.assertEquals(response.status_code, 200)
138 self.assertTemplateUsed(response, 'patchwork/optout.html')
139 self.assertTrue(self.email in response.content)
141 # check that we've got an optout in the list
142 self.assertEquals(EmailOptout.objects.count(), 1)
143 self.assertEquals(EmailOptout.objects.all()[0].email, self.email)
145 # check that the confirmation is now inactive
146 self.assertFalse(EmailConfirmation.objects.get(
147 pk = self.conf.pk).active)
150 class OptoutPreexistingTest(OptoutTest):
151 """Test that a duplicated opt-out behaves the same as the initial one"""
153 super(OptoutPreexistingTest, self).setUp()
154 EmailOptout(email = self.email).save()
156 class OptinRequestTest(TestCase):
157 view = 'patchwork.views.mail.optin'
161 self.email = u'foo@example.com'
162 EmailOptout(email = self.email).save()
164 def testOptInRequestGET(self):
165 response = self.client.get(self.url)
166 self.assertRedirects(response, reverse('patchwork.views.mail.settings'))
168 def testOptInRequestValidPOST(self):
169 response = self.client.post(self.url, {'email': self.email})
171 # check for a confirmation object
172 self.assertEquals(EmailConfirmation.objects.count(), 1)
173 conf = EmailConfirmation.objects.get(email = self.email)
175 # check confirmation page
176 self.assertEquals(response.status_code, 200)
177 self.assertEquals(response.context['confirmation'], conf)
178 self.assertTrue(self.email in response.content)
181 url = reverse('patchwork.views.confirm', kwargs = {'key': conf.key})
182 self.assertEquals(len(mail.outbox), 1)
184 self.assertEquals(msg.to, [self.email])
185 self.assertEquals(msg.subject, 'Patchwork opt-in confirmation')
186 self.assertTrue(url in msg.body)
188 def testOptoutRequestInvalidPOSTEmpty(self):
189 response = self.client.post(self.url, {'email': ''})
190 self.assertEquals(response.status_code, 200)
191 self.assertFormError(response, 'form', 'email',
192 'This field is required.')
193 self.assertTrue(response.context['error'])
194 self.assertTrue('email_sent' not in response.context)
195 self.assertEquals(len(mail.outbox), 0)
197 def testOptoutRequestInvalidPOSTNonEmail(self):
198 response = self.client.post(self.url, {'email': 'foo'})
199 self.assertEquals(response.status_code, 200)
200 self.assertFormError(response, 'form', 'email', error_strings['email'])
201 self.assertTrue(response.context['error'])
202 self.assertTrue('email_sent' not in response.context)
203 self.assertEquals(len(mail.outbox), 0)
205 class OptinTest(TestCase):
208 self.email = u'foo@example.com'
209 self.optout = EmailOptout(email = self.email)
211 self.conf = EmailConfirmation(type = 'optin', email = self.email)
214 def testOptinValidHash(self):
215 url = reverse('patchwork.views.confirm',
216 kwargs = {'key': self.conf.key})
217 response = self.client.get(url)
219 self.assertEquals(response.status_code, 200)
220 self.assertTemplateUsed(response, 'patchwork/optin.html')
221 self.assertTrue(self.email in response.content)
223 # check that there's no optout remaining
224 self.assertEquals(EmailOptout.objects.count(), 0)
226 # check that the confirmation is now inactive
227 self.assertFalse(EmailConfirmation.objects.get(
228 pk = self.conf.pk).active)
230 class OptinWithoutOptoutTest(TestCase):
231 """Test an opt-in with no existing opt-out"""
232 view = 'patchwork.views.mail.optin'
235 def testOptInWithoutOptout(self):
236 email = u'foo@example.com'
237 response = self.client.post(self.url, {'email': email})
239 # check for an error message
240 self.assertEquals(response.status_code, 200)
241 self.assertTrue(bool(response.context['error']))
242 self.assertTrue('not on the patchwork opt-out list' in response.content)
244 class UserProfileOptoutFormTest(TestCase):
245 """Test that the correct optin/optout forms appear on the user profile
246 page, for logged-in users"""
248 view = 'patchwork.views.user.profile'
250 optout_url = reverse('patchwork.views.mail.optout')
251 optin_url = reverse('patchwork.views.mail.optin')
252 form_re_template = ('<form\s+[^>]*action="%(url)s"[^>]*>'
253 '.*?<input\s+[^>]*value="%(email)s"[^>]*>.*?'
255 secondary_email = 'test2@example.com'
258 self.user = create_user()
259 self.client.login(username = self.user.username,
260 password = self.user.username)
262 def _form_re(self, url, email):
263 return re.compile(self.form_re_template % {'url': url, 'email': email},
266 def testMainEmailOptoutForm(self):
267 form_re = self._form_re(self.optout_url, self.user.email)
268 response = self.client.get(self.url)
269 self.assertEquals(response.status_code, 200)
270 self.assertTrue(form_re.search(response.content) is not None)
272 def testMainEmailOptinForm(self):
273 EmailOptout(email = self.user.email).save()
274 form_re = self._form_re(self.optin_url, self.user.email)
275 response = self.client.get(self.url)
276 self.assertEquals(response.status_code, 200)
277 self.assertTrue(form_re.search(response.content) is not None)
279 def testSecondaryEmailOptoutForm(self):
280 p = Person(email = self.secondary_email, user = self.user)
283 form_re = self._form_re(self.optout_url, p.email)
284 response = self.client.get(self.url)
285 self.assertEquals(response.status_code, 200)
286 self.assertTrue(form_re.search(response.content) is not None)
288 def testSecondaryEmailOptinForm(self):
289 p = Person(email = self.secondary_email, user = self.user)
291 EmailOptout(email = p.email).save()
293 form_re = self._form_re(self.optin_url, p.email)
294 response = self.client.get(self.url)
295 self.assertEquals(response.status_code, 200)
296 self.assertTrue(form_re.search(response.content) is not None)