-
Notifications
You must be signed in to change notification settings - Fork 154
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- improve test speed by using freezegun instead of sleep() - add tests for turning off freshness validation (make sure auth_tokens work w/o session) - improve docs around freshness - add tests to webauthn to make sure returns auth_token closes #871
- Loading branch information
Showing
13 changed files
with
143 additions
and
113 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -5,12 +5,13 @@ | |
Confirmable tests | ||
""" | ||
|
||
from datetime import date, timedelta | ||
import re | ||
import time | ||
from urllib.parse import parse_qsl, urlsplit | ||
|
||
import pytest | ||
from flask import Flask | ||
from freezegun import freeze_time | ||
from wtforms.fields import StringField | ||
from wtforms.validators import Length | ||
|
||
|
@@ -185,14 +186,14 @@ def test_requires_confirmation_error_redirect(app, clients): | |
@pytest.mark.registerable() | ||
@pytest.mark.settings(confirm_email_within="1 milliseconds") | ||
def test_expired_confirmation_token(client, get_message): | ||
with capture_registrations() as registrations: | ||
data = dict(email="[email protected]", password="awesome sunset", next="") | ||
client.post("/register", data=data, follow_redirects=True) | ||
|
||
email = registrations[0]["email"] | ||
token = registrations[0]["confirm_token"] | ||
# Note that we need relatively new-ish date since session cookies also expire. | ||
with freeze_time(date.today() + timedelta(days=-1)): | ||
with capture_registrations() as registrations: | ||
data = dict(email="[email protected]", password="awesome sunset", next="") | ||
client.post("/register", data=data, follow_redirects=True) | ||
|
||
time.sleep(1) | ||
email = registrations[0]["email"] | ||
token = registrations[0]["confirm_token"] | ||
|
||
response = client.get("/confirm/" + token, follow_redirects=True) | ||
msg = get_message("CONFIRMATION_EXPIRED", within="1 milliseconds", email=email) | ||
|
@@ -416,15 +417,16 @@ def test_spa_get(app, client, get_message): | |
def test_spa_get_bad_token(app, client, get_message): | ||
"""Test expired and invalid token""" | ||
with capture_flashes() as flashes: | ||
with capture_registrations() as registrations: | ||
response = client.post( | ||
"/register", | ||
json=dict(email="[email protected]", password="awesome sunset"), | ||
headers={"Content-Type": "application/json"}, | ||
) | ||
assert response.headers["Content-Type"] == "application/json" | ||
token = registrations[0]["confirm_token"] | ||
time.sleep(1) | ||
# Note that we need relatively new-ish date since session cookies also expire. | ||
with freeze_time(date.today() + timedelta(days=-1)): | ||
with capture_registrations() as registrations: | ||
response = client.post( | ||
"/register", | ||
json=dict(email="[email protected]", password="awesome sunset"), | ||
headers={"Content-Type": "application/json"}, | ||
) | ||
assert response.headers["Content-Type"] == "application/json" | ||
token = registrations[0]["confirm_token"] | ||
|
||
response = client.get("/confirm/" + token) | ||
assert response.status_code == 302 | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -9,12 +9,13 @@ | |
""" | ||
|
||
from contextlib import contextmanager | ||
import time | ||
from datetime import date, timedelta | ||
|
||
import flask_wtf.csrf | ||
|
||
import pytest | ||
from flask_wtf import CSRFProtect | ||
from freezegun import freeze_time | ||
|
||
from flask_security import Security, hash_password | ||
from tests.test_utils import get_form_input, get_session, logout | ||
|
@@ -229,14 +230,11 @@ def test_reset(app, client): | |
|
||
|
||
@pytest.mark.recoverable() | ||
@pytest.mark.csrf(csrfprotect=True) | ||
def test_cp_reset(app, client): | ||
"""Test that header based CSRF works for /reset when | ||
using WTF_CSRF_CHECK_DEFAULT=False. | ||
""" | ||
app.config["WTF_CSRF_ENABLED"] = True | ||
app.config["WTF_CSRF_CHECK_DEFAULT"] = False | ||
CSRFProtect(app) | ||
|
||
with mp_validate_csrf() as mp: | ||
data = dict(email="[email protected]") | ||
# should fail - no CSRF token | ||
|
@@ -348,16 +346,10 @@ def test_cp_config2(app, sqlalchemy_datastore): | |
|
||
|
||
@pytest.mark.changeable() | ||
@pytest.mark.csrf(csrfprotect=True) | ||
@pytest.mark.settings(CSRF_PROTECT_MECHANISMS=["basic", "session"]) | ||
def test_different_mechanisms(app, sqlalchemy_datastore): | ||
def test_different_mechanisms(app, client): | ||
# Verify that using token doesn't require CSRF, but sessions do | ||
app.config["WTF_CSRF_ENABLED"] = True | ||
app.config["WTF_CSRF_CHECK_DEFAULT"] = False | ||
CSRFProtect(app) | ||
app.security = Security(app=app, datastore=sqlalchemy_datastore) | ||
create_user(app) | ||
|
||
client = app.test_client() | ||
with mp_validate_csrf() as mp: | ||
auth_token, csrf_token = json_login(client) | ||
|
||
|
@@ -446,15 +438,9 @@ def test_cp_with_token_empty_mechanisms(app, client): | |
assert response.status_code == 200 | ||
|
||
|
||
@pytest.mark.csrf(csrfprotect=True) | ||
@pytest.mark.settings(csrf_ignore_unauth_endpoints=True, CSRF_COOKIE_NAME="XSRF-Token") | ||
def test_csrf_cookie(app, sqlalchemy_datastore): | ||
app.config["WTF_CSRF_ENABLED"] = True | ||
app.config["WTF_CSRF_CHECK_DEFAULT"] = False | ||
CSRFProtect(app) | ||
app.security = Security(app=app, datastore=sqlalchemy_datastore) | ||
create_user(app) | ||
|
||
client = app.test_client() | ||
def test_csrf_cookie(app, client): | ||
json_login(client) | ||
assert client.get_cookie("XSRF-Token") | ||
|
||
|
@@ -491,23 +477,17 @@ def test_cp_with_token_cookie(app, client): | |
assert not client.get_cookie("XSRF-Token") | ||
|
||
|
||
@pytest.mark.csrf(csrfprotect=True) | ||
@pytest.mark.app_settings(wtf_csrf_time_limit=1) | ||
@pytest.mark.settings(CSRF_COOKIE_NAME="XSRF-Token", csrf_ignore_unauth_endpoints=True) | ||
@pytest.mark.changeable() | ||
def test_cp_with_token_cookie_expire(app, sqlalchemy_datastore): | ||
def test_cp_with_token_cookie_expire(app, client): | ||
# Make sure that we get a new Csrf-Token cookie if expired. | ||
app.config["WTF_CSRF_ENABLED"] = True | ||
app.config["WTF_CSRF_TIME_LIMIT"] = 1 | ||
app.config["WTF_CSRF_CHECK_DEFAULT"] = False | ||
CSRFProtect(app) | ||
app.security = Security(app=app, datastore=sqlalchemy_datastore) | ||
create_user(app) | ||
|
||
client = app.test_client() | ||
|
||
json_login(client, use_header=True) | ||
# Note that we need relatively new-ish date since session cookies also expire. | ||
with freeze_time(date.today() + timedelta(days=-1)): | ||
json_login(client, use_header=True) | ||
|
||
# sleep so make csrf_token expires | ||
time.sleep(2) | ||
# time unfrozen so should be expired | ||
data = dict( | ||
password="password", | ||
new_password="battery staple", | ||
|
@@ -600,16 +580,12 @@ def test_remember_login_csrf_cookie(app, client): | |
|
||
@pytest.mark.csrf(csrfprotect=True) | ||
@pytest.mark.registerable() | ||
@pytest.mark.settings(csrf_header="X-CSRF-Token") | ||
def test_json_register_csrf_with_ignore_unauth_set_to_false(app, client): | ||
""" | ||
Test that you are able to register a user when using the JSON api | ||
and the CSRF_IGNORE_UNAUTH_ENDPOINTS is set to False. | ||
""" | ||
app.config["WTF_CSRF_ENABLED"] = True | ||
app.config["WTF_CSRF_CHECK_DEFAULT"] = False | ||
app.config["CSRF_IGNORE_UNAUTH_ENDPOINTS"] = False | ||
app.config["SECURITY_CSRF_HEADER"] = "X-CSRF-Token" | ||
CSRFProtect(app) | ||
|
||
csrf_token = client.get("/login", headers={"Accept": "application/json"}).json[ | ||
"response" | ||
|
Oops, something went wrong.