Skip to content

fix(#1137): add transaction context manager for atomic multi-write operations (duplicate, conflicts resolved)#1233

Open
ionfwsrijan wants to merge 2 commits into
utksh1:mainfrom
ionfwsrijan:duplicate/pr-1173-transaction-isolation
Open

fix(#1137): add transaction context manager for atomic multi-write operations (duplicate, conflicts resolved)#1233
ionfwsrijan wants to merge 2 commits into
utksh1:mainfrom
ionfwsrijan:duplicate/pr-1173-transaction-isolation

Conversation

@ionfwsrijan

@ionfwsrijan ionfwsrijan commented Jun 23, 2026

Copy link
Copy Markdown
Contributor

Duplicate of #1173 with merge conflicts resolved and rebased onto latest main.

Problem

Every database write was auto-committed immediately (execute() calls
connection.commit() after every query). Multi-write operations (findings insert +
report insert, asset services delete+insert, task delete cascade) had no atomicity —
a crash midway would leave partial data.

Solution

  • Added Database.transaction() async context manager that wraps
    BEGIN/COMMIT/ROLLBACK
  • Wrapped the following multi-write operations in transactions:
    • _upsert_findings_and_report (findings + report + result resources)
    • _upsert_findings_and_report_from_scanner (same)
    • cancel_task (status update + audit log)
    • replace_asset_services (DELETE + INSERT loop)
    • delete_task_records (replaced manual begin()/commit()/rollback())
    • upsert_vault_secret (SELECT-then-UPDATE/INSERT race)
  • Single-statement execute() retains its auto-commit default; callers that need
    atomicity opt in via async with db.transaction():

Files changed

backend/secuscan/database.py, backend/secuscan/executor.py,
backend/secuscan/platform_resources.py, backend/secuscan/routes.py

Closes #1137

…ite operations

- Add Database.transaction() async context manager (begin/commit/rollback)
- Wrap _upsert_findings_and_report in transaction (findings + report + resources)
- Wrap _upsert_findings_and_report_from_scanner in transaction
- Wrap cancel_task status update + audit log in transaction
- Wrap replace_asset_services delete+insert in transaction
- Wrap delete_task_records in transaction (replacing manual begin/commit/rollback)
- Wrap upsert_vault_secret select-then-upsert in transaction
- Keep existing execute() auto-commit behavior for backward compatibility
- Fix indentation in replace_asset_services for loop body after
  wrapping in async with db.transaction()
- Run ruff format on all 4 changed files
@ionfwsrijan

Copy link
Copy Markdown
Contributor Author

@utksh1 Please review this now

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[BUG] No Transaction Isolation — Auto-Commit Per Write Operation Causes Database Inconsistency

1 participant