Skip to content

Commit

Permalink
feature: add config option for default OTL TTL
Browse files Browse the repository at this point in the history
  • Loading branch information
mutantsan committed Oct 10, 2023
1 parent 5686e2b commit e179c1d
Show file tree
Hide file tree
Showing 6 changed files with 43 additions and 10 deletions.
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,10 +25,10 @@ Compatibility with core CKAN versions:

## Config settings

**TODO**. This config option is only planned:
Available configuration options:

# The number in seconds that specifies the OTL (optional, default: 86400).
ckanext.let_me_in.otl_ttl= 86400
# The number in seconds that specifies the OTL link TTL (optional, default: 86400).
ckanext.let_me_in.otl_link_ttl= 3600

## Developer installation

Expand Down
2 changes: 1 addition & 1 deletion ckanext/let_me_in/cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ def uli(uid: str, name: str, mail: str):
{"ignore_auth": True}, {"uid": uid, "name": name, "mail": mail}
)
except tk.ValidationError as e:
return click.secho(e, fg="red", err=True)
return click.secho(e.error_dict, fg="red", err=True)

click.echo("Your one-time login link has been generated")
click.secho(result["url"], fg="green")
10 changes: 10 additions & 0 deletions ckanext/let_me_in/config.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import ckan.plugins.toolkit as tk

CONF_OTL_LINK_TTL = "ckanext.let_me_in.otl_link_ttl"
DEFAULT_OTL_LINK_TTL = 86400


def get_default_otl_link_ttl() -> int:
"""Return a default TTL for an OTL link in seconds."""

return tk.asint(tk.config.get(CONF_OTL_LINK_TTL, DEFAULT_OTL_LINK_TTL))
14 changes: 9 additions & 5 deletions ckanext/let_me_in/logic/action.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
from ckan import model, types
from ckan.logic import validate

import ckanext.let_me_in.config as lmi_config
import ckanext.let_me_in.logic.schema as schema
import ckanext.let_me_in.utils as lmi_utils

Expand All @@ -31,9 +32,9 @@ def lmi_generate_otl(
"""
tk.check_access("lmi_generate_otl", context, data_dict)

uid = data_dict.get("uid", "")
name = data_dict.get("name", "")
mail = data_dict.get("mail", "")
uid: str = data_dict.get("uid", "")
name: str = data_dict.get("name", "")
mail: str = data_dict.get("mail", "")

if not any([uid, name, mail]):
raise tk.ValidationError(
Expand All @@ -51,10 +52,13 @@ def lmi_generate_otl(

user = cast(model.User, lmi_utils.get_user(uid or name or mail))
now = dt.utcnow()
expires_at = now + td(hours=24)

token = jwt.encode(
{"user_id": user.id, "exp": expires_at, "created_at": now.timestamp()},
{
"user_id": user.id,
"exp": now + td(seconds=lmi_config.get_default_otl_link_ttl()),
"created_at": now.timestamp(),
},
lmi_utils.get_secret(True),
algorithm="HS256",
)
Expand Down
20 changes: 20 additions & 0 deletions ckanext/let_me_in/tests/test_views.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from __future__ import annotations

from datetime import timedelta
from typing import cast

import pytest
Expand Down Expand Up @@ -42,3 +43,22 @@ def test_visit_link_after_user_has_been_deleted(self, app, user):
user.commit()

assert "Invalid login link" in app.get(otl["url"]).body

@pytest.mark.parametrize(
"delta_kwargs,expired",
[
({"days": 1}, True),
({"hours": 23}, False),
],
)
def test_otl_time_expiration(self, app, freezer, user, delta_kwargs, expired):
"""Each OTL link has an expiration date. By default, it's a 24 hours, but
this is configurable. We need to be sure, that it works properly"""
otl = call_action("lmi_generate_otl", uid=user["id"])

freezer.move_to(timedelta(**delta_kwargs))

resp_body: str = app.get(otl["url"]).body

err_msg = "The login link has expired. Please request a new one"
assert err_msg in resp_body if expired else err_msg not in resp_body
1 change: 0 additions & 1 deletion ckanext/let_me_in/utils.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
from __future__ import annotations

from datetime import datetime as dt
from typing import cast

from ckan import model
from ckan.lib.api_token import _get_secret
Expand Down

0 comments on commit e179c1d

Please sign in to comment.