flask_imp.security

This module contains the security utilities for a Flask application.

Functions:

  • include_csrf: Includes a CSRF token in a GET response, and checks it during a

    POST request.

  • checkpoint: Checks if the passed in Checkpoint passes or fails.

  • checkpoint_callable: Checks if a function you give passes.

Classes:

  • APIKeyCheckpoint: A checkpoint focused around checking the header or query param

    for a valid token.

  • BearerCheckpoint: A checkpoint focused around working with the Bearer tokens.

  • SessionCheckpoint: A checkpoint focused around working with Flask’s session.

flask_imp.security.include_csrf(session_key='csrf', form_key='csrf', abort_status=401)

A decorator that handles CSRF protection.

On a GET request, a CSRF token is generated and stored in the session key specified by the session_key parameter.

On a POST request, the form_key specified is checked against the session_key specified.

If they match, the request is allowed to continue.

If no match, the response will be aborted, flask.abort(abort_code), default 401.

Example of a route that requires CSRF protection:

@bp.route("/admin", methods=["GET", "POST"])
@include_csrf(session_key="csrf", form_key="csrf")
def admin_page():
    ...
    # You must pass in the CSRF token from the session into the template.
    # Then add <input type="hidden" name="csrf" value="{{ csrf }}"> to the form.
    return render_template("admin.html", csrf=session.get("csrf"))
Parameters:
  • session_key (str) – session key to store the CSRF token in.

  • form_key (str) – form key to check against the session key.

  • abort_status (int) – abort status code to use if the CSRF check fails.

Returns:

decorated function, or abort(abort_code) response.

Return type:

Callable[[…], Any]

flask_imp.security.checkpoint_callable(callable_, predefined_args=None, include_url_args=False, fail_url=None, fail_json=None, fail_response=None, fail_status=403, pass_url=None, message=None, message_category='message', disable_default_fail=False)

A decorator that evaluates if the passed in callable is truly.

Useful for feature flags or other checks that need to be done before a route is accessed.

If include_url_args is set, the url variables of the route will be passed into the callable as __url_vars__ after any predefined_args.

Example of using predefined_args:

def check_if_number(value):
    if isinstance(value, int):
        if value > 10:
            return True
    return False

@bp.route("/number", methods=["GET"])
@checkpoint_callable(
    check_if_number,
    predefined_args={"value": os.getenv("NUMBER")},
    fail_url=lazy_url_for("www.index"),
    message="Failed message"
)
def number():
    ...

Example of checking route variable:

def check_url_vars(__url_vars__):
    if __url_vars__["value"] == 10:
        return True
    return False

...

@bp.route("/number/<int:value>", methods=["GET"])
@checkpoint_callable(
    check_url_vars,
    include_url_args=True,
    fail_url=lazy_url_for("wrong_number"),
    message="Failed message"
)
def number():
    ...

Example of using predefined_args from session:

def check_session_vars(value):
    # lazy_session_get is evaluated in the decorator.
    if value == 10:
        return True
    return False

...

@bp.route("/number", methods=["GET"])
@checkpoint_callable(
    check_session_vars,
    predefined_args={"value": lazy_session_get("NUMBER")},
    fail_url=lazy_url_for("www.index"),
    message="Failed message"
)
def number():
    ...
Parameters:
  • callable – the callable to call this will be passed the url variables of the route

  • predefined_args (Dict[str, Any] | None) – a dictionary of predefined arguments to pass to the callable

  • include_url_args (bool) – load the url variables into the callable’s arguments as __url_vars__

  • fail_url (str | Callable[[], Any] | None) – the url to redirect to if the callable fails

  • fail_json (Dict[str, Any] | None) – JSON that is returned on failure

  • fail_response (Callable[[], Response] | None) – a callable that returns a Flask Response on failure

  • fail_status (int) – the status code to abort with if the callable check fails

  • pass_url (str | Callable[[], Any] | None) – the url to redirect to if the callable passes

  • message (str | None) – if a message is specified, a flash message is shown

  • message_category (str) – the category of the flash message

  • disable_default_fail (bool) – if True, the callable will be called without default failure handling

  • callable_ (Callable[[...], Any])

Returns:

the decorated callable, or abort(abort_status) response

Return type:

Callable[[…], Any]

flask_imp.security.checkpoint(checkpoint_)

A decorator that checks the specified Checkpoint class.

NOTE: If the incoming request is JSON and no fail_json or endpoints are set, the decorator will return the following JSON on failure:

{“error”: “Unauthorized”}

Example of a route that requires a user to be logged in:

