diff --git a/hc/accounts/tests/test_check_token.py b/hc/accounts/tests/test_check_token.py index d1a33112..ec778273 100644 --- a/hc/accounts/tests/test_check_token.py +++ b/hc/accounts/tests/test_check_token.py @@ -9,8 +9,12 @@ class CheckTokenTestCase(BaseTestCase): self.profile.token = make_password("secret-token") self.profile.save() - def test_it_redirects(self): + def test_it_shows_form(self): r = self.client.get("/accounts/check_token/alice/secret-token/") + self.assertContains(r, "You are about to log in") + + def test_it_redirects(self): + r = self.client.post("/accounts/check_token/alice/secret-token/") self.assertRedirects(r, "/checks/") # After login, token should be blank @@ -22,12 +26,12 @@ class CheckTokenTestCase(BaseTestCase): self.client.login(username="alice@example.org", password="password") # Login again, when already authenticated - r = self.client.get("/accounts/check_token/alice/secret-token/") + r = self.client.post("/accounts/check_token/alice/secret-token/") self.assertRedirects(r, "/checks/") def test_it_redirects_bad_login(self): # Login with a bad token url = "/accounts/check_token/alice/invalid-token/" - r = self.client.get(url, follow=True) + r = self.client.post(url, follow=True) self.assertRedirects(r, "/accounts/login/") self.assertContains(r, "incorrect or expired") diff --git a/hc/accounts/views.py b/hc/accounts/views.py index aed21d19..fffe0393 100644 --- a/hc/accounts/views.py +++ b/hc/accounts/views.py @@ -105,19 +105,28 @@ def check_token(request, username, token): # User is already logged in return redirect("hc-checks") - user = authenticate(username=username, token=token) - if user is not None and user.is_active: - # This should get rid of "welcome_code" in session - request.session.flush() + # Some email servers open links in emails to check for malicious content. + # To work around this, we sign user in if the method is POST. + # + # If the method is GET, we instead serve a HTML form and a piece + # of Javascript to automatically submit it. - user.profile.token = "" - user.profile.save() - auth_login(request, user) + if request.method == "POST": + user = authenticate(username=username, token=token) + if user is not None and user.is_active: + # This should get rid of "welcome_code" in session + request.session.flush() - return redirect("hc-checks") + user.profile.token = "" + user.profile.save() + auth_login(request, user) + + return redirect("hc-checks") + + request.session["bad_link"] = True + return redirect("hc-login") - request.session["bad_link"] = True - return redirect("hc-login") + return render(request, "accounts/check_token_submit.html") @login_required diff --git a/templates/accounts/check_token_submit.html b/templates/accounts/check_token_submit.html new file mode 100644 index 00000000..cfe82aa6 --- /dev/null +++ b/templates/accounts/check_token_submit.html @@ -0,0 +1,62 @@ + + + + + Continue to healthchecks.io + + + + +
{% csrf_token %}
+ + + + + + + + \ No newline at end of file