You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
TL;DR: Harden the service layer — split the DirectusApiClient god-class, make error handling consistent and safe, fix the permission-check race + PII logging, and add the missing unit tests — so the data/permission/preset layer is testable and trustworthy.
Context
The audit of 2026-06-22 found the service layer is the least-tested, highest-risk area: DirectusApiClient (services/api-client.ts, 865 lines, 18 public methods spanning 4 domains) has no unit tests, nor do usePermissionChecks or useUserPresets. Error handling is inconsistent (the utils/error-helpers.ts helpers are used by only 2 of ~110 catch blocks) and in places unsafe (silent permission-denying catches). This epic groups the service-layer concerns that are out of scope for #31 (block handling) and the item-selector epic.
Success Criteria
DirectusApiClient split into focused domain clients over a shared transport
Error handling is consistent: one documented pattern, no silent permission/destructive defaults
usePermissionChecks returns correct results (no race) and logs no PII
Unit-test coverage exists for api-client, usePermissionChecks, useUserPresets
Scope
In Scope:
Splitting DirectusApiClient into domain clients
Unifying error handling (adopt or remove error-helpers.ts); fixing silent catches
Fixing the usePermissionChecks race condition + removing PII logging
Adding unit tests for the untested service/permission/preset code
Caching features (previously declined, see closed caching issues)
Architecture Decisions
Binding for ALL sub-issues. Deviations require an update to this section.
Domain clients over one god-class: split DirectusApiClient into ItemsClient / MetadataClient / PermissionsClient / PresetsClient sharing one transport (retry + error + availability). No raw getApi() leak.
One error-handling pattern: either route API catches through utils/error-helpers.ts (handleApiError) everywhere, or remove it — no half-adopted helper. Destructive/permission operations must never default to "allow"/"granted" on error without an explicit, logged decision.
No PII in logs: never log full user objects (email, etc.).
Tests are part of the refactor, not after it: add tests before/alongside each split.
TL;DR: Harden the service layer — split the
DirectusApiClientgod-class, make error handling consistent and safe, fix the permission-check race + PII logging, and add the missing unit tests — so the data/permission/preset layer is testable and trustworthy.Context
The audit of 2026-06-22 found the service layer is the least-tested, highest-risk area:
DirectusApiClient(services/api-client.ts, 865 lines, 18 public methods spanning 4 domains) has no unit tests, nor dousePermissionChecksoruseUserPresets. Error handling is inconsistent (theutils/error-helpers.tshelpers are used by only 2 of ~110 catch blocks) and in places unsafe (silent permission-denying catches). This epic groups the service-layer concerns that are out of scope for #31 (block handling) and the item-selector epic.Success Criteria
DirectusApiClientsplit into focused domain clients over a shared transportusePermissionChecksreturns correct results (no race) and logs no PIIapi-client,usePermissionChecks,useUserPresetsScope
In Scope:
DirectusApiClientinto domain clientserror-helpers.ts); fixing silent catchesusePermissionChecksrace condition + removing PII loggingOut of Scope:
RelationCheckerdelete-on-error behaviour (→ bug fix: usage-check error blocks deletion instead of surfacing the unverified-usage warning #72)Architecture Decisions
Binding for ALL sub-issues. Deviations require an update to this section.
DirectusApiClientintoItemsClient/MetadataClient/PermissionsClient/PresetsClientsharing one transport (retry + error + availability). No rawgetApi()leak.utils/error-helpers.ts(handleApiError) everywhere, or remove it — no half-adopted helper. Destructive/permission operations must never default to "allow"/"granted" on error without an explicit, logged decision.Sub-Issues
api-client,usePermissionChecks,useUserPresetsusePermissionChecksrace condition + remove PII loggingerror-helpers.ts), fix silent catchesDirectusApiClientinto domain clientsParallelization: #80, #81, #82 are independent. #83 should follow #80 (tests as a safety net before the split).
References
src/services/api-client.ts(865 lines)src/utils/error-helpers.tssrc/composables/usePermissionChecks.ts(210 lines)src/composables/useUserPresets.ts(371 lines)src/services/RelationChecker.ts(has a spec)Risks
DirectusApiClientis used across composables; the split must keep call sites working. → Keep a thin facade if needed.Dependencies