LOGIN_REQUIRED = SessionCheckpoint(
    'logged_in', True
).action(
    lazy_url_for('blueprint.login_page')
)

@bp.route("/admin", methods=["GET"])
@checkpoint(LOGIN_REQUIRED)
def admin_page():
    ...

Example of a route that if the user is already logged in, redirects to the specified endpoint:

IS_LOGGED_IN = SessionCheckpoint(
    'logged_in', True
).action(
    pass_url=lazy_url_for('blueprint.admin_page'),
    message="Already logged in"
)

@bp.route("/login-page", methods=["GET"])
@checkpoint(IS_LOGGED_IN)
def login_page():
    ...

Example of a route that requires a user to be logged in and to be an admin:

LOGIN_REQUIRED = SessionCheckpoint(
    session_key="logged_in",
    values_allowed=True,
).action(
    fail_url=lazy_url_for("blueprint.login_page"),
)

PERM_REQUIRED = SessionCheckpoint(
    session_key="user_type",
    values_allowed="admin",
).action(
    fail_url=lazy_url_for("blueprint.index"),
    message="You need to be an admin to access this page"
)

@bp.route("/admin", methods=["GET"])
@checkpoint(LOGIN_REQUIRED)
@checkpoint(PERM_REQUIRED)
def admin_page():
    ...

You can also supply your own failed return JSON:

JS_FETCH_CHECKPOINT = SessionCheckpoint(
    'logged_in', True
).action(
    fail_json={"error": "You are not logged in."}
)

@bp.route("/api/resource", methods=["GET"])
@checkpoint(JS_FETCH_CHECKPOINT)
def api_page():
    ...

Note: Using this on a API route will require you to include credentials on the request.

Here’s an example using JavaScript fetch():

fetch("/api/resource", {
    method: "GET",
    credentials: "include"
})...
Parameters:
  • checkpoint – the checkpoint class to pass or fail

  • checkpoint_ (ValidCheckpoint)

Returns:

the decorated function, or abort(fail_status), or redirect, or fail_json response

Return type:

Callable[[…], Any]

class flask_imp.security.BaseCheckpoint

Bases: object

Must never be instantiated directly.

action(fail_url=None, fail_json=None, fail_response=None, fail_status=403, pass_url=None, message=None, message_category='message', disable_default_fail=False)

Set the actions to take for this checkpoint.

If fail_json is provided, passing to endpoints will be disabled.

pass_url and fail_url take either a string or the utilities.lazy_url_for function.

Here’s an example of lazy_url_for usage:

from flask_imp.utilities import lazy_url_for

CHECKPOINT = ...(...).action(pass_url=lazy_url_for(endpoint))

@app.get("/protected")
@checkpoint(CHECKPOINT)
..

Parameters:
  • fail_url (str | Callable[[], Any] | None) – the url to redirect to if the key value fails

  • fail_json (Dict[str, Any] | None) – JSON that is returned on failure

  • fail_response (Callable[[], Response] | None) – a callable that returns a Flask Response on failure

  • fail_status (int) – the status code to return if the check fails

  • pass_url (str | Callable[[], Any] | None) – the url to redirect to if the key value passes

  • message (str | None) – a message to add to Flask’s flash

  • message_category (str) – the category of the flash message

  • disable_default_fail (bool) – disable the default failure behavior

Return type:

BaseCheckpoint

disable_default_fail: bool = False
fail_json: Dict[str, Any] | None = None
fail_response: Callable[[], Response] | None = (None,)
fail_status: int = 403
fail_url: str | Callable[[], Any] | None = None
message: str | None = None
message_category: str = 'message'
pass_()
Return type:

bool

pass_url: str | Callable[[], Any] | None = None
class flask_imp.security.APIKeyCheckpoint(key, type_='header', header_or_param='x-api-key')

Bases: BaseCheckpoint

Parameters:
  • key (str)

  • type_ (Literal['header', 'query_param'])

  • header_or_param (str)

pass_()
Return type:

bool

key: str
header: str
type_: Literal['header', 'query_param']
class flask_imp.security.BearerCheckpoint(token)

Bases: BaseCheckpoint

Parameters:

token (str)

pass_()
Return type:

bool

token: str
class flask_imp.security.SessionCheckpoint(session_key, values_allowed)

Bases: BaseCheckpoint

Parameters:
  • session_key (str)

  • values_allowed (List[str | int | bool] | str | int | bool)

pass_()
Return type:

bool

session_key: str
values_allowed: List[str | int | bool] | str | int | bool