mirror of
https://github.com/hansjone/netx.git
synced 2026-10-09 00:50:46 +08:00
Harden auth with revocable sessions, cookies, and single-login default.
Issue short-lived access JWTs backed by AuthSession rows, HttpOnly cookies with refresh rotation, idle timeout, session management UI, WebCRT ownership caps, and optional Redis login rate limits; new logins revoke other sessions by default. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
ba33ab5c4f
commit
20c2fcd496
34 changed files with 1462 additions and 149 deletions
40
alembic/versions/20260806_auth_refresh.py
Normal file
40
alembic/versions/20260806_auth_refresh.py
Normal file
|
|
@ -0,0 +1,40 @@
|
|||
"""Add refresh token columns on auth_session.
|
||||
|
||||
Revision ID: 20260806_auth_refresh
|
||||
Revises: 20260806_auth_session
|
||||
Create Date: 2026-08-06
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from typing import Sequence, Union
|
||||
|
||||
from alembic import op
|
||||
|
||||
revision: str = "20260806_auth_refresh"
|
||||
down_revision: Union[str, Sequence[str], None] = "20260806_auth_session"
|
||||
branch_labels: Union[str, Sequence[str], None] = None
|
||||
depends_on: Union[str, Sequence[str], None] = None
|
||||
|
||||
|
||||
def upgrade() -> None:
|
||||
from netx_api.schema_patches import apply_auth_schema_patches
|
||||
|
||||
apply_auth_schema_patches(op.get_bind())
|
||||
|
||||
|
||||
def downgrade() -> None:
|
||||
bind = op.get_bind()
|
||||
dialect = bind.dialect.name
|
||||
if dialect == "postgresql":
|
||||
op.execute("ALTER TABLE auth_session DROP COLUMN IF EXISTS refresh_expires_at")
|
||||
op.execute("ALTER TABLE auth_session DROP COLUMN IF EXISTS refresh_token_hash")
|
||||
else:
|
||||
try:
|
||||
op.drop_column("auth_session", "refresh_expires_at")
|
||||
except Exception:
|
||||
pass
|
||||
try:
|
||||
op.drop_column("auth_session", "refresh_token_hash")
|
||||
except Exception:
|
||||
pass
|
||||
35
alembic/versions/20260806_auth_session.py
Normal file
35
alembic/versions/20260806_auth_session.py
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
"""Create auth_session table for revocable JWT logins.
|
||||
|
||||
Revision ID: 20260806_auth_session
|
||||
Revises: 20260802_legacy
|
||||
Create Date: 2026-08-06
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from typing import Sequence, Union
|
||||
|
||||
from alembic import op
|
||||
|
||||
revision: str = "20260806_auth_session"
|
||||
down_revision: Union[str, Sequence[str], None] = "20260802_legacy"
|
||||
branch_labels: Union[str, Sequence[str], None] = None
|
||||
depends_on: Union[str, Sequence[str], None] = None
|
||||
|
||||
|
||||
def upgrade() -> None:
|
||||
from netx_api.schema_patches import apply_auth_schema_patches
|
||||
|
||||
apply_auth_schema_patches(op.get_bind())
|
||||
|
||||
|
||||
def downgrade() -> None:
|
||||
bind = op.get_bind()
|
||||
dialect = bind.dialect.name
|
||||
if dialect == "postgresql":
|
||||
op.execute("DROP TABLE IF EXISTS auth_session")
|
||||
else:
|
||||
try:
|
||||
op.drop_table("auth_session")
|
||||
except Exception:
|
||||
pass
|
||||
Loading…
Add table
Add a link
Reference in a new issue