-
Notifications
You must be signed in to change notification settings - Fork 498
Significantly faster users/[user_id] endpoint (and some others) #998
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
Note Other AI code review bot(s) detectedCodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review. WalkthroughReplaces Prisma-based tenancy lookups with RawQuery-driven tenancy/project/config queries, changes Changes
Sequence Diagram(s)sequenceDiagram
participant Client
participant API as API Handler
participant Smart as smart-request
participant TenLib as tenancies
participant RawQ as RawQuery
participant DB
rect rgb(245,250,255)
Note over Client,API: Incoming request with auth and project/branch headers
Client->>API: HTTP request
API->>Smart: build SmartRequest (include projectId, branchId)
Smart->>TenLib: getSoleTenancyFromProjectBranchQuery(projectId, branchId, true)
TenLib->>RawQ: compose bundled RawQuery (tenancy, project, rendered config)
RawQ->>DB: execute queries
DB-->>RawQ: tenancy, project, config
RawQ-->>TenLib: tenancy (includes tenancy.config)
TenLib-->>Smart: return Tenancy
Smart->>API: call getUser({ tenancy, userId })
API->>RawQ: user lookup using tenancy.config.sourceOfTruth
RawQ->>DB: fetch user
DB-->>RawQ: user
RawQ-->>API: return user
API-->>Client: response
end
rect rgb(240,255,240)
Note over TenLib,DB: Dev-time cross-check (non-prod)
TenLib->>DB: run legacy Prisma path for comparison
DB-->>TenLib: legacy result
alt mismatch
TenLib-->>API: throw StackAssertionError (dev)
else match
TenLib-->>API: continue
end
end
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes
Possibly related PRs
Poem
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (1 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
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. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull Request Overview
This PR refactors tenancy fetching to use the new RawQuery pattern for improved performance and query bundling. The key motivation is to optimize the smart request authentication flow by fetching tenancies alongside other required data rather than sequentially.
- Introduced
getSoleTenancyFromProjectBranchQueryandgetTenancyFromProjectQueryto support query bundling - Refactored
getUserto accept aTenancyobject directly, avoiding redundant fetches - Added development mode validation to ensure the new RawQuery implementation matches the old Prisma-based approach
Reviewed Changes
Copilot reviewed 3 out of 3 changed files in this pull request and generated 1 comment.
| File | Description |
|---|---|
| apps/backend/src/route-handlers/smart-request.tsx | Integrated tenancy fetching into bundled queries and removed the performance hack for /users/me endpoint |
| apps/backend/src/lib/tenancies.tsx | Added RawQuery-based implementations and deprecated old Prisma methods, with development mode validation |
| apps/backend/src/app/api/latest/users/crud.tsx | Updated getUser to accept Tenancy object and use getRenderedProjectConfigQuery for optimization |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Greptile Overview
Greptile Summary
Performance optimization that reduces database queries by batching tenancy fetching into the initial request bundle in SmartRequestAuth.
Key Changes
tenancies.tsx: refactoredgetTenancyFromProjectto useRawQuerypattern, enabling parallel query executionsmart-request.tsx: tenancy now fetched in bundled query alongside project/user/config, eliminating redundant callsusers/crud.tsx:getUser()accepts tenancy object directly to avoid re-fetching config when tenancy is already available
Issues Found
- Critical logic bug in
tenancies.tsx:185- development validation runs in production instead of development due to inverted boolean logic
Confidence Score: 1/5
- Critical logic error causes validation code to run in production instead of development
- The inverted condition in tenancies.tsx:185 causes expensive validation queries to execute in production environments where they shouldn't run, while skipping validation in development where they're needed. This will cause performance degradation in prod and miss bugs in dev.
- apps/backend/src/lib/tenancies.tsx requires immediate fix to line 185 condition
Important Files Changed
File Analysis
| Filename | Score | Overview |
|---|---|---|
| apps/backend/src/lib/tenancies.tsx | 1/5 | refactored tenancy fetching to use RawQuery for performance; critical logic bug in development validation (runs in prod instead of dev) |
| apps/backend/src/route-handlers/smart-request.tsx | 5/5 | optimized by fetching tenancy in bundled query instead of separate call; removed performance hack comment |
| apps/backend/src/app/api/latest/users/crud.tsx | 5/5 | updated getUser to accept tenancy object directly, avoiding redundant config queries |
Sequence Diagram
sequenceDiagram
participant Client
participant SmartRequest
participant RawQuery as RawQuery Bundle
participant GlobalDB as Global Database
participant SourceDB as Source-of-Truth DB
Client->>SmartRequest: API Request (e.g., GET /users/:user_id)
SmartRequest->>RawQuery: Create bundled query (project, tenancy, user, config, keys)
RawQuery->>GlobalDB: Execute all queries in parallel
GlobalDB-->>RawQuery: Return results
RawQuery-->>SmartRequest: project, tenancy, config, userIfOnGlobal
alt Source-of-truth is hosted (global DB)
SmartRequest->>SmartRequest: Use userIfOnGlobal from bundle
else Source-of-truth is external
SmartRequest->>SourceDB: getUser(projectId, branchId, userId)
SourceDB-->>SmartRequest: user data
end
SmartRequest->>Client: Complete request with auth context
Note over SmartRequest,GlobalDB: Performance improvement: tenancy fetched<br/>in initial bundle instead of separate call
3 files reviewed, 1 comment
There was a problem hiding this 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
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (3)
apps/backend/src/app/api/latest/users/crud.tsx(3 hunks)apps/backend/src/lib/tenancies.tsx(5 hunks)apps/backend/src/route-handlers/smart-request.tsx(3 hunks)
🧰 Additional context used
🧬 Code graph analysis (3)
apps/backend/src/lib/tenancies.tsx (6)
apps/backend/src/prisma-client.tsx (4)
rawQuery(304-307)globalPrismaClient(37-37)RawQuery(230-234)RawQuery(236-302)packages/stack-shared/src/utils/errors.tsx (1)
StackAssertionError(69-85)apps/backend/src/lib/projects.tsx (1)
getProjectQuery(41-69)apps/backend/src/lib/config.tsx (1)
getRenderedOrganizationConfigQuery(51-56)packages/stack-shared/src/utils/env.tsx (1)
getNodeEnvironment(65-67)packages/stack-shared/src/utils/objects.tsx (1)
deepPlainEquals(29-65)
apps/backend/src/app/api/latest/users/crud.tsx (3)
apps/backend/src/lib/tenancies.tsx (1)
Tenancy(53-53)apps/backend/src/prisma-client.tsx (4)
rawQuery(304-307)globalPrismaClient(37-37)getPrismaClientForSourceOfTruth(91-112)getPrismaSchemaForSourceOfTruth(114-134)apps/backend/src/lib/config.tsx (1)
getRenderedProjectConfigQuery(30-35)
apps/backend/src/route-handlers/smart-request.tsx (3)
apps/backend/src/lib/tenancies.tsx (1)
getSoleTenancyFromProjectBranchQuery(78-80)apps/backend/src/prisma-client.tsx (2)
rawQueryAll(309-313)globalPrismaClient(37-37)packages/stack-shared/src/known-errors.tsx (2)
KnownErrors(1570-1572)KnownErrors(1574-1695)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (13)
- GitHub Check: CodeQL analysis (javascript-typescript)
- GitHub Check: Vercel Agent Review
- GitHub Check: lint_and_build (latest)
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test
- GitHub Check: docker
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: all-good
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: setup-tests
- GitHub Check: build (22.x)
- GitHub Check: Security Check
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (1)
apps/backend/src/lib/tenancies.tsx (1)
180-218: Excellent validation approach; consider case normalization.The development-mode cross-validation against the legacy Prisma path is a robust migration pattern. The logic on line 185 is correct (runs validation when environment does NOT include "prod").
For added robustness, consider normalizing the case to handle edge cases where
NODE_ENVmight be capitalized:- if (!getNodeEnvironment().includes("prod")) { + if (!getNodeEnvironment().toLowerCase().includes("prod")) {This ensures the validation skips in production regardless of case (e.g., "PRODUCTION", "Production").
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
apps/backend/src/lib/tenancies.tsx(5 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
apps/backend/src/lib/tenancies.tsx (6)
apps/backend/src/prisma-client.tsx (4)
rawQuery(304-307)globalPrismaClient(37-37)RawQuery(230-234)RawQuery(236-302)packages/stack-shared/src/utils/errors.tsx (1)
StackAssertionError(69-85)apps/backend/src/lib/projects.tsx (1)
getProjectQuery(41-69)apps/backend/src/lib/config.tsx (1)
getRenderedOrganizationConfigQuery(51-56)packages/stack-shared/src/utils/env.tsx (1)
getNodeEnvironment(65-67)packages/stack-shared/src/utils/objects.tsx (1)
deepPlainEquals(29-65)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (12)
- GitHub Check: build (22.x)
- GitHub Check: lint_and_build (latest)
- GitHub Check: build (22.x)
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: docker
- GitHub Check: all-good
- GitHub Check: setup-tests
- GitHub Check: Vercel Agent Review
- GitHub Check: Security Check
🔇 Additional comments (7)
apps/backend/src/lib/tenancies.tsx (7)
1-8: LGTM: Imports support the new RawQuery migration.All new imports are necessary and correctly sourced for the RawQuery-based tenancy retrieval and development-mode validation.
21-51: LGTM: Legacy implementation preserved for validation.Keeping the old Prisma-based implementation as
tenancyPrismaToCrudUnusedfor development-mode cross-validation is a solid migration safety pattern.
53-53: LGTM: Type definition ensures consistency.Deriving the
Tenancytype from the legacy implementation maintains type stability during the migration.
59-72: LGTM: Clean refactor to RawQuery.The function now correctly delegates to
getSoleTenancyFromProjectBranchQuerywhile preserving the existing overloads and error handling.
74-80: LGTM: Query helper correctly implemented.The new
getSoleTenancyFromProjectBranchQueryproperly returns aRawQueryand delegates togetTenancyFromProjectQuerywith the sole-tenancy assumption (null organizationId).
82-91: LGTM: Simplified to use unified tenancy retrieval.Refactoring
getTenancyto delegate togetTenancyFromProjecteliminates duplication and ensures all tenancy retrieval flows through the new RawQuery path.
93-171: LGTM: Well-structured RawQuery implementation.The new
getTenancyFromProjectQueryeffectively combines tenancy, project, and config fetching in a single query batch viaRawQuery.all, improving performance. The SQL is properly parameterized, the validation logic forhasNoOrganizationis correctly duplicated from the legacy path, and error handling is comprehensive.
Refactor to await tenancyResultPromise separately and check for null.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (2)
apps/backend/src/lib/tenancies.tsx (2)
78-80: Remove unused parameter or document its purpose.The
returnNullIfNotFoundparameter is declared in the signature but never used in the function body. SincegetTenancyFromProjectQueryalways returns a nullable result, this parameter doesn't affect the query behavior and only serves as a type-level constraint.Consider removing the parameter for clarity:
-export function getSoleTenancyFromProjectBranchQuery(project: Omit<ProjectsCrud["Admin"]["Read"], "config"> | string, branchId: string, returnNullIfNotFound: true): RawQuery<Promise<Tenancy | null>> { +export function getSoleTenancyFromProjectBranchQuery(project: Omit<ProjectsCrud["Admin"]["Read"], "config"> | string, branchId: string): RawQuery<Promise<Tenancy | null>> { return getTenancyFromProjectQuery(typeof project === 'string' ? project : project.id, branchId, null); }And update the caller on line 66:
- const res = await rawQuery(globalPrismaClient, getSoleTenancyFromProjectBranchQuery(projectOrId, branchId, true)); + const res = await rawQuery(globalPrismaClient, getSoleTenancyFromProjectBranchQuery(projectOrId, branchId));
187-187: Make environment check case-insensitive.While the logic is now correct (single negation), the environment check should be case-insensitive for robustness, as
NODE_ENVcould theoretically be uppercase.Apply this diff:
- if (!getNodeEnvironment().includes("prod")) { + if (!getNodeEnvironment().toLowerCase().includes("prod")) {
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
apps/backend/src/lib/tenancies.tsx(5 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
apps/backend/src/lib/tenancies.tsx (6)
apps/backend/src/prisma-client.tsx (4)
rawQuery(304-307)globalPrismaClient(37-37)RawQuery(230-234)RawQuery(236-302)packages/stack-shared/src/utils/errors.tsx (1)
StackAssertionError(69-85)apps/backend/src/lib/projects.tsx (1)
getProjectQuery(41-69)apps/backend/src/lib/config.tsx (1)
getRenderedOrganizationConfigQuery(51-56)packages/stack-shared/src/utils/env.tsx (1)
getNodeEnvironment(65-67)packages/stack-shared/src/utils/objects.tsx (1)
deepPlainEquals(29-65)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (12)
- GitHub Check: Vercel Agent Review
- GitHub Check: build (22.x)
- GitHub Check: setup-tests
- GitHub Check: build (22.x)
- GitHub Check: docker
- GitHub Check: all-good
- GitHub Check: restart-dev-and-test
- GitHub Check: build (22.x)
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: lint_and_build (latest)
- GitHub Check: Security Check
🔇 Additional comments (6)
apps/backend/src/lib/tenancies.tsx (6)
1-8: LGTM!The new imports correctly support the RawQuery-based implementation and development-mode validation logic.
21-51: LGTM!The deprecated function is correctly preserved for development-mode validation. The validation logic duplication with the new implementation (lines 147-159) is intentional to ensure correctness of the migration.
93-173: LGTM!The new RawQuery-based implementation correctly:
- Combines tenancy, project, and config queries efficiently using
RawQuery.all- Handles the two organizationId cases (null vs non-null) with appropriate SQL
- Validates cardinality and data consistency
- Returns early when no tenancy is found
188-217: LGTM! Development-mode validation is thorough.The cross-check between old and new implementations provides strong confidence in the migration. The strict
deepPlainEqualscomparison (withoutignoreUndefinedValues) will catch any structural differences.Note: This validation doubles database queries in development environments. Once confidence is established, consider removing or feature-flagging this check to improve development performance.
82-91: LGTM!The function correctly delegates to the updated
getTenancyFromProject, maintaining the public API while benefiting from the new RawQuery-based implementation.
65-72: LGTM!The function correctly uses the new RawQuery-based
getSoleTenancyFromProjectBranchQuerywhile maintaining the same public behavior and error handling.
|
@claude fix this FAIL |@stackframe/e2e-tests| tests/backend/endpoints/api/v1/auth/oauth/authorize.test.ts > should not redirect the user to the OAuth provider with the right arguments when forcing a branch id that does not exist This is likely an error in Stack. Please make sure you are running the newest version and report it. |
|
@claude fix this FAIL |@stackframe/e2e-tests| tests/backend/endpoints/api/v1/auth/oauth/authorize.test.ts > should not redirect the user to the OAuth provider with the right arguments when forcing a branch id that does not exist This is likely an error in Stack. Please make sure you are running the newest version and report it. fix it in tenancies.tsx |
There was a problem hiding this 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
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (6)
apps/backend/src/lib/config.tsx(1 hunks)apps/backend/src/lib/tenancies.tsx(5 hunks)apps/backend/src/route-handlers/smart-request.tsx(3 hunks)apps/e2e/tests/backend/backend-helpers.ts(1 hunks)apps/e2e/tests/backend/endpoints/api/v1/index.test.ts(1 hunks)apps/e2e/tests/backend/endpoints/api/v1/projects.test.ts(1 hunks)
🧰 Additional context used
🧬 Code graph analysis (5)
apps/e2e/tests/backend/endpoints/api/v1/projects.test.ts (1)
apps/e2e/tests/helpers.ts (1)
it(12-12)
apps/backend/src/route-handlers/smart-request.tsx (4)
apps/backend/src/lib/tenancies.tsx (1)
getSoleTenancyFromProjectBranchQuery(78-80)apps/backend/src/lib/config.tsx (1)
getRenderedEnvironmentConfigQuery(44-49)apps/backend/src/prisma-client.tsx (2)
rawQueryAll(309-313)globalPrismaClient(37-37)apps/backend/src/app/api/latest/users/crud.tsx (1)
getUser(391-408)
apps/e2e/tests/backend/endpoints/api/v1/index.test.ts (2)
apps/e2e/tests/backend/backend-helpers.ts (3)
backendContext(35-57)niceBackendFetch(109-173)InternalProjectKeys(77-82)apps/e2e/tests/helpers.ts (1)
it(12-12)
apps/backend/src/lib/tenancies.tsx (6)
apps/backend/src/prisma-client.tsx (4)
rawQuery(304-307)globalPrismaClient(37-37)RawQuery(230-234)RawQuery(236-302)packages/stack-shared/src/utils/errors.tsx (1)
StackAssertionError(69-85)apps/backend/src/lib/projects.tsx (1)
getProjectQuery(41-69)apps/backend/src/lib/config.tsx (1)
getRenderedOrganizationConfigQuery(51-56)packages/stack-shared/src/utils/env.tsx (1)
getNodeEnvironment(65-67)packages/stack-shared/src/utils/objects.tsx (1)
deepPlainEquals(29-65)
apps/backend/src/lib/config.tsx (4)
packages/stack-shared/src/config/schema.ts (2)
migrateConfigOverride(271-347)BranchConfigOverride(1025-1025)apps/backend/src/prisma-client.tsx (2)
RawQuery(230-234)RawQuery(236-302)apps/backend/src/lib/tenancies.tsx (1)
DEFAULT_BRANCH_ID(19-19)packages/stack-shared/src/utils/errors.tsx (1)
StackAssertionError(69-85)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (12)
- GitHub Check: Vercel Agent Review
- GitHub Check: all-good
- GitHub Check: build (22.x)
- GitHub Check: restart-dev-and-test-with-custom-base-port
- GitHub Check: check_prisma_migrations (22.x)
- GitHub Check: build (22.x)
- GitHub Check: docker
- GitHub Check: lint_and_build (latest)
- GitHub Check: restart-dev-and-test
- GitHub Check: build (22.x)
- GitHub Check: setup-tests
- GitHub Check: Security Check
| if (options.branchId !== DEFAULT_BRANCH_ID) { | ||
| throw new StackAssertionError('getBranchConfigOverrideQuery is not implemented for branches other than the default one'); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Invalid branch still returns 500
This guard still throws a StackAssertionError whenever branchId !== DEFAULT_BRANCH_ID, so the bundled environmentRenderedConfig query in parseAuth explodes before the tenancy lookup can emit KnownErrors.BranchDoesNotExist. Repro: send any request with x-stack-project-id set to a real project and x-stack-branch-id: invalid-branch; you still get the old “Not implemented” 500 from here, so the new e2e test will keep failing. Please drop the throw (return the empty override instead) so the tenancy logic can surface the intended 400.
- if (options.branchId !== DEFAULT_BRANCH_ID) {
- throw new StackAssertionError('getBranchConfigOverrideQuery is not implemented for branches other than the default one');
- }
return migrateConfigOverride("branch", {});📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| if (options.branchId !== DEFAULT_BRANCH_ID) { | |
| throw new StackAssertionError('getBranchConfigOverrideQuery is not implemented for branches other than the default one'); | |
| } | |
| return migrateConfigOverride("branch", {}); |
🤖 Prompt for AI Agents
In apps/backend/src/lib/config.tsx around lines 146 to 148, the guard currently
throws a StackAssertionError when options.branchId !== DEFAULT_BRANCH_ID which
causes a 500 instead of allowing tenancy lookup to surface
KnownErrors.BranchDoesNotExist; remove the throw and return an empty override
(e.g., an empty config override object) in that branch so the function succeeds
and downstream tenancy logic can emit the intended 400.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Greptile Overview
Greptile Summary
Performance optimization that reduces database roundtrips for user endpoints by resolving tenancy earlier and bundling queries.
Key Changes:
- Refactored
getTenancyFromProjectto useRawQueryfor query composition and parallel execution - Moved tenancy resolution into bundled queries in
smart-request.tsx, fetching project, tenancy, config, and user data in parallel instead of sequentially - Updated
getUserto accept tenancy directly, eliminating redundant config lookups by reusing already-fetched data - Changed config lookup from environment-level to project-level for
sourceOfTruthfield, which is valid sincesourceOfTruthis defined at project level - Added development-mode validation that compares new RawQuery implementation against old Prisma implementation to ensure correctness
- Improved error handling for missing project configs to gracefully handle null results
- Added E2E tests for invalid project IDs and branch IDs
Confidence Score: 4/5
- Safe to merge with one minor logic issue already flagged in previous comments
- The refactoring is well-structured with strong validation in development mode. The bundled query approach is sound, and the change from environment to project config for
sourceOfTruthis valid. However, there's one logic issue (inverted condition on line 187) that was already caught in previous review. - Pay attention to
apps/backend/src/lib/tenancies.tsx:187- the validation condition logic was flagged in previous comments
Important Files Changed
File Analysis
| Filename | Score | Overview |
|---|---|---|
| apps/backend/src/lib/tenancies.tsx | 4/5 | Refactored tenancy queries to use RawQuery for better performance, with development-mode validation comparing old and new implementations |
| apps/backend/src/route-handlers/smart-request.tsx | 5/5 | Moved tenancy resolution to bundled queries for parallel execution, improving request handling performance |
| apps/backend/src/app/api/latest/users/crud.tsx | 5/5 | Changed getUser to accept tenancy directly, avoiding unnecessary database lookups by using config from already-fetched tenancy |
| apps/backend/src/lib/config.tsx | 5/5 | Improved error handling for missing project configs and moved branch validation check to postProcess function |
Sequence Diagram
sequenceDiagram
participant Client
participant SmartRequest as SmartRequest Handler
participant RawQueryAll
participant DB as Global DB
participant TenancyQuery as Tenancy Query
participant ProjectQuery as Project Query
participant ConfigQuery as Config Query
participant UserQuery as User Query (optimistic)
participant SourceOfTruthDB as Source-of-Truth DB
Client->>SmartRequest: HTTP Request (users/[user_id])
Note over SmartRequest: OLD: Sequential fetching<br/>project → tenancy → config → user
Note over SmartRequest: NEW: Parallel fetching with bundled queries
SmartRequest->>RawQueryAll: Bundle queries in parallel
par Parallel Query Execution
RawQueryAll->>ProjectQuery: getProjectQuery(projectId)
ProjectQuery->>DB: SELECT Project
DB-->>ProjectQuery: Project data
RawQueryAll->>TenancyQuery: getSoleTenancyFromProjectBranchQuery()
TenancyQuery->>DB: SELECT Tenancy + Project + Config
DB-->>TenancyQuery: Tenancy with config
RawQueryAll->>ConfigQuery: getRenderedEnvironmentConfigQuery()
ConfigQuery->>DB: SELECT Config overrides
DB-->>ConfigQuery: Rendered config
RawQueryAll->>UserQuery: getUserIfOnGlobalPrismaClient()
UserQuery->>DB: SELECT User (optimistic)
DB-->>UserQuery: User data or null
end
RawQueryAll-->>SmartRequest: All query results
Note over SmartRequest: Validate project & tenancy exist
alt Source of Truth is Hosted (Global DB)
SmartRequest->>SmartRequest: Use optimistically fetched user
else Source of Truth is External
SmartRequest->>SourceOfTruthDB: getUser(projectId, branchId)
SourceOfTruthDB-->>SmartRequest: User from external DB
end
SmartRequest->>Client: Response with user data
Note over SmartRequest,Client: Performance improvement: 1 roundtrip instead of multiple sequential queries
7 files reviewed, no comments
Summary by CodeRabbit
Refactor
Bug Fixes
Tests