Skip to content

Release: hardening#10

Merged
rennf93 merged 2 commits into
masterfrom
release/hardening
Apr 27, 2026
Merged

Release: hardening#10
rennf93 merged 2 commits into
masterfrom
release/hardening

Conversation

@rennf93
Copy link
Copy Markdown
Owner

@rennf93 rennf93 commented Apr 27, 2026

Description

Hardening release. Preflights previously short-circuited inside _before_request before the security pipeline ran, so banned IPs could preflight freely. Now the security pipeline executes for every request including OPTIONS. The _after_request hook injects CORS headers via the new shared guard_core.sync.handlers.cors_handler.CorsHandler module.

The branch also removes every form of suppression that had accumulated in pyproject.toml and the test suite, fixing the underlying issues at root.

Pipeline / CORS

  • _before_request: runs the security pipeline FIRST for every method including OPTIONS. After the pipeline returns None (no block), checks is_preflight() and either builds a preflight response via cors_handler.build_preflight_response or returns None to continue.
  • Blocked responses get CORS headers attached so cross-origin clients see the real status (403, 429, …) instead of an opaque CORS error.
  • _after_request: injects CORS headers into normal responses via cors_handler.build_response_headers.
  • Old _handle_preflight flow removed; replaced by _attach_cors_to_blocked and _build_flask_preflight_response helpers that delegate to CorsHandler.

Suppressions removed (root-cause fixes)

  • All [[tool.mypy.overrides]] ignore_missing_imports = true / follow_imports = "skip" / disallow_untyped_decorators = false blocks. Replaced with proper stubs and inline-typed packages.
  • All # type: ignore markers from edited files. Replaced with proper cast(...), MagicMock(spec=...), or typed callbacks.
  • [tool.uv.sources] guard-core = { path = ..., editable = true } block stripped from committed pyproject.toml.
  • guard-agent added to dev dependencies (was missing — only mentioned in deptry config).

Related Issue

N/A (audit findings).


Motivation and Context

Companion to guard-core 2.2.0 and guard-agent 2.3.0. The audit found that every adapter shipped its own preflight short-circuit ahead of the security pipeline. guard-core 2.2.0 landed the framework-agnostic cors_handler module so adapters consume one source of truth.

Removing the suppressions was a separate-but-related cleanup: per-module mypy overrides like ignore_missing_imports = true had been hiding real type mismatches in test fixtures and a few adapter call sites. The strict no-suppression rule across the release wave catches these at root rather than letting them rot.


Type of change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)
  • Documentation change
  • Performance improvement
  • Code cleanup or refactoring

How Has This Been Tested?

Full quality suite green:

Gate Result
ruff format / ruff check clean
mypy flaskapi_guard/ tests/ 0 errors, 21 source files
vulture clean
bandit -ll 0 medium-or-higher findings
radon average rank A (2.49)
xenon clean
deptry clean
pytest -W error --cov-branch 214 passed, 0 warnings, 100% line + 100% branch (376 stmts, 70 branches, 0 partial)

Suppression scan on the diff: 0 added, all mypy override suppression blocks removed, all # type: ignore markers removed.

E2E tested against guard-core 2.2.0 from PyPI plus the local guard-agent 2.3.0 (release/hardening) — 210 tests pass cleanly.

Tested locally on Python 3.10. CI runs the matrix to 3.14.


Screenshots (if appropriate):

N/A — library release.


Checklist:

  • My code follows the code style of this project (Mypy, Ruff)
  • I have added tests to cover my changes
  • All new and existing tests passed
  • My change requires a change to the documentation
  • I have updated the documentation accordingly
  • I have checked that my changes don't introduce any new warnings or errors
  • I have updated the version number if necessary
  • I have added any new dependencies to the appropriate requirements file

rennf93 added 2 commits April 27, 2026 08:53
Companion to guard-core 2.2.0 and guard-agent 2.3.0. Pipeline-first CORS in the FlaskAPIGuard extension via guard_core.sync.handlers.cors_handler.

- _before_request now runs the security pipeline for every method including OPTIONS preflight. Preflights were previously short- circuited inside the extension before the pipeline ran; banned IPs could preflight freely.

- Preflight handling moved BEFORE the passthrough / bypass check so cross-origin preflights to excluded paths (e.g. /health) still receive a valid CORS response. Passthrough and bypass return paths now also inject CORS headers via _attach_cors_to_blocked.

- _after_request injects CORS headers via the shared guard_core.sync.handlers.cors_handler.CorsHandler module.

- Removed every [[tool.mypy.overrides]] suppression block (ignore_missing_imports = true / follow_imports = 'skip' / disallow_untyped_decorators = false). Replaced with proper stubs (django-stubs) and inline-typed packages.

- Removed every # type: ignore from edited files.

- Stripped [tool.uv.sources] guard-core local-path block from committed pyproject.toml.

- Added guard-agent to dev dependencies (was missing -- only mentioned in deptry's per_rule_ignores). Tests exercising agent integration via enable_agent=True now have an explicit declared dev dep.

- Test infrastructure: added two regression tests proving cross-origin preflight + GET to excluded paths both work correctly with CORS.

Full suite: 216 passed, 100% line + 100% branch coverage. Quality suite (mypy / ruff / vulture / bandit / radon / xenon / deptry) clean. 0 added suppressions. See CHANGELOG.md.

BREAKING CHANGE: CORS is configured purely via SecurityConfig.cors_* fields and activates automatically inside the FlaskAPIGuard extension. There is no separate configure_cors entry point. OPTIONS preflight requests are now subject to the full security pipeline.
@github-actions github-actions Bot added documentation Docs, README, CHANGELOG, governance files area: extension Touches flaskapi_guard/extension.py (Flask extension hook) area: decorators Touches Flask-specific decorator wiring or re-exports tests Test suite changes dependencies pyproject.toml or uv.lock labels Apr 27, 2026
@rennf93 rennf93 self-assigned this Apr 27, 2026
@rennf93 rennf93 changed the title Release/hardening Release: hardening Apr 27, 2026
@rennf93 rennf93 merged commit 78a56f3 into master Apr 27, 2026
10 of 11 checks passed
@rennf93 rennf93 deleted the release/hardening branch April 27, 2026 07:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area: decorators Touches Flask-specific decorator wiring or re-exports area: extension Touches flaskapi_guard/extension.py (Flask extension hook) dependencies pyproject.toml or uv.lock documentation Docs, README, CHANGELOG, governance files tests Test suite changes

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant