Skip to content

Fix/manual fields setting#172

Merged
HardMax71 merged 5 commits intomainfrom
fix/manual-fields-setting
Feb 12, 2026
Merged

Fix/manual fields setting#172
HardMax71 merged 5 commits intomainfrom
fix/manual-fields-setting

Conversation

@HardMax71
Copy link
Owner

@HardMax71 HardMax71 commented Feb 12, 2026


Summary by cubic

Standardized API responses with Pydantic model_validate/from_attributes and introduced typed list wrappers for scripts and subscriptions. Unified admin event export to /export/{format} and enforced strict notification URL validation; OpenAPI, SDK, and Editor are updated.

  • Refactors

    • Routes now return model_validate results (DLQ, notifications, saved scripts, saga list/cancel); schemas set from_attributes.
    • Added SavedScriptListResponse/DomainSavedScriptListResult and DomainSubscriptionListResult; frontend reads scripts from result.scripts.
    • Introduced ExportFormat; merged export endpoints into /admin/events/export/{format} (CSV/JSON).
    • Converted RateLimitRule to BaseModel and added UserRateLimitUpdate; admin settings/users use user_id only; removed usernames from audit logs.
  • Bug Fixes

    • Subscription updates use DomainSubscriptionUpdate with channel-specific checks and URL patterns (https-only webhooks, Slack hooks domain); SSE delivery is reliable.
    • Consistent user_id usage fixes audit and permission checks.
    • Removed manual serialization to prevent domain object serialization issues.

Written for commit 6ebef43. Summary will update on new commits.

Summary by CodeRabbit

  • New Features

    • Unified event export endpoint supporting CSV/JSON via an export format parameter
    • Export format enum added
  • Changes

    • List endpoints now return wrapped response objects (e.g., scripts, subscriptions) instead of raw arrays
    • Rate-limit updates use a dedicated update payload
    • Saga cancellation returns a structured result with success/message
    • Admin APIs now use user IDs (no user-visible behavior change)
  • Validation

    • Subscription webhook and Slack URLs now validated (rejects invalid URLs)

@coderabbitai
Copy link

coderabbitai bot commented Feb 12, 2026

Caution

Review failed

The pull request is closed.

📝 Walkthrough

Walkthrough

Consolidates CSV/JSON event export into a single parameterized /export/{export_format} endpoint; replaces admin username parameters with user_id across admin settings/users; wraps several list responses in container models; migrates select dataclasses to Pydantic BaseModel; standardizes response construction via model_validate.

Changes

Cohort / File(s) Summary
Admin Events Export Consolidation
backend/app/api/routes/admin/events.py, backend/app/services/admin/admin_events_service.py, backend/app/domain/enums/common.py, backend/app/domain/enums/__init__.py, docs/reference/openapi.json, frontend/src/lib/api/types.gen.ts, frontend/src/lib/api/sdk.gen.ts, frontend/src/lib/api/index.ts
Merged CSV and JSON exports into a single /api/v1/admin/events/export/{export_format} endpoint using new ExportFormat enum; added export_events(export_format) route and service dispatcher with _export_csv/_export_json helpers; updated OpenAPI and frontend SDK/types.
Admin Settings — user_id consolidation
backend/app/api/routes/admin/settings.py, backend/app/services/admin/admin_settings_service.py, backend/app/db/repositories/admin/admin_settings_repository.py, backend/app/db/docs/admin_settings.py, backend/tests/unit/services/test_admin_settings_service.py, backend/tests/e2e/db/repositories/test_admin_settings_repository.py
Replaced username/updated_by parameters with single user_id across routes, service, repository and tests; removed username from AuditLogDocument and adjusted audit payloads.
Admin Users — admin_user_id & rate-limit update
backend/app/api/routes/admin/users.py, backend/app/services/admin/admin_user_service.py, backend/app/domain/rate_limit/__init__.py, backend/app/domain/rate_limit/rate_limit_models.py
Switched admin context args from admin_username to admin_user_id; introduced UserRateLimitUpdate and refactored update_user_rate_limits to accept an update payload assembled via model_validate.
Notifications — DI and subscription model changes
backend/app/api/routes/notifications.py, backend/app/services/notification_service.py, backend/app/domain/notification/models.py, backend/app/domain/notification/__init__.py, backend/tests/e2e/notifications/test_notification_sse.py, backend/tests/e2e/services/notifications/test_notification_service.py
Replaced manual auth extraction with Depends(current_user) and injected User; changed update_subscription to accept DomainSubscriptionUpdate; get_subscriptions now returns DomainSubscriptionListResult; adapted calls and tests.
List response wrappers (saved scripts, notifications, subscriptions)
backend/app/api/routes/saved_scripts.py, backend/app/services/saved_script_service.py, backend/app/domain/saved_script/models.py, backend/app/domain/saved_script/__init__.py, frontend/src/routes/Editor.svelte, backend/tests/e2e/test_saved_scripts_routes.py, frontend/src/routes/__tests__/Editor.test.ts, backend/tests/e2e/services/saved_script/test_saved_script_service.py
Added list wrapper models (SavedScriptListResponse, DomainSavedScriptListResult) and updated services/routes/frontend/tests to use result.scripts/result.subscriptions instead of raw arrays/dicts.
Saga cancellation result & response simplification
backend/app/domain/saga/models.py, backend/app/domain/saga/__init__.py, backend/app/services/saga/saga_service.py, backend/app/api/routes/saga.py, backend/app/schemas_pydantic/saga.py
Added SagaCancellationResult, changed cancel_saga to return it; added model_config to response schemas and switched handlers to return service results via model_validate.
DLQ & aggregated response model_validate usage
backend/app/api/routes/dlq.py
Removed per-item DLQMessageResponse mapping and now validate aggregated result directly with DLQMessagesResponse.model_validate(result); removed unused import.
Replay models refactor
backend/app/domain/admin/replay_models.py, backend/app/services/admin/admin_events_service.py
Converted ReplaySessionStatusDetail from dataclass to Pydantic class inheriting ReplaySessionState, removed redundant session field; get_replay_status now uses model_validate and assigns estimated_completion/execution_results in-place.
Rate limit models — dataclass → Pydantic
backend/app/domain/rate_limit/rate_limit_models.py
Migrated RateLimitRule and UserRateLimit from dataclasses to Pydantic BaseModel (with model_config and Field); added UserRateLimitUpdate for update payloads.
Frontend and OpenAPI sync
docs/reference/openapi.json, frontend/src/lib/api/types.gen.ts, frontend/src/lib/api/index.ts, frontend/src/lib/api/sdk.gen.ts, frontend/src/routes/Editor.svelte
Updated OpenAPI and generated frontend types/SDK to reflect new export endpoint and SavedScriptListResponse; adjusted frontend to read data?.scripts.
Validation improvements
backend/app/schemas_pydantic/notification.py, backend/tests/e2e/test_notifications_routes.py
Added URL pattern validation to SubscriptionUpdate fields (webhook_url, slack_webhook) and added e2e tests asserting invalid URLs return 422.
Tests updated
multiple tests (export, subscriptions, saved scripts, settings)
Refactored tests to match new shapes/signatures: combined/parameterized export tests, subscription update payloads, saved scripts wrapper usage, and settings/user_id signature changes.

Sequence Diagram(s)

sequenceDiagram
    participant Client as Client
    participant API as Admin Events Route
    participant Service as AdminEventsService
    participant Repo as EventsRepository

    Client->>API: GET /api/v1/admin/events/export/{export_format}?filters...
    API->>Service: export_events(event_filter, limit, export_format)
    Service->>Repo: fetch_events(event_filter, limit)
    Repo-->>Service: events list
    alt export_format == "csv"
        Service->>Service: build CSV rows, generate bytes/stream
    else export_format == "json"
        Service->>Service: serialize events to JSON bytes/stream
    end
    Service-->>API: ExportResult (stream, filename, content-type)
    API-->>Client: StreamingResponse (file download)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

  • Fix/manual fields setting #172: implements the same unification of admin events CSV/JSON endpoints into export/{export_format} and matching service/route changes.
  • fix: mongo docs #168: refactors admin events export flow and touches the same route/service files involved in this PR.
  • Fix/sonar reliability #149: overlapping edits to admin/events export endpoints and parameter typing that likely conflict or complement these changes.

Poem

🐰 I hop through code with tidy paws,
Swapped usernames for simple user_id laws.
One export route now serves both kinds,
Lists go nested, models realigned.
model_validate hums — the rabbit cheers, "Hooray!" ✨

🚥 Pre-merge checks | ✅ 1 | ❌ 2
❌ Failed checks (1 warning, 1 inconclusive)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 64.21% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Title check ❓ Inconclusive The title 'Fix/manual fields setting' is vague and does not clearly convey the main changes in this substantial refactoring PR that affects multiple systems (responses, schemas, exports, rate limiting, admin endpoints). Consider a more descriptive title such as 'Standardize response modeling with Pydantic model_validate and from_attributes' or 'Refactor API responses and schema handling for consistency' to better reflect the scope of changes.
✅ Passed checks (1 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch fix/manual-fields-setting

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@cubic-dev-ai cubic-dev-ai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 issues found across 39 files

Prompt for AI agents (all issues)

Check if these issues are valid — if so, understand the root cause of each and fix them.


<file name="backend/app/services/notification_service.py">

<violation number="1" location="backend/app/services/notification_service.py:546">
P2: Webhook URL validation is skipped when callers update only `webhook_url` (enabled is None), so invalid URLs can now be saved. Validate the URL whenever a webhook URL is provided, not only when `enabled` is true.</violation>

<violation number="2" location="backend/app/services/notification_service.py:551">
P2: Slack webhook validation is skipped when callers update only `slack_webhook` (enabled is None), allowing invalid URLs to be stored. Validate the Slack webhook whenever it is provided.</violation>
</file>

Reply with feedback, questions, or to request a fix. Tag @cubic-dev-ai to re-run a review.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
docs/reference/openapi.json (1)

2080-2248: ⚠️ Potential issue | 🟠 Major

Document the export payload properly (current schema is empty).

The 200 response has an empty schema and only application/json, which makes client generation and content negotiation ambiguous for a downloadable CSV/JSON file. Please describe the payload as a binary file and add the appropriate content types (e.g., text/csv and application/json or application/octet-stream).

💡 Suggested OpenAPI fix
         "responses": {
           "200": {
             "description": "Successful Response",
             "content": {
-              "application/json": {
-                "schema": {}
-              }
+              "text/csv": {
+                "schema": {
+                  "type": "string",
+                  "format": "binary"
+                }
+              },
+              "application/json": {
+                "schema": {
+                  "type": "string",
+                  "format": "binary"
+                }
+              }
             }
           },
🤖 Fix all issues with AI agents
In `@backend/app/services/notification_service.py`:
- Around line 546-555: The channel-specific URL validation incorrectly uses "if
... and update_data.enabled" which treats None as False and skips validation on
partial updates; update these checks in the notification_service (the block
using NotificationChannel, update_data, and NotificationValidationError) to run
when enabled is not explicitly False (e.g., change the condition to "if channel
== NotificationChannel.WEBHOOK and update_data.enabled is not False" and
similarly for "if channel == NotificationChannel.SLACK and update_data.enabled
is not False") so validation runs when enabled is True or omitted (None),
keeping the same error messages and checks for
webhook_url.startswith("https://") and
slack_webhook.startswith("https://hooks.slack.com/").

@HardMax71 HardMax71 merged commit 1f64712 into main Feb 12, 2026
9 of 10 checks passed
@HardMax71 HardMax71 deleted the fix/manual-fields-setting branch February 12, 2026 15:51
@sonarqubecloud
Copy link

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.

1 participant