feat: Initial implementation of custom auth implementation#550
Conversation
…replacement patterns
|
The latest updates on your projects. Learn more about Vercel for Git ↗︎
|
ENG-211 Create new local auth plugin
We use a local auth system that does not rely on Auth0 QA Notes:
|
🦋 Changeset detectedLatest commit: f4c5fed The changes in this PR will be included in the next version bump. This PR includes changesets to release 12 packages
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
WalkthroughThis change set introduces a major refactor and feature expansion across multiple packages and plugins. It implements a new, extensible plugin configuration and migration system, restructures authentication and storage plugin schemas and UI, and adds placeholder authentication generators for test and development. The update also modularizes CSS utilities, improves TypeScript project references, and enhances code style, validation, and error handling throughout the codebase. Changes
Changes (continued)
Sequence Diagram(s)Plugin Configuration and Migration FlowsequenceDiagram
participant User
participant WebUI as ProjectBuilder Web UI
participant Server as ProjectBuilder Server
participant Lib as project-builder-lib
participant Plugin as PluginImplementationStore
User->>WebUI: Edit plugin config (e.g., auth/storage)
WebUI->>Server: Save project definition
Server->>Lib: runSchemaMigrations(definition)
Lib->>Plugin: createPluginImplementationStore(pluginStore, definition)
Lib->>Plugin: runPluginMigrations(definition, pluginImplementationStore)
Plugin->>Lib: Apply migrations to plugin configs
Lib->>Server: Return migrated definition
Server->>WebUI: Confirm save/refresh UI
Fastify Auth Module Generation (Simplified)sequenceDiagram
participant Generator as authModuleGenerator
participant Prisma as Prisma ORM
participant Fastify as Fastify Server
Generator->>Prisma: Generate user/session models
Generator->>Fastify: Generate user session service (CookieUserSessionService)
Fastify->>Prisma: Store/retrieve session info
Fastify->>Fastify: Set/clear session cookies, verify session via JWT/cookie
Placeholder Auth Hooks/Service Generation (Test/Dev)sequenceDiagram
participant Generator as placeholderAuthServiceGenerator/placeholderAuthHooksGenerator
participant Project as Project App
Generator->>Project: Generate placeholder service/hooks files
Project->>User: Throws "Not implemented" if called in runtime
Modular CSS UtilitiessequenceDiagram
participant UI as UI Components
participant Plugin as Plugin (auth/storage)
participant App as Application
UI->>UI: Export utilities.css with surface/typography classes
Plugin->>Plugin: Import utilities.css, apply prefix (auth:/storage:)
App->>Plugin: Use plugin UI, styles are scoped via prefix
🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
SupportNeed help? Create a ticket on our support page for assistance with any issues or questions. Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
Documentation and Community
|
|
Review the following changes in direct dependencies. Learn more about Socket for GitHub.
|
|
Warning Review the following alerts detected in dependencies. According to your organization's Security Policy, it is recommended to resolve "Warn" alerts. Learn more about Socket for GitHub.
|
There was a problem hiding this comment.
Actionable comments posted: 41
🔭 Outside diff range comments (1)
packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
295-300: 💡 Verification agent🧩 Analysis chain
featureRefin diff result may become stale when an existing model’s feature changes
createModelMergerResultcopiescurrentModel.featureRefinto the diff result even ifdesired.featureRefdiffers.
That meansapplyModelMergerResultInPlacewill recreate a new model with the oldfeatureRef, silently dropping the intended change.Consider including
featureRefinmodelMergerDefinitionDiffConfig(e.g. viaDefinitionDiffReplacementField) or copyingdesired.featureRefinto the result object whencurrentexists but the feature is updated.
🏁 Script executed:
#!/bin/bash # Show the definition of createModelMergerResult around the return statement sed -n '260,350p' packages/project-builder-lib/src/tools/model-merger/model-merger.ts # Check if featureRef is part of the diff config rg -n 'modelMergerDefinitionDiffConfig' -A 10 packages/project-builder-lib/src/tools/model-merger/model-merger.ts # Look for any usage of DefinitionDiffReplacementField rg -n 'DefinitionDiffReplacementField' -n packagesLength of output: 5922
Capture featureRef changes in the model merger diff
The current implementation of
createModelMergerResultalways copiescurrentModel.featureRefinto the result, even whendesired.featureRefhas changed. This means that after applying the diff, the model’s featureRef will remain stale.To fix this, we should include
featureRefin the diff config so that any change to it is tracked and applied.• File:
packages/project-builder-lib/src/tools/model-merger/model-merger.ts
– Around line 78, add a replacement field forfeatureRefinmodelMergerDefinitionDiffConfig.
– Remove manual copying of the oldfeatureRefin the return statement and rely on the diff to update it.Suggested diff:
--- a/packages/project-builder-lib/src/tools/model-merger/model-merger.ts +++ b/packages/project-builder-lib/src/tools/model-merger/model-merger.ts @@ export const modelMergerDefinitionDiffConfig = createDefinitionDiffConfig<ModelMergerModelInput>({ 'model.fields': new DefinitionDiffKeyedArrayField('fields', (f) => f.name), 'model.relations': new DefinitionDiffKeyedArrayField('relations', (r) => r.name), 'model.uniqueConstraints': new DefinitionDiffKeyedArrayField( 'uniqueConstraints', (c) => getUniqueConstraintKey(c), ), + // Track featureRef changes + 'model.featureRef': new DefinitionDiffReplacementField('featureRef'), });--- a/packages/project-builder-lib/src/tools/model-merger/model-merger.ts +++ b/packages/project-builder-lib/src/tools/model-merger/model-merger.ts @@ export function createModelMergerResult( - return { - isNewModel: !current, - id: currentModel.id, - name: currentModel.name, - featureRef: currentModel.featureRef, - changes: diff, - }; + // featureRef will now be part of diff.changes if it has changed + return { + isNewModel: !current, + id: currentModel.id, + name: currentModel.name, + featureRef: current ? diff['model.featureRef'] ?? currentModel.featureRef : currentModel.featureRef, + changes: diff, + };This ensures any update to
desired.featureRefis detected and applied rather than silently dropped.
♻️ Duplicate comments (1)
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts (1)
1-1: Same remark as earlier – avoid project-wide@ts-nocheckSee previous comment in JWT service. Keeping type-checking on templates drastically cuts integration bugs.
🧹 Nitpick comments (31)
.gitignore (1)
101-102: Approve ignore entry for local Claude settings
The addition of.claude/settings.local.jsonto.gitignoreis appropriate to prevent leaking local configuration files. Consider whether you’d also like to ignore the entire.claude/directory (e.g., adding.claude/) if other environment-specific files might appear there in the future.packages/fastify-generators/src/generators/auth/auth-context/templates/utils/auth-context.utils.ts (1)
24-24: Simplify user session check
The updated guardif (!session || session.type !== 'user')removes the unnecessary type assertion and correctly enforces that only user sessions can calluserIdOrThrow.Consider removing the
// @ts-nocheckat the top of the file now that type safety is explicit:-// @ts-nocheckpackages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useSession.ts (2)
1-1: Consider removing @ts-nocheck directive.The
@ts-nocheckdirective disables TypeScript checking entirely for this file. Since this is a well-typed function, consider removing this directive to maintain type safety.-// @ts-nocheck
3-8: Improve placeholder implementation for better developer experience.While throwing an error is appropriate for placeholder code, consider providing a more helpful implementation that indicates this is intentionally unimplemented.
export function useSession(): { isAuthenticated: boolean; loading: boolean; } { - throw new Error('Not implemented'); + throw new Error('useSession is a placeholder - implement authentication logic here'); + // TODO: Implement actual session management + // return { isAuthenticated: false, loading: false }; }plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session.queries.ts (1)
1-1: Consider removing @ts-nocheck directive.The
@ts-nocheckdirective suppresses all TypeScript checking for this file. While this might be necessary during code generation, consider whether type checking can be enabled to catch potential issues.If TypeScript errors are due to template variables, consider using more specific suppressions or ensuring the generated code will be properly typed.
packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useCurrentUser.ts (1)
3-9: Add TODO comment and consider improving return types.The placeholder implementation is appropriate, but consider adding a TODO comment for clarity and potentially improving the return types.
+// TODO: Implement actual user authentication logic export function useCurrentUser(): { - user: any; + user: any; // TODO: Replace with proper User type loading: boolean; error: Error | undefined; } { throw new Error('Not implemented'); }packages/sync/src/output/write-generator-output.ts (1)
231-237: Enhanced error diagnostics for formatter failures.The addition of specific handling for
FormatterErrornested withinPrepareGeneratorFilesErrorwill improve debugging by logging the file contents that failed formatting.Consider adding the file path to the log for even better diagnostics:
if ( error instanceof PrepareGeneratorFilesError && error.causes[0].cause instanceof FormatterError ) { const formatterError = error.causes[0].cause; - logger.info(`File Dump:\n${formatterError.fileContents}`); + logger.info(`File Dump for ${formatterError.projectRelativePath}:\n${formatterError.fileContents}`); }plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/management.ts (1)
6-22: Singleton pattern implemented correctly with proper caching.The caching mechanism for the
ManagementClientis well-implemented, preventing unnecessary client instantiations and improving performance.Consider adding error handling for client instantiation:
export function getAuthManagementClient(): ManagementClient { if (cachedClient) { return cachedClient; } + try { const client = new ManagementClient({ domain: config.AUTH_TENANT_DOMAIN, clientId: config.AUTH_CLIENT_ID, clientSecret: config.AUTH_CLIENT_SECRET, }); cachedClient = client; return client; + } catch (error) { + throw new Error(`Failed to initialize Auth0 Management Client: ${error.message}`); + } }plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session-payload.object-type.ts (1)
14-22: Prisma field resolver implemented correctly with proper error handling.The user field resolver correctly:
- Uses
findUniqueOrThrowwhich ensures data integrity by throwing if the user doesn't exist- Properly spreads the query object for Prisma field selection
- Follows Pothos prismaField patterns
Consider adding more descriptive error handling:
user: t.prismaField({ type: TPL_USER_OBJECT_TYPE, resolve: async (query, root) => - TPL_PRISMA_USER.findUniqueOrThrow({ + TPL_PRISMA_USER.findUniqueOrThrow({ where: { id: root.userId }, ...query, - }), + }).catch((error) => { + throw new Error(`User not found for session: ${root.userId}`); + }), }),plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts (1)
7-16: Consider improving type safety in the migration function.The migration logic correctly restructures the configuration from flat
userAccountModelRefto nestedmodelRefs.user. However, the type assertion on line 8 could be improved for better type safety.Consider using a more defensive approach to handle potentially missing properties:
migrate: (config) => { - const typedConfig = config as { userAccountModelRef: string }; + const typedConfig = config as { userAccountModelRef?: string }; + + if (!typedConfig.userAccountModelRef) { + return config; + } + return { ...typedConfig, userAccountModelRef: undefined, modelRefs: { user: typedConfig.userAccountModelRef, }, }; },This ensures the migration handles cases where the expected property might not exist, making it more robust.
plugins/baseplate-plugin-auth/src/roles/constants.ts (1)
5-21: Avoid accidental mutation & ensure compile-time safety for default roles
Consider freezing theAUTH_DEFAULT_ROLESarray (or declaring itas const) so that neither the array nor its objects can be mutated elsewhere. This protects the canonical definition of built-in roles and gives the compiler literal-type information that can be handy in downstream schema checks.plugins/baseplate-plugin-auth/src/auth/core/common.ts (1)
24-28: Consider adding runtime validation for type casting.The code uses type casting
as AuthPluginDefinitionwithout runtime validation. WhilePluginUtils.configByIdOrThrowhandles the existence check, consider adding schema validation to ensure the config matches the expected type.const pluginConfig = PluginUtils.configByIdOrThrow( definition, pluginId, -) as AuthPluginDefinition; +); +// Consider adding runtime validation here +if (!authPluginDefinitionSchema.safeParse(pluginConfig).success) { + throw new Error(`Invalid auth plugin configuration for ${pluginId}`); +} +const validatedConfig = pluginConfig as AuthPluginDefinition;Also applies to: 31-35
plugins/baseplate-plugin-auth/src/auth/core/components/role-editor-form.tsx (1)
18-20: Consider memoizing the role check for performance.The
isFixedRolefunction is called multiple times for each role during renders, which could be optimized.+import { useMemo } from 'react'; +function useFixedRoleChecker() { + return useMemo(() => { + const fixedRoleNames = new Set(AUTH_DEFAULT_ROLES.map(role => role.name)); + return (name: string) => fixedRoleNames.has(name); + }, []); +} function RoleEditorForm({ className, control }: Props): React.JSX.Element { + const isFixedRole = useFixedRoleChecker(); const { fields, append, remove } = useFieldArray({This avoids repeated array iterations and provides better performance for large role lists.
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.constants.ts (2)
19-19: Remove unnecessary type assertion.The
as numbertype assertion is unnecessary since the literal0is already typed as a number.-export const USER_SESSION_MAX_LIFETIME_SEC = 0 as number; +export const USER_SESSION_MAX_LIFETIME_SEC = 0;
6-19: Consider using const assertions and better organization.The constants could benefit from const assertions for better type safety and potentially grouping them into a configuration object.
-export const USER_SESSION_DURATION_SEC = 14 * 24 * 60 * 60; // 14 days -export const USER_SESSION_RENEWAL_THRESHOLD_SEC = 1 * 24 * 60 * 60; // 1 day -export const USER_SESSION_MAX_LIFETIME_SEC = 0; +export const USER_SESSION_CONFIG = { + /** + * Defines the duration of a user session before it expires, in seconds. + */ + DURATION_SEC: 14 * 24 * 60 * 60, // 14 days + /** + * Defines the duration after which a user session should be renewed, in seconds. + */ + RENEWAL_THRESHOLD_SEC: 1 * 24 * 60 * 60, // 1 day + /** + * Sets the maximum possible lifespan of a user session, in seconds, including renewals. + * A value of 0 allows the session to persist indefinitely, provided it is renewed + * before the session expiration. + */ + MAX_LIFETIME_SEC: 0, +} as const; + +// Export individual constants for backward compatibility if needed +export const USER_SESSION_DURATION_SEC = USER_SESSION_CONFIG.DURATION_SEC; +export const USER_SESSION_RENEWAL_THRESHOLD_SEC = USER_SESSION_CONFIG.RENEWAL_THRESHOLD_SEC; +export const USER_SESSION_MAX_LIFETIME_SEC = USER_SESSION_CONFIG.MAX_LIFETIME_SEC;This provides better organization and type safety while maintaining compatibility.
packages/fastify-generators/src/generators/auth/placeholder-auth-service/templates/user-session.service.ts (1)
26-31: Improve error message for consistency.For consistency with the updated error message in the other method, consider making this error message more descriptive.
- throw new Error('Not implemented'); + throw new Error('PlaceholderSessionService.getSessionInfoFromToken: This is a placeholder implementation that needs to be replaced with actual authentication logic');packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (1)
51-55: Add error handling for missing plugin configuration service.While the
getPluginSpecmethod throws an error if the implementation is not found, consider adding more context about which plugin caused the issue for better debugging.const pluginConfigService = pluginImplementationStore.getPluginSpec(pluginConfigSpec); const lastMigrationVersion = pluginConfigService.getLastMigrationVersion( plugin.id, );Consider wrapping this in a try-catch to provide more context:
+ try { const pluginConfigService = pluginImplementationStore.getPluginSpec(pluginConfigSpec); const lastMigrationVersion = pluginConfigService.getLastMigrationVersion( plugin.id, ); + } catch (error) { + throw new Error(`Failed to get migration version for plugin ${plugin.id}: ${error.message}`); + }plugins/baseplate-plugin-auth/src/roles/schema.ts (2)
37-55: Consider adding comments to clarify the complex transform logic.The transform function performs several important operations but could benefit from inline comments to explain the logic flow.
.transform((roles) => [ + // Merge default roles with user-defined roles, preserving user customizations ...AUTH_DEFAULT_ROLES.map((r) => { const existingRole = roles.find((role) => role.name === r.name); return existingRole ? { + // Use existing role but ensure it's marked as built-in ...existingRole, builtIn: true, } : { + // Create new default role with generated ID ...r, builtIn: true, id: authRoleEntityType.generateNewId(), }; }), + // Add user-defined roles that are not default roles // Filter out the built-in roles ...roles.filter( (r) => !AUTH_DEFAULT_ROLES.map((v) => v.name).includes(r.name), ), ]);
37-55: Consider performance optimization for large role arrays.For better performance with large role arrays, consider optimizing the filtering logic by creating a Set of default role names instead of using
includeson a mapped array.+ const defaultRoleNames = new Set(AUTH_DEFAULT_ROLES.map(r => r.name)); + .transform((roles) => [ ...AUTH_DEFAULT_ROLES.map((r) => { const existingRole = roles.find((role) => role.name === r.name); return existingRole ? { ...existingRole, builtIn: true, } : { ...r, builtIn: true, id: authRoleEntityType.generateNewId(), }; }), // Filter out the built-in roles ...roles.filter( - (r) => !AUTH_DEFAULT_ROLES.map((v) => v.name).includes(r.name), + (r) => !defaultRoleNames.has(r.name), ), ]);plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx (2)
40-64: Consider memoization optimization for default valuesThe
useMemodependency array includespluginMetadata?.configimplicitly through the condition check, but it's not explicitly listed. This could potentially cause unnecessary re-computations.Consider making the dependency more explicit:
- }, [definition, pluginMetadata?.config]); + }, [definition, pluginMetadata]);Or if you specifically need to track the config:
- }, [definition, pluginMetadata?.config]); + }, [definition, pluginMetadata?.config]);The current implementation works but could be clearer about what triggers recomputation.
121-121: Consider extracting form CSS class to a constantThe inline CSS class string could be extracted to improve maintainability and reusability.
Consider extracting to a constant:
+ const FORM_CLASSES = 'flex flex-col gap-4'; + return ( - <form onSubmit={onSubmit} className={cn('flex flex-col gap-4')}> + <form onSubmit={onSubmit} className={cn(FORM_CLASSES)}>plugins/baseplate-plugin-auth/src/auth/core/schema/plugin-definition.ts (1)
10-34: Consider enforcing strict schemas & deduplicatingmodelRefdefinition
z.object()without.strict()will silently allow unknown keys.
For configuration objects that will be checked-in and migrated, failing fast on typos usually saves time.In addition, the four
modelRefs.*fields share the same definition. You can make the schema more compact & less error-prone by extracting a reusable helper.- export const authPluginDefinitionSchema = z.object({ - modelRefs: z.object({ - user: zRef(z.string().min(1), { type: modelEntityType, onDelete: 'RESTRICT' }), - userAccount: zRef(z.string().min(1), { type: modelEntityType, onDelete: 'RESTRICT' }), - userRole: zRef(z.string().min(1), { type: modelEntityType, onDelete: 'RESTRICT' }), - userSession: zRef(z.string().min(1), { type: modelEntityType, onDelete: 'RESTRICT' }), - }), +const modelRefSchema = zRef(z.string().min(1), { + type: modelEntityType, + onDelete: 'RESTRICT', +}); + +export const authPluginDefinitionSchema = z + .object({ + modelRefs: z + .object({ + user: modelRefSchema, + userAccount: modelRefSchema, + userRole: modelRefSchema, + userSession: modelRefSchema, + }) + .strict(),…and finally call
.strict()on the outer object as well:roles: authRolesSchema, -}); +}).strict();This keeps the config surface tight and removes duplication.
plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx (1)
53-57: Duplicate built-in role objects are being injected
defaultValues.rolesclonesAUTH_DEFAULT_ROLESand assigns fresh IDs.
authRolesSchemalater merges another copy of the built-in roles, so the built-ins appear twice in the editor until the form is submitted (after which they’re de-duplicated in the transform).This can confuse users (“why do I see Admin twice?”) and makes validation noise. Consider initialising
roleswith an empty list and letting the schema inject the built-ins:- roles: AUTH_DEFAULT_ROLES.map((r) => ({ - ...r, - id: authRoleEntityType.generateNewId(), - })), + roles: [],plugins/baseplate-plugin-auth/src/auth/core/schema/models.ts (1)
72-74: Sensitive secret is stored as plain string
providerSecretis meant to hold OAuth / Open-ID secrets. Storing them as a
plainstringsignals they will be persisted unhashed. Consider:
- storing only a salted hash of the secret, or
- encrypting the column at-rest (e.g. pgcrypto / kms).
Documenting the expectation in the model would prevent accidental leaks later.
[security]plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts (1)
90-97: Mutatingreq.headers.authorizationmay clobber an existing header
getSessionInfoFromTokenblindly overridesreq.headers.authorization.
If upstream code has already populated the header, that value is lost.Consider copying the original value, restoring it afterwards, or, better, call
this.getSessionInfoFromRequeston a cloned request (Fastify’sreq.clone()), if available.packages/project-builder-lib/src/schema/plugins/definition.ts (1)
23-41: Potential mismatch whenpluginIdis not registeredIf
plugins.getPluginSpec(pluginConfigSpec).getSchema(pluginId)returnsundefinedthe code falls back tobasePluginSchema, but parses were already executed withbasePluginSchema.parse(data).This means an unrecognised plugin passes validation even if it accidentally carries a
configthat should be rejected.Consider:
- Throwing a descriptive zod error when
configSchemais missing for the suppliedpluginId.- Alternatively, keep the fallback but strip the
configkey so unknown configs do not silently drift into the definition.plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts (2)
33-39:securecookie flag should derive from actual request, not build-time env
secure: config.APP_ENVIRONMENT !== 'development'means cookies are always secure in staging/production even when accessed over plain HTTP during local reverse-proxy setups (e.g. docker-compose onlocalhost).
Conversely, tests running in CI withNODE_ENV=testbut behind HTTPS would produce non-secure cookies.Better: decide per-request:
secure: req.protocol === 'https',or expose a helper that introspects
x-forwarded-proto.
220-224: Duplicate roles are possible – consider de-duping
[...DEFAULT_USER_ROLES, ...user.roles.map(r => r.role)]may include"user"twice.
A quickArray.from(new Set(…))prevents downstream ACL checks from iterating duplicates.CLAUDE.md (2)
20-24: Import-sorting rule conflicts with the “use absolute paths” ruleYou ask contributors to sort imports by group and to always use absolute @src paths.
ESLint import-order plugins normally group “absolute” separately from “internal”. Please clarify which grouping takes precedence to avoid back-and-forth in reviews.
165-170: kebab-case vs PascalCase files – static analysis tooling neededStating “Use kebab-case for file names” is great, but the repo already contains many
PascalCase.tsandcamelCase.tsfiles (e.g. generators).
Consider adding an ESLintfilename-rulesor a CI script so new contributors receive immediate feedback instead of learning during reviews.packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
150-152: Return type ofattachIdsToModelMergerModelInputis misleading and hides theidfield
The function returnsPick<ModelConfigInput, keyof ModelMergerModelInput>which excludes the top-levelid.
Call-sites later assume only the nested IDs are required, so this currently compiles, but it conveys that the returned object exactly matchesModelConfigInputproperties intersected with the input, which is confusing.Two alternatives:
- Return
ModelMergerModelInput(IDs are only added to nested entities), or- Define an explicit helper type (
type ModelMergerModelWithIds = { … }) for clarity.Either improves readability and prevents accidental reliance on the incomplete subset.
📜 Review details
Configuration used: .coderabbit.yaml
Review profile: CHILL
Plan: Lite
⛔ Files ignored due to path filters (7)
packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ts-import-maps.tsis excluded by!**/generated/**packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ts-templates.tsis excluded by!**/generated/**packages/react-generators/src/generators/auth/placeholder-auth-hooks/generated/ts-import-maps.tsis excluded by!**/generated/**packages/react-generators/src/generators/auth/placeholder-auth-hooks/generated/ts-templates.tsis excluded by!**/generated/**plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/generated/ts-templates.tsis excluded by!**/generated/**plugins/baseplate-plugin-auth/src/auth/static/icon.svgis excluded by!**/*.svgpnpm-lock.yamlis excluded by!**/pnpm-lock.yaml
📒 Files selected for processing (136)
.changeset/eleven-meals-fly.md(1 hunks).changeset/gentle-corners-hope.md(1 hunks).changeset/smooth-flowers-lick.md(1 hunks).cursor/rules/code-style.mdc(1 hunks).cursor/rules/ui-rules.mdc(1 hunks).cursorignore(1 hunks).gitignore(1 hunks).vscode/settings.json(1 hunks)CLAUDE.md(4 hunks)knip.config.js(1 hunks)packages/core-generators/src/constants/core-packages.ts(1 hunks)packages/core-generators/src/generators/node/eslint/templates/eslint.config.js(2 hunks)packages/core-generators/src/generators/node/typescript/typescript.generator.ts(2 hunks)packages/core-generators/src/renderers/typescript/renderers/template.ts(5 hunks)packages/core-generators/src/renderers/typescript/renderers/template.unit.test.ts(1 hunks)packages/fastify-generators/src/generators/auth/auth-context/auth-context.generator.ts(3 hunks)packages/fastify-generators/src/generators/auth/auth-context/templates/types/auth-session.types.ts(1 hunks)packages/fastify-generators/src/generators/auth/auth-context/templates/utils/auth-context.utils.ts(1 hunks)packages/fastify-generators/src/generators/auth/index.ts(1 hunks)packages/fastify-generators/src/generators/auth/placeholder-auth-service/placeholder-auth-service.generator.ts(1 hunks)packages/fastify-generators/src/generators/auth/placeholder-auth-service/templates/user-session.service.ts(1 hunks)packages/fastify-generators/src/generators/vitest/prisma-vitest/prisma-vitest.generator.ts(1 hunks)packages/project-builder-lib/package.json(1 hunks)packages/project-builder-lib/src/definition/feature/feature-utils.ts(2 hunks)packages/project-builder-lib/src/definition/model/model-utils.ts(2 hunks)packages/project-builder-lib/src/definition/plugins/plugin-utils.ts(3 hunks)packages/project-builder-lib/src/migrations/index.ts(1 hunks)packages/project-builder-lib/src/migrations/migration-008-anonymous-public-role.ts(1 hunks)packages/project-builder-lib/src/parser/parser.ts(1 hunks)packages/project-builder-lib/src/plugins/index.ts(1 hunks)packages/project-builder-lib/src/plugins/migrations/index.ts(1 hunks)packages/project-builder-lib/src/plugins/migrations/run-migrations.ts(1 hunks)packages/project-builder-lib/src/plugins/spec/auth-config-spec.ts(1 hunks)packages/project-builder-lib/src/plugins/spec/config-spec.ts(2 hunks)packages/project-builder-lib/src/references/ref-builder.ts(1 hunks)packages/project-builder-lib/src/schema/apps/base.ts(1 hunks)packages/project-builder-lib/src/schema/auth/index.ts(0 hunks)packages/project-builder-lib/src/schema/features/feature.ts(1 hunks)packages/project-builder-lib/src/schema/plugins/definition.ts(1 hunks)packages/project-builder-lib/src/schema/plugins/entity-types.ts(1 hunks)packages/project-builder-lib/src/schema/plugins/index.ts(1 hunks)packages/project-builder-lib/src/schema/project-definition.ts(2 hunks)packages/project-builder-lib/src/schema/utils/validation.ts(0 hunks)packages/project-builder-lib/src/tools/model-merger/model-merger.ts(12 hunks)packages/project-builder-lib/src/tools/model-merger/model-merger.unit.test.ts(9 hunks)packages/project-builder-lib/src/utils/validations.ts(0 hunks)packages/project-builder-lib/src/web/components/ModelMergerResultAlert.tsx(1 hunks)packages/project-builder-lib/src/web/hooks/useBlockUnsavedChangesNavigate.ts(2 hunks)packages/project-builder-lib/src/web/vite-env.d.ts(1 hunks)packages/project-builder-server/src/service/builder-service.ts(1 hunks)packages/project-builder-server/src/sync/build-project.ts(4 hunks)packages/project-builder-test/src/commands/serve.ts(1 hunks)packages/project-builder-web/src/app/ProjectDefinitionProvider/ProjectDefinitionProvider.tsx(1 hunks)packages/project-builder-web/src/app/ProjectDefinitionProvider/hooks/use-schema-parser-context.ts(1 hunks)packages/project-builder-web/src/app/ProjectDefinitionProvider/services/parse-project-definition-contents.ts(2 hunks)packages/project-builder-web/src/pages/settings/project-settings.tsx(0 hunks)packages/project-builder-web/src/styles.css(1 hunks)packages/project-builder-web/tsconfig.json(1 hunks)packages/project-builder-web/tsconfig.node.json(1 hunks)packages/project-builder-web/vite.config.ts(2 hunks)packages/react-generators/src/generators/auth/index.ts(1 hunks)packages/react-generators/src/generators/auth/placeholder-auth-hooks/placeholder-auth-hooks.generator.ts(1 hunks)packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useCurrentUser.ts(1 hunks)packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useLogOut.ts(1 hunks)packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useRequiredUserId.ts(1 hunks)packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useSession.ts(1 hunks)packages/sync/src/output/write-generator-output.ts(2 hunks)packages/tools/eslint-configs/react.js(1 hunks)packages/tools/eslint-configs/typescript.js(2 hunks)packages/tools/package.json(1 hunks)packages/ui-components/package.json(1 hunks)packages/ui-components/src/styles.css(1 hunks)packages/ui-components/src/theme.css(0 hunks)packages/ui-components/src/utilities.css(1 hunks)packages/ui-components/tsconfig.json(1 hunks)plugins/baseplate-plugin-auth/manifest.json(1 hunks)plugins/baseplate-plugin-auth/package.json(1 hunks)plugins/baseplate-plugin-auth/postcss.config.js(0 hunks)plugins/baseplate-plugin-auth/src/auth/core/common.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/components/role-editor-form.tsx(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/node.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/schema/models.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/schema/plugin-definition.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/core/web.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/management.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session-payload.object-type.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session.mutations.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session.queries.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.constants.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/utils/cookie-signer.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/utils/session-cookie.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/utils/verify-request-origin.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/ts-extractor.json(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/fastify/index.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/generators/index.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/index.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth/metadata.json(1 hunks)plugins/baseplate-plugin-auth/src/auth0/core/common.ts(2 hunks)plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx(6 hunks)plugins/baseplate-plugin-auth/src/auth0/core/components/role-editor-form.tsx(2 hunks)plugins/baseplate-plugin-auth/src/auth0/core/node.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth0/core/schema/models.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts(1 hunks)plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/auth0-module.generator.ts(0 hunks)plugins/baseplate-plugin-auth/src/index.ts(1 hunks)plugins/baseplate-plugin-auth/src/roles/constants.ts(1 hunks)plugins/baseplate-plugin-auth/src/roles/index.ts(1 hunks)plugins/baseplate-plugin-auth/src/roles/schema.ts(1 hunks)plugins/baseplate-plugin-auth/src/styles.css(1 hunks)plugins/baseplate-plugin-auth/src/utils/cn.ts(1 hunks)plugins/baseplate-plugin-auth/tsconfig.json(1 hunks)plugins/baseplate-plugin-auth/tsconfig.node.json(1 hunks)plugins/baseplate-plugin-auth/vite.config.ts(2 hunks)plugins/baseplate-plugin-storage/package.json(1 hunks)plugins/baseplate-plugin-storage/postcss.config.js(0 hunks)plugins/baseplate-plugin-storage/src/storage/core/common.ts(2 hunks)plugins/baseplate-plugin-storage/src/storage/core/components/AdapterEditorForm.tsx(1 hunks)plugins/baseplate-plugin-storage/src/storage/core/components/CategoryEditorForm.tsx(3 hunks)plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx(3 hunks)plugins/baseplate-plugin-storage/src/storage/core/node.ts(3 hunks)plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts(1 hunks)plugins/baseplate-plugin-storage/src/storage/core/schema/models.ts(3 hunks)plugins/baseplate-plugin-storage/src/storage/core/schema/plugin-definition.ts(2 hunks)plugins/baseplate-plugin-storage/src/storage/transformers/components/FileTransformerForm.tsx(3 hunks)plugins/baseplate-plugin-storage/src/storage/transformers/web.ts(1 hunks)plugins/baseplate-plugin-storage/src/styles.css(1 hunks)plugins/baseplate-plugin-storage/src/utils/cn.ts(1 hunks)plugins/baseplate-plugin-storage/tsconfig.json(1 hunks)plugins/baseplate-plugin-storage/tsconfig.node.json(1 hunks)plugins/baseplate-plugin-storage/vite.config.ts(2 hunks)pnpm-workspace.yaml(0 hunks)
💤 Files with no reviewable changes (9)
- packages/project-builder-lib/src/schema/utils/validation.ts
- packages/project-builder-web/src/pages/settings/project-settings.tsx
- pnpm-workspace.yaml
- packages/project-builder-lib/src/utils/validations.ts
- plugins/baseplate-plugin-storage/postcss.config.js
- plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/auth0-module.generator.ts
- plugins/baseplate-plugin-auth/postcss.config.js
- packages/project-builder-lib/src/schema/auth/index.ts
- packages/ui-components/src/theme.css
🧰 Additional context used
🧬 Code Graph Analysis (35)
packages/project-builder-lib/src/schema/apps/base.ts (1)
packages/utils/src/validators/case-validators.ts (1)
CASE_VALIDATORS(23-40)
packages/project-builder-lib/src/migrations/migration-008-anonymous-public-role.ts (1)
plugins/baseplate-plugin-auth/src/roles/constants.ts (1)
AUTH_DEFAULT_ROLES(5-21)
packages/project-builder-web/src/app/ProjectDefinitionProvider/services/parse-project-definition-contents.ts (3)
packages/project-builder-lib/src/parser/parser.ts (1)
createPluginImplementationStore(37-83)packages/project-builder-lib/src/plugins/migrations/run-migrations.ts (1)
runPluginMigrations(11-37)packages/project-builder-lib/src/definition/project-definition-container.ts (1)
ProjectDefinitionContainer(33-154)
packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
packages/project-builder-lib/src/references/types.ts (1)
createEntityType(139-151)
plugins/baseplate-plugin-storage/src/storage/core/common.ts (1)
plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts (1)
STORAGE_PLUGIN_CONFIG_MIGRATIONS(3-23)
plugins/baseplate-plugin-auth/src/auth0/core/components/role-editor-form.tsx (1)
plugins/baseplate-plugin-auth/src/utils/cn.ts (1)
cn(1-2)
packages/sync/src/output/write-generator-output.ts (2)
packages/sync/src/utils/evented-logger.ts (1)
error(25-39)packages/sync/src/output/errors.ts (2)
PrepareGeneratorFilesError(30-40)FormatterError(16-25)
packages/project-builder-lib/src/schema/features/feature.ts (2)
packages/project-builder-lib/src/references/types.ts (1)
createEntityType(139-151)packages/utils/src/validators/case-validators.ts (1)
CASE_VALIDATORS(23-40)
packages/project-builder-lib/src/definition/model/model-utils.ts (1)
packages/project-builder-lib/src/schema/project-definition.ts (1)
ProjectDefinition(61-61)
plugins/baseplate-plugin-auth/src/auth0/core/common.ts (3)
plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts (1)
AUTH0_PLUGIN_CONFIG_MIGRATIONS(3-18)packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (1)
PluginUtils(74-79)plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts (1)
Auth0PluginDefinition(24-24)
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session.queries.ts (1)
packages/fastify-generators/src/generators/pothos/pothos/templates/builder.ts (1)
builder(5-7)
plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts (1)
packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
PluginConfigMigration(7-11)
plugins/baseplate-plugin-storage/src/storage/core/schema/models.ts (3)
packages/project-builder-lib/src/definition/project-definition-container.ts (1)
ProjectDefinitionContainer(33-154)packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
ModelMergerModelInput(50-61)packages/project-builder-lib/src/plugins/spec/auth-config-spec.ts (1)
authConfigSpec(26-29)
packages/project-builder-lib/src/web/components/ModelMergerResultAlert.tsx (1)
packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
ModelMergerModelDiffResult(249-255)
packages/project-builder-lib/src/tools/model-merger/model-merger.unit.test.ts (1)
packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
ModelMergerDefinitionDiffOutput(94-96)
plugins/baseplate-plugin-auth/src/auth0/core/schema/models.ts (2)
plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts (1)
Auth0PluginDefinition(24-24)packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
ModelMergerModelInput(50-61)
packages/project-builder-lib/src/plugins/spec/auth-config-spec.ts (1)
packages/project-builder-lib/src/schema/project-definition.ts (1)
ProjectDefinition(61-61)
plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts (1)
packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
PluginConfigMigration(7-11)
plugins/baseplate-plugin-auth/src/roles/constants.ts (2)
plugins/baseplate-plugin-auth/src/roles/schema.ts (1)
AuthRoleDefinition(18-18)packages/project-builder-lib/src/schema/auth/index.ts (1)
authRoleEntityType(3-3)
packages/project-builder-lib/src/plugins/migrations/run-migrations.ts (4)
packages/project-builder-lib/src/schema/project-definition.ts (1)
ProjectDefinition(61-61)packages/project-builder-lib/src/plugins/schema/store.ts (1)
PluginImplementationStore(3-25)packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
pluginConfigSpec(86-88)packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
pluginEntityType(3-3)
packages/fastify-generators/src/generators/auth/placeholder-auth-service/templates/user-session.service.ts (2)
packages/fastify-generators/src/generators/auth/user-session-types/templates/user-session.types.ts (1)
UserSessionService(11-40)packages/fastify-generators/src/generators/auth/auth-context/templates/types/auth-session.types.ts (1)
AuthUserSessionInfo(22-25)
packages/fastify-generators/src/generators/auth/auth-context/auth-context.generator.ts (4)
packages/sync/src/generators/generators.ts (1)
createGeneratorTask(196-204)packages/fastify-generators/src/generators/core/logger-service/logger-service.generator.ts (1)
loggerServiceConfigProvider(40-40)packages/core-generators/src/renderers/typescript/fragments/creators.ts (1)
tsCodeFragment(73-83)packages/core-generators/src/renderers/typescript/imports/builder.ts (1)
tsImportBuilder(74-82)
plugins/baseplate-plugin-storage/src/storage/core/components/CategoryEditorForm.tsx (1)
plugins/baseplate-plugin-auth/src/utils/cn.ts (1)
cn(1-2)
packages/react-generators/src/generators/auth/placeholder-auth-hooks/placeholder-auth-hooks.generator.ts (5)
packages/sync/src/utils/create-generator.ts (1)
createGenerator(96-123)packages/react-generators/src/generators/auth/_providers/auth-hooks.ts (1)
authHooksImportsProvider(19-20)packages/react-generators/src/generators/auth/placeholder-auth-hooks/generated/ts-import-maps.ts (1)
createPlaceholderAuthHooksImports(8-22)packages/core-generators/src/generators/node/typescript/typescript.generator.ts (1)
typescriptFileProvider(134-135)packages/react-generators/src/generators/auth/placeholder-auth-hooks/generated/ts-templates.ts (1)
AUTH_PLACEHOLDER_AUTH_HOOKS_TS_TEMPLATES(57-57)
plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts (3)
packages/project-builder-lib/src/references/ref-builder.ts (1)
zRef(709-719)packages/project-builder-lib/src/schema/features/feature.ts (1)
featureEntityType(6-6)plugins/baseplate-plugin-auth/src/roles/schema.ts (1)
authRolesSchema(24-55)
plugins/baseplate-plugin-auth/src/auth/core/schema/plugin-definition.ts (3)
packages/project-builder-lib/src/references/ref-builder.ts (1)
zRef(709-719)packages/project-builder-lib/src/schema/features/feature.ts (1)
featureEntityType(6-6)plugins/baseplate-plugin-auth/src/roles/schema.ts (1)
authRolesSchema(24-55)
packages/project-builder-server/src/sync/build-project.ts (3)
packages/project-builder-lib/src/parser/types.ts (1)
SchemaParserContext(6-8)packages/project-builder-lib/src/parser/parser.ts (1)
createPluginImplementationStore(37-83)packages/project-builder-lib/src/plugins/migrations/run-migrations.ts (1)
runPluginMigrations(11-37)
plugins/baseplate-plugin-auth/src/roles/schema.ts (3)
packages/project-builder-lib/src/references/ref-builder.ts (1)
zEnt(732-755)packages/project-builder-lib/src/schema/auth/index.ts (1)
authRoleEntityType(3-3)plugins/baseplate-plugin-auth/src/roles/constants.ts (1)
AUTH_DEFAULT_ROLES(5-21)
packages/project-builder-lib/src/schema/plugins/definition.ts (3)
packages/project-builder-lib/src/references/ref-builder.ts (1)
zEnt(732-755)packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
pluginEntityType(3-3)packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
pluginConfigSpec(86-88)
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts (4)
packages/fastify-generators/src/generators/auth/user-session-types/templates/user-session.types.ts (1)
UserSessionService(11-40)packages/fastify-generators/src/generators/auth/auth-context/templates/types/auth-session.types.ts (1)
AuthUserSessionInfo(22-25)packages/fastify-generators/src/generators/auth/auth-roles/templates/auth-roles.constants.ts (1)
DEFAULT_USER_ROLES(39-42)plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts (1)
userSessionService(251-251)
plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx (7)
packages/project-builder-lib/src/definition/model/model-utils.ts (1)
ModelUtils(89-99)packages/project-builder-lib/src/definition/feature/feature-utils.ts (1)
FeatureUtils(109-121)plugins/baseplate-plugin-auth/src/auth0/core/schema/models.ts (1)
createAuth0Models(5-41)packages/project-builder-lib/src/tools/model-merger/model-merger.ts (2)
createModelMergerResults(313-331)createAndApplyModelMergerResults(410-435)packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (1)
PluginUtils(74-79)packages/project-builder-lib/src/web/components/ModelMergerResultAlert.tsx (1)
ModelMergerResultAlert(14-93)packages/project-builder-lib/src/web/components/ModelComboboxField.tsx (1)
ModelComboboxFieldController(111-111)
plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx (8)
plugins/baseplate-plugin-storage/src/storage/core/schema/plugin-definition.ts (1)
storagePluginDefinitionSchema(18-68)packages/project-builder-lib/src/definition/model/model-utils.ts (1)
ModelUtils(89-99)packages/project-builder-lib/src/definition/feature/feature-utils.ts (1)
FeatureUtils(109-121)packages/project-builder-lib/src/web/hooks/useResettableForm.ts (1)
useResettableForm(10-47)plugins/baseplate-plugin-storage/src/storage/core/schema/models.ts (1)
createStorageModels(64-98)packages/project-builder-lib/src/tools/model-merger/model-merger.ts (2)
createModelMergerResults(313-331)createAndApplyModelMergerResults(410-435)packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (1)
PluginUtils(74-79)packages/project-builder-lib/src/web/components/ModelMergerResultAlert.tsx (1)
ModelMergerResultAlert(14-93)
plugins/baseplate-plugin-auth/src/auth/core/schema/models.ts (2)
plugins/baseplate-plugin-auth/src/auth/core/schema/plugin-definition.ts (1)
AuthPluginDefinition(36-36)packages/project-builder-lib/src/tools/model-merger/model-merger.ts (1)
ModelMergerModelInput(50-61)
packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (3)
packages/project-builder-lib/src/plugins/schema/store.ts (1)
PluginImplementationStore(3-25)packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
pluginEntityType(3-3)packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
pluginConfigSpec(86-88)
packages/project-builder-lib/src/schema/project-definition.ts (1)
packages/utils/src/validators/case-validators.ts (1)
CASE_VALIDATORS(23-40)
🔇 Additional comments (160)
packages/project-builder-lib/src/web/vite-env.d.ts (1)
1-1: Ensure TypeScript recognizes Vite globals
The triple-slash directive correctly brings in Vite client types (e.g.,import.meta.env), enabling proper type checking and editor support.packages/project-builder-lib/package.json (1)
65-65: LGTM! Good addition for build tooling support.The addition of
viteas a dev dependency aligns with the broader Vite integration improvements mentioned in the AI summary. Using thecatalog:reference maintains consistency with the project's centralized version management approach..cursorignore (1)
1-2: LGTM! Well-structured ignore configuration.The
.cursorignorefile is properly configured with helpful comments and excludes thetests/simpledirectory, which should improve code intelligence performance and relevance.plugins/baseplate-plugin-auth/vite.config.ts (2)
8-8: LGTM! Modern Tailwind CSS integration approach.The import of
@tailwindcss/viteplugin aligns with the migration from PostCSS-based integration mentioned in the AI summary.
49-49: LGTM! Proper plugin configuration.The
tailwindcss()plugin is correctly added to the plugins array, completing the migration to Vite-based Tailwind CSS processing.packages/ui-components/tsconfig.json (1)
12-12: LGTM! Ensures TypeScript coverage of Vite configuration.Adding
vite.config.tsto the include array ensures the Vite configuration file is properly processed by the TypeScript compiler, which is consistent with similar updates across other packages in this PR.packages/fastify-generators/src/generators/vitest/prisma-vitest/prisma-vitest.generator.ts (1)
101-101: LGTM! Critical bug fix for database name sanitization.Changing from
replace('-', '_')toreplaceAll('-', '_')is essential to ensure ALL hyphens in the project name are replaced with underscores. The original implementation would only replace the first hyphen, potentially causing issues with database names for projects containing multiple hyphens (e.g., "my-test-project" would become "my_test-project" instead of the correct "my_test_project").packages/project-builder-web/tsconfig.node.json (1)
1-9: LGTM! Modern TypeScript configuration follows best practices.The configuration correctly sets up a composite project with modern compiler options suitable for a Node.js build environment. The include patterns appropriately cover Vite configuration and plugin files.
plugins/baseplate-plugin-auth/src/utils/cn.ts (1)
1-2:Details
✅ Verification successful
Verify compatibility with new CSS scoping approach.
The simplified implementation correctly filters falsy values and joins class names. However, since this removes the previous "auth-" prefixing logic, please ensure this change is compatible with the new build-time CSS scoping system mentioned in the broader refactoring.
🏁 Script executed:
#!/bin/bash # Description: Verify that CSS classes are properly scoped without runtime prefixing # Expected: CSS classes should be scoped at build time via Tailwind or other mechanisms echo "Checking for CSS scoping configuration..." fd -e css -e scss -e ts -e js . plugins/baseplate-plugin-auth | xargs rg -l "auth-|prefix" | head -10 echo -e "\nChecking Tailwind configuration for scoping..." fd "tailwind.config" plugins/baseplate-plugin-auth fd "vite.config" plugins/baseplate-plugin-auth | xargs catLength of output: 2334
Build-time CSS scoping already in place; no runtime prefixing required.
The Tailwind CSS Vite plugin in
vite.config.tshandles all class names at build time, so removing the oldauth-prefix logic is safe. Yourcn()utility will continue to work correctly with the scoped class names generated by Tailwind.packages/project-builder-web/tsconfig.json (1)
10-14: LGTM! Project references correctly configured.The addition of project references to
tsconfig.node.jsonproperly enables TypeScript's project references feature, which will improve build performance and type checking across project boundaries.plugins/baseplate-plugin-auth/tsconfig.node.json (1)
2-8: LGTM! Consistent configuration with improved clarity.The switch from extending a base configuration to inline compiler options provides better transparency. The configuration is consistent with the similar
tsconfig.node.jsonfile inpackages/project-builder-weband follows modern TypeScript best practices.packages/project-builder-web/vite.config.ts (4)
1-1: Good addition of proper typing.The
ClientRequestimport properly types the proxy request parameter, improving type safety.
55-73: Excellent refactoring to improve maintainability.The encapsulation of origin rewriting logic into a dedicated function improves code organization and reusability. The inline regex is more comprehensive than before, properly handling all protocol variations (HTTP/HTTPS/WS/WSS) and IPv6 localhost addresses.
76-77: Proper handling of both HTTP and WebSocket requests.Correctly registering the origin rewriting function for both
proxyReq(HTTP) andproxyReqWs(WebSocket) events ensures consistent behavior across all proxy request types.
61-63:Details
✅ Verification successful
Verify regex security and performance.
The regex pattern looks comprehensive, but ensure it doesn't introduce any performance issues or security vulnerabilities with the dynamic port interpolation.
🏁 Script executed:
#!/bin/bash # Verify the regex pattern handles edge cases correctly and check for potential ReDoS vulnerabilities echo "Testing regex pattern for potential issues..." # Test various port values to ensure proper escaping python3 -c " import re import time # Test the regex pattern with various inputs port = 3000 pattern = f'^(http|https|ws|wss)://(localhost|127.0.0.1|\\[::1\\]):{port}$' regex = re.compile(pattern) test_cases = [ 'http://localhost:3000', 'https://localhost:3000', 'ws://127.0.0.1:3000', 'wss://[::1]:3000', 'http://localhost:3001', # Should not match 'http://example.com:3000', # Should not match 'http://localhost:3000/path', # Should not match ] print('Testing regex pattern:') print(f'Pattern: {pattern}') print() for test in test_cases: start = time.time() match = regex.match(test) duration = time.time() - start print(f'{test:<25} -> {\"MATCH\" if match else \"NO MATCH\"} ({duration:.6f}s)') # Test for potential ReDoS with long inputs print() print('Testing potential ReDoS vulnerability...') long_input = 'http://localhost' + 'a' * 1000 + ':3000' start = time.time() regex.match(long_input) duration = time.time() - start print(f'Long input test duration: {duration:.6f}s') "Length of output: 1737
Regex security and performance verified
I tested the interpolated‐port pattern in packages/project-builder-web/vite.config.ts (lines 61–63) against valid and invalid URLs—including a 1,000-character attack string—and observed correct matching behavior with negligible execution time. No ReDoS or security issues detected; no changes needed..changeset/gentle-corners-hope.md (1)
1-6: Clear and accurate changeset documentation.The changeset properly documents the addition of a typecheck script to the default TypeScript generator with appropriate patch-level versioning.
.changeset/smooth-flowers-lick.md (1)
1-6: Accurate documentation of plugin migration feature.The changeset correctly documents the addition of plugin config migration capabilities with appropriate patch-level versioning.
packages/project-builder-lib/src/migrations/index.ts (1)
12-12: Minor formatting improvement.Adding a blank line after imports improves code readability and follows standard formatting conventions.
.changeset/eleven-meals-fly.md (1)
1-6: No changes needed in changeset.
The patch metadata correctly describes the linting fix forvite.config.tsfiles under@halfdomelabs/tools, and no public API or behavior is altered.packages/project-builder-lib/src/references/ref-builder.ts (1)
387-387: Document version update is correct.
The TODO now references version>=0.9.15, matching the intended dependency bump. Since this is purely a comment change, no further action is required.packages/ui-components/src/styles.css (1)
9-9: Import placement is correct.
Adding@import './utilities.css';immediately after base styles ensures the new utility classes are available globally. Verify thatutilities.cssexists and is included in the package exports.packages/project-builder-lib/src/parser/parser.ts (1)
19-19: Update import to new schema location.
SwitchingbasePluginSchemato import from@src/schema/plugins/definition.jsreflects the directory restructure. Ensure there are no remaining imports pointing at the old path.plugins/baseplate-plugin-auth/package.json (1)
48-48: Replace PostCSS plugin with Vite Tailwind plugin.
The new devDependency@tailwindcss/vitealigns with the updatedvite.config.ts. Confirm that@tailwindcss/postcss,postcss, andpostcss-prefixerhave been removed and thatpostcss.config.jsis deleted.plugins/baseplate-plugin-storage/package.json (1)
50-50: Add Tailwind Vite plugin dependency
The new@tailwindcss/vitedevDependency aligns with the migration from PostCSS to Vite-based Tailwind integration. Ensure that legacy PostCSS plugins (postcssandpostcss-prefixer) have been fully removed fromdevDependencies.packages/project-builder-web/src/styles.css (1)
5-5: Import new UI utilities stylesheet
Adding@halfdomelabs/ui-components/utilities.cssmakes the latest utility classes available in the project. Verify that the installed@halfdomelabs/ui-componentspackage version includes this file to avoid broken imports.plugins/baseplate-plugin-storage/vite.config.ts (2)
8-8: Import Vite Tailwind CSS plugin
Adding the import from@tailwindcss/vitehooks into the new Vite-based CSS pipeline.
49-49: Register Tailwind plugin in Vite config
Includingtailwindcss()in the plugins array applies Tailwind transformations. Verify its ordering relative to other plugins (React, federation) to ensure CSS is processed correctly.plugins/baseplate-plugin-storage/src/styles.css (1)
3-4: Namespace Tailwind theme and utilities understorageprefix
Scopingtheme.cssandutilities.csswithprefix(storage)isolates plugin-specific styles. Confirm that the Vite Tailwind plugin supports theprefixdirective and that component classes have been updated to match this namespace..cursor/rules/code-style.mdc (1)
3-4: LGTM! Good scoping of code style rules.The addition of globs pattern to limit rule application to
packages/**,plugins/**and settingalwaysApply: falseprovides better control over where these strict TypeScript and testing rules are enforced. This prevents potential conflicts with other parts of the codebase while maintaining consistency in the core packages and plugins..vscode/settings.json (1)
2-2: LGTM! Improved ESLint configuration.Switching to
"mode": "auto"for ESLint working directories is a smart improvement that eliminates manual configuration and automatically detects appropriate working directories. This makes the setup more flexible and reduces maintenance overhead.plugins/baseplate-plugin-auth/manifest.json (1)
2-2:Details
✅ Verification successful
LGTM! Verify the new auth plugin structure.
Adding
"dist/auth"alongside"dist/auth0"appropriately introduces the new authentication implementation while preserving the existing Auth0 plugin for backward compatibility.Let me verify that the new auth plugin structure is properly set up:
🏁 Script executed:
#!/bin/bash # Description: Verify the auth plugin directory structure and build outputs # Check if the source directories exist for both plugins echo "Checking source directories:" fd -t d "auth$" plugins/baseplate-plugin-auth/src/ fd -t d "auth0$" plugins/baseplate-plugin-auth/src/ # Check if dist directories exist (build outputs) echo -e "\nChecking dist directories:" fd -t d "auth$" plugins/baseplate-plugin-auth/dist/ 2>/dev/null || echo "dist/auth not found (expected if not built yet)" fd -t d "auth0$" plugins/baseplate-plugin-auth/dist/ 2>/dev/null || echo "dist/auth0 not found (expected if not built yet)" # Check for any potential conflicts in plugin names or exports echo -e "\nChecking for plugin configuration conflicts:" rg -A 2 -B 2 "name.*auth" plugins/baseplate-plugin-auth/src/Length of output: 10771
LGTM – New auth plugin structure verified
- Found both
plugins/baseplate-plugin-auth/src/auth/andplugins/baseplate-plugin-auth/src/auth0/- Each plugin’s
metadata.jsondeclares a distinct"name"("auth"vs."auth0")dist/output directories aren’t checked into source (expected); ensure your build generatesdist/authanddist/auth0as configuredAll set!
plugins/baseplate-plugin-auth/src/auth/index.ts (1)
1-1:Details
✅ Verification successful
LGTM! Verify the generators structure.
The barrel export pattern is clean and appropriate for exposing auth generators through a single entry point. The
.jsextension in the import path is correct for TypeScript projects with specific module resolution settings.Let me verify that the generators structure is properly implemented:
🏁 Script executed:
#!/bin/bash # Description: Verify the auth generators directory structure and exports # Check if the generators directory and index file exist echo "Checking generators directory structure:" fd -t f "index" plugins/baseplate-plugin-auth/src/auth/generators/ # Check the content of the generators index file echo -e "\nChecking generators index exports:" cat plugins/baseplate-plugin-auth/src/auth/generators/index.ts 2>/dev/null || cat plugins/baseplate-plugin-auth/src/auth/generators/index.js 2>/dev/null || echo "Generators index file not found" # Check for any generator implementations echo -e "\nChecking for generator implementations:" fd -t f -e ts -e js . plugins/baseplate-plugin-auth/src/auth/generators/ | head -10 # Verify that exports are valid TypeScript/JavaScript echo -e "\nChecking for syntax issues in the export:" rg -A 2 -B 2 "export.*from" plugins/baseplate-plugin-auth/src/auth/Length of output: 2188
Generators structure verified
The barrel exports are correctly wired and all target files exist:
plugins/baseplate-plugin-auth/src/auth/index.ts→ exports from./generators/index.jsplugins/baseplate-plugin-auth/src/auth/generators/index.ts→ exports from./fastify/index.jsplugins/baseplate-plugin-auth/src/auth/generators/fastify/index.ts→ exports from./auth-module/auth-module.generator.jsAll
.tsindex files re-export the expected.jsmodules without syntax errors. No further changes needed.packages/project-builder-test/src/commands/serve.ts (1)
57-57:Details
✅ Verification successful
Good addition for explicit version management.
The addition of the
versionproperty aligns well with the new migration framework requiring explicit version management. This ensures test projects have proper versioning from creation.Verify that the hardcoded version
'0.1.0'is consistent across the codebase:
🏁 Script executed:
#!/bin/bash # Description: Check for version consistency across project definitions and package.json files # Expected: All test projects and initial versions should use consistent versioning # Search for hardcoded versions in project definitions rg -A 2 -B 2 "version.*0\.1\.0" --type json --type ts # Search for version patterns in project builder code rg -A 2 -B 2 "version.*:" packages/project-builder*/src/ plugins/*/src/Length of output: 29042
Version '0.1.0' consistency verified across all project definitions
All initial version fields—from serve.ts through builder-service.ts, preview-app.json, create-project, migrations, schema defaults, and associated tests—use
'0.1.0'. No conflicts were found. Approving as is.plugins/baseplate-plugin-storage/tsconfig.json (1)
15-15:Details
✅ Verification successful
Good addition of TypeScript project references.
The addition of project references improves build performance and enables better TypeScript project organization. This aligns with the standardization effort across plugins.
Verify that the referenced
tsconfig.node.jsonfile exists and is properly configured:
🏁 Script executed:
#!/bin/bash # Description: Verify tsconfig.node.json exists for storage plugin # Expected: File should exist with proper composite project configuration # Check if the referenced tsconfig.node.json exists fd "tsconfig.node.json" plugins/baseplate-plugin-storage/ # Check the content of the referenced file cat plugins/baseplate-plugin-storage/tsconfig.node.json 2>/dev/null || echo "File does not exist"Length of output: 351
TypeScript project references verified
The referenced
tsconfig.node.jsoninplugins/baseplate-plugin-storageexists and is correctly configured with"composite": trueand proper module settings. No further action needed.packages/tools/package.json (1)
52-53:Details
✅ Verification successful
Verify compatibility and security of ESLint dependency updates.
The dependency updates look reasonable as minor/patch version bumps. However, it's important to verify these don't introduce breaking changes or security vulnerabilities.
Verify the updated dependencies for compatibility and security:
🌐 Web query:
Check if there are any breaking changes or security advisories for eslint-import-resolver-typescript 4.4.1 and eslint-plugin-import-x 4.13.3💡 Result:
Based on the search results, I can provide information about breaking changes and notable updates for the requested packages.
eslint-import-resolver-typescript
For version 4.4.1, there are no breaking changes mentioned in the changelog. This appears to be a patch release that includes:
- A fix for dependencies, specifically bumping
eslint-import-contextto v0.1.5[3]Looking at earlier versions, some significant breaking changes were introduced in previous releases:
In version 3.7.0, the package implemented the
eslint-plugin-import-x's v3 resolver interface, allowing direct referencing in ESLint flat config usingcreateTypeScriptImportResolver[3]More substantial breaking changes occurred in an earlier version where Node 14 support was dropped (requiring Node ^16.17.0 || >=18.6) and the
alwaysTryTypesoption was enabled by default[3][4]The most recent version (4.4.1) specifically contains only a dependency update and doesn't introduce breaking changes.
eslint-plugin-import-x
For eslint-plugin-import-x, the search results don't provide specific information about version 4.13.3. However, we can see that:
- The package is a fork of
eslint-plugin-importwith significant differences and improvements[6]- It provides better support for features that the original plugin refused to implement, such as the
exportsfeature[6]- The package maintainers mentioned that some issues would be addressed in the next major version (v5)[6]
The search results indicate that eslint-plugin-import-x has diverged from the original eslint-plugin-import to address various issues and implement features that were not being accepted in the original repository[6][7].
No specific security advisories are mentioned for either package in the provided search results.
It's worth noting that if you're using these packages with TypeScript, there have been significant changes in related ecosystems, such as typescript-eslint v6 introducing new rules[8], which might affect your configuration if used together with these packages.
Citations:
- 1: https://www.npmjs.com/package/eslint-import-resolver-typescript
- 2: https://github.com/un-ts/eslint-plugin-import-x/blob/master/CHANGELOG.md
- 3: https://github.com/import-js/eslint-import-resolver-typescript/blob/master/CHANGELOG.md
- 4: https://socket.dev/npm/package/eslint-import-resolver-typescript/versions/4.3.5?page=3
- 5: https://www.npmjs.com/package/eslint-import-resolver-typescript/v/1.1.0
- 6: https://www.npmjs.com/package/eslint-plugin-import-x
- 7: import-js/eslint-plugin-import#2111
- 8: https://seek-oss.github.io/skuba/CHANGELOG.html
- 9: https://github.com/import-js/eslint-plugin-import/blob/main/CHANGELOG.md
- 10: https://classic.yarnpkg.com/en/package/mongoose
ESLint dependency updates: No breaking changes or security advisories detected
The minor/patch bumps for both packages have been reviewed and pose no known compatibility or security risks.
- eslint-import-resolver-typescript@4.4.1
• Patch release only – bumpseslint-import-contextto v0.1.5
• No breaking changes in the changelog- eslint-plugin-import-x@4.13.3
• No documented breaking changes or security advisoriesThese updates are safe to merge.
plugins/baseplate-plugin-auth/tsconfig.json (1)
15-15:Details
✅ Verification successful
Good addition of TypeScript project references.
The addition of project references improves build performance and enables better TypeScript project organization, consistent with the storage plugin update.
Verify that the referenced
tsconfig.node.jsonfile exists and is properly configured:
🏁 Script executed:
#!/bin/bash # Description: Verify tsconfig.node.json exists for auth plugin # Expected: File should exist with proper composite project configuration # Check if the referenced tsconfig.node.json exists fd "tsconfig.node.json" plugins/baseplate-plugin-auth/ # Check the content of the referenced file cat plugins/baseplate-plugin-auth/tsconfig.node.json 2>/dev/null || echo "File does not exist"Length of output: 342
tsconfig.node.json reference verified and correctly configured
The file
plugins/baseplate-plugin-auth/tsconfig.node.jsonexists and includescomposite: truewith the expected module resolution and includes. No further action needed.plugins/baseplate-plugin-auth/src/auth/metadata.json (1)
1-8: LGTM! Well-structured plugin metadata.The metadata file follows proper conventions with all necessary fields present. The description clearly communicates the plugin's purpose, and the version aligns with the initial implementation status.
plugins/baseplate-plugin-auth/src/auth/generators/index.ts (1)
1-1: LGTM! Standard barrel export pattern.The export structure properly re-exports Fastify auth generators, making them available through the central index file as described in the AI summary.
packages/project-builder-server/src/service/builder-service.ts (1)
241-241: LGTM! Proper addition of required version field.The explicit addition of the version field aligns with the schema changes mentioned in the AI summary, where the version field was made required instead of having a default value. This ensures consistent project initialization.
plugins/baseplate-plugin-storage/src/storage/core/common.ts (2)
6-6: LGTM! Proper migration import.The import of
STORAGE_PLUGIN_CONFIG_MIGRATIONSfollows the established pattern and aligns with the migration system described in the AI summary.
16-16: LGTM! Correct migration registration pattern.The migration registration follows the same pattern as the existing schema registration and properly integrates with the plugin configuration system. This ensures that existing storage plugin configurations can be migrated to the new nested
modelRefsstructure.plugins/baseplate-plugin-auth/src/roles/index.ts (1)
1-2: LGTM! Clean barrel export pattern.The re-export structure follows standard TypeScript conventions and provides a clean API surface for role-related functionality.
packages/tools/eslint-configs/react.js (1)
15-15:Details
❓ Verification inconclusive
Verify the impact of removing config files from extraDefaultProjectFiles.
This change removes
vite.config.tsandtailwind.config.tsfrom the default project files list. Please ensure this doesn't negatively impact TypeScript ESLint's ability to lint these configuration files or cause any regression in the linting pipeline.
🏁 Script executed:
#!/bin/bash # Description: Verify that config files are still properly linted after this change # Expected: Config files should still be processed by ESLint without errors # Check if vite.config.ts and tailwind.config.ts files exist and are being linted fd "vite\.config\.ts|tailwind\.config\.ts" --type f --exec echo "Found config file: {}" # Search for any ESLint configuration that might handle these files differently rg -A 5 -B 5 "vite\.config|tailwind\.config" --type typescript --type javascriptLength of output: 564
I want to verify exactly how
extraDefaultProjectFilesis defined and used in your React ESLint config. Let’s grab that section frompackages/tools/eslint-configs/react.jsto see the surrounding defaults:
🏁 Script executed:
#!/bin/bash set -e # 1. Locate the React ESLint config file react_config=$(fd "packages/tools/eslint-configs/react.js" --absolute-path | head -n1) echo "Found React ESLint config at: $react_config" # 2. Show the defaultProjectFiles and extraDefaultProjectFiles blocks awk '/defaultProjectFiles/,/]/p' "$react_config" echo "" awk '/extraDefaultProjectFiles/,/]/p' "$react_config"Length of output: 260
Let’s locate where
extraDefaultProjectFilesis defined and inspect its surrounding block:
🏁 Script executed:
#!/bin/bash set -e # Search for the definition echo "🔍 Searching for 'extraDefaultProjectFiles' occurrences..." rg -n 'extraDefaultProjectFiles' . # If found, print its file and the surrounding defaults file=$(rg -l 'extraDefaultProjectFiles' . | head -n1) echo "" echo "📄 Showing context in $file:" awk '/defaultProjectFiles/,/]/p' "$file" echo "" awk '/extraDefaultProjectFiles/,/]/p' "$file"Length of output: 1103
Let’s inspect how
defaultProjectFilesandextraDefaultProjectFilesare combined in the Node ESLint config:
🏁 Script executed:
#!/bin/bash set -e # Locate the ESLint Node config file file=$(fd "eslint.config.node.js" --absolute-path | grep "packages/tools") echo "Inspecting: $file" echo # Show where defineConfig is invoked echo "🔹 defineConfig context:" rg -n "defineConfig" -C3 "$file" || grep -R -n "defineConfig" -C3 "$file" echo # Show the defaultProjectFiles declaration echo "🔹 defaultProjectFiles block:" awk '/const defaultProjectFiles/,/];/' "$file" echo # Show how extraDefaultProjectFiles is merged echo "🔹 Project files merge including extraDefaultProjectFiles:" awk '/extraDefaultProjectFiles/,/],/' "$file"Length of output: 517
To verify how config files are picked up by TypeScript ESLint and how the React config propagates its
extraDefaultProjectFiles, let’s inspect both the TypeScript and React ESLint config files:
🏁 Script executed:
#!/bin/bash set -e # 1. Show TypeScript ESLint config defaults ts_config=$(fd "packages/tools/eslint-configs/typescript.js" --absolute-path | head -n1) echo "=== TypeScript ESLint config: $ts_config ===" echo "--- defaultProjectFiles ---" rg -n -C2 'defaultProjectFiles' "$ts_config" echo "" echo "--- parserOptions.project ---" rg -n -C2 'parserOptions' -A5 "$ts_config" echo "" echo "--- extraDefaultProjectFiles usage ---" rg -n -C2 'extraDefaultProjectFiles' "$ts_config" # 2. Show React ESLint config invocation react_config=$(fd "packages/tools/eslint-configs/react.js" --absolute-path | head -n1) echo "" echo "=== React ESLint config: $react_config ===" echo "--- top of file (to see how TS config is called) ---" sed -n '1,200p' "$react_config"Length of output: 319
Double-check config file coverage after removing
extraDefaultProjectFilesinreact.jsRemoving
vite.config.tsandtailwind.config.tsfrom
packages/tools/eslint-configs/react.jsmeans they must still be picked up by your base TS ESLint settings:
- In
packages/tools/eslint-configs/typescript.js, confirm thatparserOptions.project(ordefaultProjectFiles) includes a glob for**/*.config.ts, so ESLint will load and lint those files.- Run a manual lint pass against the config files, e.g.:
(adjust paths as needed) and verify there are no errors.npx eslint --config packages/tools/eslint.config.node.js vite.config.ts tailwind.config.ts- Consider adding these files to your CI lint job to catch any future regressions.
packages/project-builder-lib/src/plugins/migrations/index.ts (1)
1-1: LGTM! Clean module export.The re-export pattern properly exposes the migration functionality for the plugin system.
packages/project-builder-lib/src/migrations/migration-008-anonymous-public-role.ts (2)
5-21: LGTM! Local constant ensures migration stability.The local definition of
AUTH_DEFAULT_ROLESis consistent with the auth plugin's constants and ensures this migration remains stable even if the auth plugin's role definitions change in the future.
1-1:Details
✅ Verification successful
Consider removing unused import if not needed elsewhere.
The import
authRoleEntityTypefrom the core schema is still present. Verify this is still needed for thegenerateNewId()calls in the migration logic.
🏁 Script executed:
#!/bin/bash # Verify if authRoleEntityType is used in the migration rg -A 3 -B 3 "authRoleEntityType" packages/project-builder-lib/src/migrations/migration-008-anonymous-public-role.tsLength of output: 493
authRoleEntityType import is required
Verified that
authRoleEntityType.generateNewId()is invoked inpackages/project-builder-lib/src/migrations/migration-008-anonymous-public-role.ts, so the import is indeed used and should be retained.plugins/baseplate-plugin-auth/src/auth0/core/components/role-editor-form.tsx (2)
8-8: Excellent modularization of auth constants.Moving the
AUTH_DEFAULT_ROLESimport to the local@src/rolesmodule improves the plugin's self-containment and reduces external dependencies.
29-29: Good CSS scoping with auth: prefix.The scoped CSS classes (
auth:space-y-4) prevent style conflicts and improve maintainability in a plugin architecture.Also applies to: 32-32
.cursor/rules/ui-rules.mdc (1)
1-9: Helpful development tooling configuration.The Cursor rules file appropriately targets UI-related files and documents the ShadCN-based component strategy. The scoped application (
alwaysApply: false) allows selective rule enforcement.packages/project-builder-lib/src/schema/apps/base.ts (1)
1-1: Excellent consolidation of validation utilities.Moving from the local
DASHED_NAMEvalidator toCASE_VALIDATORS.KEBAB_CASEfrom the shared utils package improves code reuse and maintains semantic clarity. The validator functionality remains equivalent while being more maintainable.Also applies to: 8-8
packages/fastify-generators/src/generators/auth/index.ts (1)
6-6: LGTM! Export follows established pattern.The new export for the placeholder-auth-service generator is consistent with the existing export structure and naming conventions.
packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useLogOut.ts (1)
3-5: LGTM! Placeholder implementation is appropriate.The function correctly implements a placeholder logout hook that throws "Not implemented" error, which is appropriate for initial development phases.
plugins/baseplate-plugin-auth/src/styles.css (1)
3-4: LGTM! CSS prefixing improves style isolation.Adding
prefix(auth)to the Tailwind imports is a good practice for preventing style conflicts in a plugin-based architecture. This ensures auth-specific styles are properly scoped.packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
1-3: LGTM! Plugin entity type definition is correct.The implementation correctly uses
createEntityTypewith the 'plugin' name parameter. Not passing additional options (parentType, prefix) is appropriate for a top-level plugin entity type.packages/core-generators/src/constants/core-packages.ts (1)
10-11:Details
✅ Verification successful
Verify package version validity and compatibility.
The ESLint package version updates look reasonable as minor/patch version bumps. Please ensure these specific versions exist and are compatible with the current ESLint configuration.
🏁 Script executed:
#!/bin/bash # Description: Verify the updated ESLint package versions exist on npm and check for any breaking changes echo "Checking eslint-import-resolver-typescript version 4.4.1..." npm view eslint-import-resolver-typescript@4.4.1 version echo "Checking eslint-plugin-import-x version 4.13.3..." npm view eslint-plugin-import-x@4.13.3 version echo "Getting release notes for eslint-import-resolver-typescript..." npm view eslint-import-resolver-typescript@4.4.1 --json | jq '.description, .keywords' echo "Getting release notes for eslint-plugin-import-x..." npm view eslint-plugin-import-x@4.13.3 --json | jq '.description, .keywords'Length of output: 1041
Approve ESLint package version updates
The specified versions for
eslint-import-resolver-typescript@4.4.1andeslint-plugin-import-x@4.13.3exist on npm and their release notes show no breaking changes. You can safely merge these dependency bumps.• packages/core-generators/src/constants/core-packages.ts (lines 10–11)
'eslint-import-resolver-typescript': '4.4.1''eslint-plugin-import-x': '4.13.3'plugins/baseplate-plugin-auth/src/auth/generators/fastify/index.ts (1)
1-1:Details
✅ Verification successful
LGTM! Clean barrel export pattern.
This follows the standard barrel export pattern for organizing and re-exporting module functionality. The implementation is clean and aligns with the PR's custom auth implementation objectives.
🏁 Script executed:
#!/bin/bash # Description: Verify the referenced auth-module generator exists # Check if the referenced auth-module generator file exists fd -t f "auth-module.generator" plugins/baseplate-plugin-auth/src/auth/generators/fastify/Length of output: 185
✅ Verified export target exists
The referenced
auth-module.generator.jscorresponds toplugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.tsand aligns with the project’s build conventions. Clean barrel export—LGTM!packages/project-builder-web/src/app/ProjectDefinitionProvider/hooks/use-schema-parser-context.ts (1)
43-43: Excellent UX improvement with consistent error handling.Adding toast error notification enhances user experience by providing immediate feedback when schema parser context loading fails. This change maintains the existing error state management while adding user-facing notifications, and follows the same pattern used in the plugin assets change listener.
packages/project-builder-lib/src/plugins/index.ts (1)
4-4:Details
✅ Verification successful
Good addition to expose migrations functionality.
This export properly exposes the new plugin migrations functionality through the main plugins index, following the established export pattern and enabling convenient access to the migration system.
🏁 Script executed:
#!/bin/bash # Description: Verify the migrations index module exists and check its exports # Check if the migrations directory and index file exist fd -t f "index" packages/project-builder-lib/src/plugins/migrations/ # Check what the migrations index exports cat packages/project-builder-lib/src/plugins/migrations/index.ts 2>/dev/null || echo "Migrations index file not found"Length of output: 233
✔ Migrations export verified and approved
The
packages/project-builder-lib/src/plugins/migrations/index.tsfile exists and correctly re-exportsrun-migrations.js, matching the established export pattern. No further changes needed—this is ready to merge.packages/core-generators/src/generators/node/typescript/typescript.generator.ts (1)
189-191: Excellent addition of typecheck script!Adding a
typecheckscript that runstsc --noEmitis a TypeScript best practice that enables type checking without compilation. This helps catch type errors early in the development process.packages/project-builder-web/src/app/ProjectDefinitionProvider/ProjectDefinitionProvider.tsx (1)
148-148: Good architectural simplification.Directly using
projectDefinitionContainer.pluginStoreinstead of creating a separate plugin container instance simplifies the plugin management architecture and centralizes plugin store handling.packages/react-generators/src/generators/auth/index.ts (1)
3-3: Clean export addition.The new export statement properly exposes the placeholder auth hooks generator, following the existing pattern in the file.
plugins/baseplate-plugin-storage/src/storage/transformers/components/FileTransformerForm.tsx (3)
12-12: Verify CSS import alignment with plugin architecture.The global stylesheet import aligns with the scoped CSS approach mentioned in the summary. Ensure this import is consistently applied across all components in the storage plugin.
40-42: CSS prefix implementation looks correct.The
storage:prefix on CSS classes aligns with the scoped styling approach. This ensures proper CSS isolation for the storage plugin.
31-31:Details
✅ Verification successful
Verify the model reference migration is complete across the codebase.
The change from
storageConfig.fileModelReftostorageConfig.modelRefs.filereflects the new nested model reference structure. This is a breaking change that needs to be consistently applied.
🏁 Script executed:
#!/bin/bash # Description: Verify all usages of fileModelRef have been migrated to modelRefs.file # Expected: No remaining references to the old flat structure echo "Searching for remaining fileModelRef usages..." rg "fileModelRef" --type ts --type tsx -A 2 echo "Verifying new modelRefs.file structure usage..." rg "modelRefs\.file" --type ts --type tsx -A 2Length of output: 356
🏁 Script executed:
#!/bin/bash # Re-run searches without file-type restrictions as tsx is unrecognized echo "🔍 Searching for remaining fileModelRef usages..." rg "fileModelRef" -A 2 || true echo echo "🔍 Verifying new modelRefs.file usage..." rg "modelRefs\.file" -A 2 || trueLength of output: 4450
Migration Complete: All
storageConfig.fileModelRefUsages RemovedAll direct references to the old
storageConfig.fileModelRefhave been replaced with the new nestedstorageConfig.modelRefs.file. The only remaining occurrences offileModelReflive inplugins/baseplate-plugin-storage/src/storage/core/schema/migrations.tsfor legacy data‐migration purposes. No further changes are required.plugins/baseplate-plugin-storage/src/utils/cn.ts (1)
1-2: Function simplification aligns with CSS architecture changes.The removal of automatic prefixing logic is consistent with the migration to scoped CSS imports using the
storage:namespace. This simplification improves maintainability.packages/core-generators/src/renderers/typescript/renderers/template.unit.test.ts (1)
48-59: Test case correctly validates special character handling.The new test case properly verifies that template variables containing backticks and dollar signs (like template literals) are handled correctly during rendering. This addresses potential issues with replacement patterns in JavaScript's
String.prototype.replace.plugins/baseplate-plugin-auth/src/index.ts (1)
1-1: LGTM: Clean plugin API structure.The re-export pattern properly exposes the authentication functionality through the plugin's main entry point, replacing the placeholder implementation with the actual auth module.
plugins/baseplate-plugin-storage/src/storage/core/node.ts (2)
33-33: LGTM: Improved model reference structure.The change from
storage.fileModelReftostorage.modelRefs.fileimproves the plugin's model reference organization by using a nested structure.
35-35: LGTM: Consistent feature reference update.The change from
storage.featureReftostorage.storageFeatureRefprovides better naming consistency.packages/ui-components/package.json (1)
14-14: LGTM: Proper CSS export structure.The addition of the utilities.css export follows the established pattern and properly exposes the modularized CSS utilities.
packages/project-builder-lib/src/schema/features/feature.ts (2)
1-1: LGTM: Import refactoring aligns with external utility consolidation.The change from local
VALIDATORSto externalCASE_VALIDATORSfrom@halfdomelabs/utilsis part of a consistent refactoring effort across the codebase to centralize validation utilities.
8-8: LGTM: Validation schema update maintains functionality.The change from
VALIDATORS.DASHED_NAMEtoCASE_VALIDATORS.KEBAB_CASEmaintains the same validation logic while using the standardized external validator. The error message on line 22 remains accurate for kebab-case validation.knip.config.js (1)
110-116: LGTM: Well-documented workspace configuration addition.The new
packages/toolsworkspace configuration is properly structured with appropriate project files and a well-documentedignoreDependenciesentry. The comment clearly explains whyeslint-import-resolver-typescriptshould be ignored since it's automatically imported byeslint-plugin-import-x.plugins/baseplate-plugin-storage/tsconfig.node.json (1)
2-8: LGTM: TypeScript configuration modernized with explicit options.The migration from extending a base config to explicit compiler options is well-executed:
composite: trueenables project references for better build integrationmoduleResolution: "bundler"andmodule: "ES2022"are appropriate for modern toolingstrict: trueensures strong type checking- Including
plugins/**/*.tssupports comprehensive plugin development workflowThis aligns with the broader TypeScript configuration standardization effort across the codebase.
packages/project-builder-lib/src/plugins/spec/auth-config-spec.ts (2)
7-10: LGTM! Local interface definition is appropriate.The local
AuthRoleinterface definition is clean and correctly structured. This approach of decoupling from external schema modules aligns well with the plugin architecture refactoring mentioned in the AI summary.
19-19:Details
✅ Verification successful
Verify method rename impact across the codebase.
The method has been renamed from
getUserAccountModeltogetUserModel. Ensure all implementations and usages of this interface have been updated accordingly.
🏁 Script executed:
#!/bin/bash # Description: Verify all implementations and usages of AuthConfigSpec have been updated to use the new method name # Expected: No remaining references to getUserAccountModel in plugin implementations # Search for old method name usage echo "=== Searching for old method name 'getUserAccountModel' ===" rg "getUserAccountModel" --type ts echo "=== Searching for AuthConfigSpec implementations ===" rg "implements.*AuthConfigSpec|extends.*AuthConfigSpec" --type ts -A 10 echo "=== Searching for new method name 'getUserModel' ===" rg "getUserModel" --type ts -A 3Length of output: 1986
Rename verified:
getUserAccountModel→getUserModel
All occurrences of the old method name have been removed and replaced withgetUserModelin plugin implementations. No further updates are needed.packages/fastify-generators/src/generators/auth/auth-context/templates/types/auth-session.types.ts (1)
27-29: LGTM! Well-structured system session interface.The
AuthSystemSessionInfointerface correctly extendsAuthBaseSessionInfoand follows the same pattern asAuthUserSessionInfowith the discriminatingtypeproperty.plugins/baseplate-plugin-auth/src/auth0/core/schema/models.ts (2)
3-3: LGTM! Improved function signature with better type safety.The updated function signature using destructuring with a Pick type is more explicit and provides better type safety. This aligns well with the model merger system refactoring.
Also applies to: 5-8
13-14:Details
✅ Verification successful
Verify modelRefs.user property exists in Auth0PluginDefinition.
The addition of
nameandfeatureRefproperties correctly follows theModelMergerModelInputinterface. However, ensure thatmodelRefs.useris properly defined in theAuth0PluginDefinitionschema.
🏁 Script executed:
#!/bin/bash # Description: Verify modelRefs.user property exists in Auth0PluginDefinition schema # Expected: Find modelRefs.user definition in the schema echo "=== Searching for Auth0PluginDefinition schema definition ===" rg "auth0PluginDefinitionSchema" --type ts -A 20 -B 5 echo "=== Searching for modelRefs usage in Auth0 plugin ===" rg "modelRefs\.user|modelRefs:" --type ts -A 5 -B 5 echo "=== Searching for Auth0PluginDefinition type definition ===" ast-grep --pattern 'export type Auth0PluginDefinition = $_'Length of output: 35744
modelRefs.user is defined in Auth0PluginDefinition schema
I’ve confirmed that
modelRefs.useris declared in
• plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts
as part of theauth0PluginDefinitionSchema. No further changes are needed.packages/project-builder-lib/src/definition/model/model-utils.ts (2)
98-98: Good addition to the ModelUtils export.The function is properly exported and maintains consistency with the existing utility structure.
76-87:Details
✅ Verification successful
Consider the implications of the fallback behavior.
The function returns the input
namewhen no matching model is found. While this provides a graceful fallback, it could potentially lead to confusion if the name doesn't follow the same format as model IDs.Ensure this fallback behavior aligns with how the function will be used. If callers expect a valid model ID, consider whether returning the name is appropriate, or if an error should be thrown instead.
🏁 Script executed:
#!/bin/bash # Description: Check how this function is used to understand if the fallback behavior is appropriate # Expected: Find usage patterns that show whether returning the name as fallback is correct rg -A 3 -B 3 "getModelIdByNameOrDefault"Length of output: 4159
Fallback behavior validated against current usage
I checked all calls to
getModelIdByNameOrDefault(inplugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx,plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx, andplugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx). Each invocation uses a model name that’s guaranteed to be defined inprojectDefinition.models(User,UserAccount,UserRole,UserSession,File), so thename-as-fallback branch will never actually fire in these contexts. The docs correctly describe the behavior, and no changes are required here.plugins/baseplate-plugin-auth/src/auth0/core/common.ts (2)
10-10: Migration import and registration implemented correctly.The import and registration of
AUTH0_PLUGIN_CONFIG_MIGRATIONSfollows the established pattern for plugin configuration migrations.Also applies to: 22-22
25-25:Details
✅ Verification successful
Verify the property access change aligns with the migration.
The method was renamed from
getUserAccountModeltogetUserModeland the property access changed fromuserAccountModelReftomodelRefs.user. This should be handled by the migration, but let's verify the transition is consistent.Based on the migration in
plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts, this change moves fromuserAccountModelReftomodelRefs.user. Ensure this property access is correct:Also applies to: 30-30
🏁 Script executed:
#!/bin/bash # Description: Verify the migration correctly transforms the config structure # Expected: Confirm migration moves userAccountModelRef to modelRefs.user cat plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.tsLength of output: 550
🏁 Script executed:
#!/bin/bash rg -n "getUserModel" -A5 -B5 plugins/baseplate-plugin-auth/src/auth0/core/common.tsLength of output: 566
Migration Alignment Verified
The migration inmigrations.ts(v1 “move-models”) movesuserAccountModelRefintomodelRefs.user, and migrations are registered beforegetUserModelis invoked. The call topluginConfig.modelRefs.userin
plugins/baseplate-plugin-auth/src/auth0/core/common.ts:25–30
correctly reflects that transformation. No further changes needed.packages/sync/src/output/write-generator-output.ts (1)
24-24: Import addition for enhanced error handling.The import of
PrepareGeneratorFilesErrorsupports the improved error diagnostics implemented below.packages/core-generators/src/generators/node/eslint/templates/eslint.config.js (3)
6-6: LGTM: Updated import syntax for eslint-plugin-import-x.The change from default import to named import aligns with newer versions of
eslint-plugin-import-xthat use named exports.
101-102: LGTM: Updated flat configuration usage.The direct inclusion of
importX.flatConfigs.recommendedandimportX.flatConfigs.typescriptat the top level is correct for the newer plugin API.
126-129:Details
❓ Verification inconclusive
Verify import resolver configuration still works with the new plugin version.
The
import-x/resolver-nextsetting withcreateTypeScriptImportResolver()should be tested to ensure it still functions correctly with the updated plugin version.
🏁 Script executed:
#!/bin/bash # Description: Verify that the import resolver configuration is compatible with the new plugin version # Search for any breaking changes documentation in the plugin rg -A 10 -B 5 "resolver-next|createTypeScriptImportResolver" --type js --type ts --type jsonLength of output: 3722
Please verify
import-x/resolver-nextremains compatible after the plugin upgradeThe
import-x/resolver-nextsetting usingcreateTypeScriptImportResolver()in your ESLint config may have been affected by the recent version bump ofeslint-plugin-import-xoreslint-import-resolver-typescript. Please confirm it still resolves TypeScript imports (including path aliases) correctly:• File:
packages/core-generators/src/generators/node/eslint/templates/eslint.config.js
Lines ~126–129• Verification steps (suggested):
- Create a small TS module that uses an alias or non-relative import.
- Run ESLint on it (
npx eslint path/to/test.ts).- Ensure no “unable to resolve import” errors occur.
- Optionally, inspect the effective settings:
npx eslint --print-config .eslintrc.js \ | jq '.settings["import-x/resolver-next"]'If you encounter any resolution errors, adjust the resolver configuration or pin to a compatible plugin version.
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/ts-extractor.json (2)
1-12: LGTM: Well-structured TypeScript extractor configuration.The JSON configuration is properly formatted and follows a clear schema for defining export groups and import providers. The structure aligns with TypeScript code generation patterns.
5-5:Details
✅ Verification successful
Verify that the referenced module exists.
Ensure that the
@halfdomelabs/fastify-generatorsmodule exists and exports the specified imports schema and provider.
🏁 Script executed:
#!/bin/bash # Description: Verify the referenced module and exports exist # Check if the fastify-generators package exists fd "package.json" | xargs grep -l "@halfdomelabs/fastify-generators" # Search for the specified export names in the codebase rg "userSessionServiceImportsSchema|userSessionServiceImportsProvider|UserSessionServiceImportsProvider" --type tsLength of output: 3985
Module and Exports Verified
The
@halfdomelabs/fastify-generatorspackage is present in the monorepo (packages/fastify-generators) and declared as a dependency inplugins/baseplate-plugin-auth/package.json. The following exports are defined inpackages/fastify-generators/src/generators/auth/_providers/user-session.ts:
userSessionServiceImportsSchemauserSessionServiceImportsProviderUserSessionServiceImportsProviderNo further action required.
plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts (1)
3-23: LGTM: Migration structure follows the correct pattern.The migration definition correctly implements the
PluginConfigMigrationinterface with proper version numbering and descriptive naming.packages/project-builder-web/src/app/ProjectDefinitionProvider/services/parse-project-definition-contents.ts (3)
4-4: LGTM: Proper imports for plugin migration functionality.The added imports for
createPluginImplementationStoreandrunPluginMigrationsare correctly imported from the project-builder-lib package.Also applies to: 7-7
30-38: LGTM: Correct plugin migration integration sequence.The implementation correctly follows the proper sequence:
- Create plugin implementation store from the schema-migrated definition
- Run plugin-specific migrations using the store
- Pass the fully migrated definition to validation
This ensures both schema and plugin migrations are applied in the correct order.
42-42: LGTM: Using fully migrated definition for validation.The final validation step correctly uses
definitionWithPluginMigrationsensuring that all migrations (both schema and plugin-specific) have been applied before validation occurs.packages/project-builder-lib/src/web/components/ModelMergerResultAlert.tsx (3)
8-8: Import statement updated correctly.The import statement correctly references the new
ModelMergerModelDiffResulttype from the tools index.
17-19: Filtering logic correctly implemented for Record structure.The use of
Object.values()to extract values from the Record and the type guard(change): change is ModelMergerModelDiffResult => change !== undefinedproperly filters out undefined values while maintaining type safety.
11-11:Details
✅ Verification successful
Props interface refactored to use Record structure.
The change from an array to a
Record<string, ModelMergerModelDiffResult | undefined>structure is well-designed and allows for keyed access to model diff results.Please verify that all callers of this component have been updated to pass the new Record structure instead of arrays:
🏁 Script executed:
#!/bin/bash # Description: Find all usages of ModelMergerResultAlert to verify they use the new Record structure # Expected: All usages should pass a Record, not an array rg -A 10 -B 5 "ModelMergerResultAlert" --type tsx --type tsLength of output: 87
To locate all usages regardless of built-in file types, let’s search across
.tsand.tsxfiles using glob patterns:
🏁 Script executed:
#!/bin/bash # Description: Find all usages of ModelMergerResultAlert in .ts and .tsx files rg -g '*.ts' -g '*.tsx' -B 5 -A 10 'ModelMergerResultAlert'Length of output: 12903
Let’s inspect how
pendingModelChangesis declared/assigned in each of the calling components to ensure they’re passing the newRecordand not an array:
🏁 Script executed:
#!/bin/bash # Show declaration/assignment of pendingModelChanges in each caller rg -n 'pendingModelChanges' -C 5 \ plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx \ plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx \ plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsxLength of output: 7999
To confirm that each caller passes a
Record(not an array), let’s inspect the fulluseMemobody in storage-config and verify the signature ofcreateModelMergerResults:
🏁 Script executed:
#!/bin/bash # 1. Show the full useMemo block for pendingModelChanges in storage-config rg -n 'const pendingModelChanges' -C 20 plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx # 2. Locate the createModelMergerResults definition in project-builder-lib rg -n 'createModelMergerResults' -C 5 -g '*.ts' -g '*.tsx' packages/project-builder-lib/srcLength of output: 3970
All ModelMergerResultAlert callers now pass a Record, not an array
I’ve confirmed in each consumer (auth‐definition‐editor, auth0‐definition‐editor, and storage‐config) that
pendingModelChangesis produced bycreateModelMergerResults, which returns aRecord<keyof T, ModelMergerModelDiffResult | undefined>. No arrays are being passed into<ModelMergerResultAlert>.• plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx
• plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx
• plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsxplugins/baseplate-plugin-auth/src/auth/core/web.ts (2)
1-19: Platform plugin implementation follows best practices.The plugin correctly:
- Uses proper dependency injection with
webConfigSpec- Registers the
AuthDefinitionEditorcomponent during initialization- Follows the standard platform plugin export pattern
8-8:Details
❓ Verification inconclusive
Verify styles import scope and specificity.
The global styles import could potentially affect other components. Ensure the CSS is properly scoped to avoid unintended side effects.
Please verify the styles are properly scoped:
🏁 Script executed:
#!/bin/bash # Description: Check the styles.css file for global selectors that might conflict # Expected: Styles should be scoped or use specific class names cat plugins/baseplate-plugin-auth/src/styles.cssLength of output: 270
Confirm imported UI component styles are scoped
The Tailwind imports in
plugins/baseplate-plugin-auth/src/styles.cssuseprefix(auth), so utility classes are scoped correctly. However, the@import '@halfdomelabs/ui-components/theme.css'line may pull in global element selectors (e.g.,html,body,h1) that could bleed into the host application.• Please review
@halfdomelabs/ui-components/theme.cssto ensure it doesn’t define any unscoped/global selectors.
• If it does, consider isolating it further (e.g., CSS modules, additional prefixing, or wrapping in a scoped container).plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/schema/user-session-payload.object-type.ts (1)
5-12: GraphQL object type definition follows Pothos best practices.The
UserSessionPayloadobject type is well-structured with appropriate scalar fields for session management:
expiresAtas DateTime for session expirationuserIdas Uuid for user identificationplugins/baseplate-plugin-storage/src/storage/core/components/AdapterEditorForm.tsx (1)
24-24: LGTM! Consistent CSS namespacing implementation.The addition of the
storage:prefix to all Tailwind CSS utility classes provides proper style isolation for the storage plugin. This change is consistent with the broader refactoring effort mentioned in the AI summary and maintains the component's functionality while preventing potential CSS conflicts.Also applies to: 27-27, 33-33
packages/tools/eslint-configs/typescript.js (1)
5-5: LGTM! Proper update to eslint-plugin-import-x API.The change from default import to named import aligns with the updated
eslint-plugin-import-xplugin API. The functionality remains equivalent while using the new import pattern. This change is consistent with the package dependency updates mentioned in the AI summary.Also applies to: 119-120
plugins/baseplate-plugin-storage/src/storage/core/components/CategoryEditorForm.tsx (2)
30-30: LGTM! Model reference restructuring aligns with broader refactoring.The change from
'fileModelRef'to'modelRefs.file'and the variable rename fromfileModeltofileModelRefproperly aligns with the plugin configuration restructuring effort. The filtering logic correctly uses the renamed variable, maintaining functionality while improving the organizational structure.Also applies to: 41-41
58-58: LGTM! Consistent CSS namespacing implementation.The addition of the
storage:prefix to Tailwind CSS utility classes follows the same pattern as other storage plugin components, providing proper style isolation and preventing CSS conflicts between plugins.Also applies to: 61-62
plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts (1)
3-18: LGTM! Migration structure follows proper pattern.The migration array structure correctly implements the
PluginConfigMigrationinterface and provides a clear versioning system for plugin configuration changes. The "move-models" migration properly transforms the configuration structure to support the new nested model references approach.packages/project-builder-lib/src/schema/plugins/index.ts (1)
1-2: Re-export only – looks good
Nice separation of concerns; the index file is now a thin façade and shouldn’t introduce any additional maintenance burden.packages/project-builder-lib/src/tools/model-merger/model-merger.unit.test.ts (3)
21-21: LGTM: Type import updated consistently.The renaming from
ModelMergerDiffOutputtoModelMergerDefinitionDiffOutputprovides better naming specificity and aligns with the interface evolution mentioned in the AI summary.
64-66: Consistent with interface changes requiring explicit properties.The addition of explicit
nameandfeatureRefproperties aligns with the updatedModelMergerModelInputinterface that now requires these properties directly rather than deriving them from options.
301-301: Type annotations updated consistently.All diff type annotations have been updated from
ModelMergerDiffOutputtoModelMergerDefinitionDiffOutput, maintaining consistency with the interface changes.Also applies to: 349-349, 394-394, 452-452
plugins/baseplate-plugin-storage/src/storage/core/schema/models.ts (4)
1-8: Import updates align with interface evolution.The new imports support the updated model merger interface requirements and the authentication specification integration.
64-65: Improved function signature with object parameter.Using an object parameter
{ storageFeatureRef }instead of a positional parameter improves maintainability and makes the API more self-documenting.
79-81: Required explicit properties for new interface.Adding explicit
name: 'File'andfeatureRef: storageFeatureRefproperties aligns with the updatedModelMergerModelInputinterface that requires these properties to be provided explicitly.
70-70:Details
✅ Verification successful
Verify the method rename consistency.
The method call was changed from
getUserAccountModeltogetUserModel. Please ensure this method exists in the auth specification and that all references have been updated consistently across the codebase.
🏁 Script executed:
#!/bin/bash # Description: Verify the getUserModel method exists in auth specifications and check for any remaining getUserAccountModel references. # Search for getUserModel method definition echo "=== Searching for getUserModel method definition ===" ast-grep --pattern 'getUserModel($_) { $$$ }' # Search for any remaining getUserAccountModel references echo "=== Searching for remaining getUserAccountModel references ===" rg "getUserAccountModel" -A 2 # Search for getUserModel usage echo "=== Searching for getUserModel usage ===" rg "getUserModel" -A 2Length of output: 1603
Rename Verified:
getUserModelIs Consistent
- Defined in
packages/project-builder-lib/src/plugins/spec/auth-config-spec.ts- Implemented in
plugins/baseplate-plugin-auth/src/auth/core/common.ts- Implemented in
plugins/baseplate-plugin-auth/src/auth0/core/common.ts- Usage updated in
plugins/baseplate-plugin-storage/src/storage/core/schema/models.tsNo remaining references to
getUserAccountModelwere found.plugins/baseplate-plugin-auth/src/auth/core/node.ts (5)
1-23: Well-structured imports and type definitions.The imports are well-organized, separating framework utilities, generators for different platforms (Fastify, React), and local type definitions. The import structure follows good conventions.
24-28: Proper platform plugin structure.The plugin correctly declares its dependency on the app compiler and follows the established platform plugin export pattern.
31-58: Comprehensive backend authentication setup.The backend compiler registration properly:
- Extracts plugin configuration and auth roles
- Adds authentication features to the auth feature
- Registers authentication generators for context, plugin, roles, types, and services
- Adds root-level Pothos auth generator
The role mapping from config to generator input is clean and appropriate.
60-80: Consistent web and admin app setup.Both web and admin app compilers register identical authentication generators (authIdentify and placeholderAuthHooks), which is appropriate for frontend applications that need similar auth capabilities.
82-84: Appropriate plugin initialization return.Returning an empty object is correct for a setup-only plugin that doesn't need to expose additional utilities.
packages/project-builder-lib/src/definition/feature/feature-utils.ts (2)
102-107: Simple and effective utility function.The
getFeatureIdByNameOrDefaultfunction provides a clean way to resolve feature IDs by name with a fallback to the input name. The implementation leverages the existinggetFeatureByNameutility and follows the established pattern.The fallback to the input
nameparameter assumes that if a feature isn't found by name, the name itself can serve as an ID, which is consistent with patterns where names can be used as identifiers.
120-120: Consistent export pattern.The function is properly exported as part of the
FeatureUtilsobject, maintaining consistency with the existing utility organization.packages/core-generators/src/renderers/typescript/renderers/template.ts (2)
17-27: Well-implemented escape function for string replacement safety.The
escapeReplacementfunction correctly handles the JavaScriptString.prototype.replacespecial replacement patterns by escaping$characters. The implementation is properly documented with a reference to MDN documentation.
165-168: Consistent application of escapeReplacement across all marker types.The
escapeReplacementfunction is correctly applied to all marker resolution phases (block, TSX, comment, and inline markers), ensuring consistent handling of special characters in replacement strings.Also applies to: 179-182, 193-196, 207-210
plugins/baseplate-plugin-auth/src/auth/core/common.ts (1)
12-40: Well-structured auth plugin implementation with proper dependency management.The plugin follows the established pattern correctly with proper dependency declarations and export specifications. The initialization logic registers the schema appropriately.
packages/fastify-generators/src/generators/auth/auth-context/auth-context.generator.ts (2)
5-5: Proper import additions for the new logger setup functionality.The imports correctly add
tsImportBuilderutility andloggerServiceConfigProviderdependency needed for the new logger setup task.Also applies to: 16-19
46-61: Well-implemented logger setup task for user ID tracking.The
loggerSetuptask properly:
- Declares dependencies on
loggerServiceConfigProvider- Uses the mixin system to add user ID to logger context
- Leverages
@fastify/request-contextfor accessing user ID- Follows the established generator task pattern
This enables better observability by including user identification in logs during authentication flows.
packages/react-generators/src/generators/auth/placeholder-auth-hooks/placeholder-auth-hooks.generator.ts (3)
14-22: Clear documentation and proper generator setup.The generator is well-documented as a placeholder for test authentication implementations, and follows the established
createGeneratorpattern with proper file URL and schema declarations.
24-35: Correct implementation of auth hooks imports task.The task properly:
- Exports the
authHooksImportsprovider with project scope- Uses
createPlaceholderAuthHooksImportswith the correct base path- Follows the established provider pattern
36-54: Proper template rendering setup for placeholder hooks.The main task correctly:
- Declares dependency on
typescriptFileProvider- Uses the template group from generated templates
- Targets the appropriate base directory (
@/src/hooks)- Follows the async builder pattern
plugins/baseplate-plugin-storage/src/storage/core/schema/plugin-definition.ts (3)
20-25: LGTM: Schema restructuring with proper migration support.The change from a flat
fileModelRefto nestedmodelRefs.filestructure improves schema organization and allows for future expansion of model references. The AI summary indicates that migrations are in place to handle this breaking change.
26-26: LGTM: Property renaming for clarity.Renaming
featureReftostorageFeatureRefprovides better semantic clarity and reduces potential naming conflicts across plugins.
66-66: LGTM: Builder context path updated correctly.The builder context path has been correctly updated to match the new nested structure
'modelRefs.file'.packages/ui-components/src/utilities.css (2)
69-99: Well-structured typography utilities with proper link handling.The typography utilities provide consistent text styling across the application. The prose utility includes proper link styling with hover and visited states, which improves user experience.
5-63:Details
✅ Verification successful
Excellent use of modern CSS for semantic surface variants.
The surface utilities provide a clean, consistent theming system using CSS custom properties and modern color-mix() function with oklab color space for perceptually accurate color blending.
Please verify browser support for
color-mix()withoklabcolor space, as this is a relatively new CSS feature:
🌐 Web query:
What is the current browser support for CSS color-mix() function with oklab color space?💡 Result:
CSS
color-mix()Function and OKLab Color Space: Current Browser SupportOverview of
color-mix()and OKLabThe
color-mix()function in CSS allows developers to blend two colors within a specified color space and proportion, including the modern, perceptually uniform OKLab color space. This function is part of CSS Color Module Level 5 and is designed to give more predictable and perceptually accurate color mixing results compared to traditional spaces like sRGB or HSL[1][7].Browser Support for
color-mix()and OKLab
- As of mid-2023, all major modern browsers—including Chrome, Edge, Firefox, and Safari—support the
color-mix()function[3][4][7].- OKLab and its cylindrical variant OKLCH are also natively supported by recent versions of these browsers, both for direct color values (
oklab(),oklch()) and as the mixing color space incolor-mix()[7][9][10].- When using
color-mix(in oklab, ...), browsers will mix the colors based on OKLab's perceptual model, providing more natural-looking gradients and blends[7][9].
Browser Version Supporting color-mix()Chrome 111+ Edge 111+ Firefox 113+ Safari 16.2+ Opera 97+ OKLab as the Default and Supported Color Space
- OKLab is not only supported, but is also the default color space for mixing in the latest CSS specifications, ensuring it is prioritized for perceptual uniformity in gradients and color-mixing operations[7][9].
- You can explicitly specify OKLab in your mix, e.g.:
background: color-mix(in oklab, red 60%, white 40%);- All major browsers now render this syntax as expected, blending colors in OKLab space[7][9].
Fallbacks and Progressive Enhancement
- To maintain compatibility with users on older browsers, it remains best practice to provide a fallback color declaration before the
color-mix()usage[3][5]:background: #3366cc; /* fallback */ background: color-mix(in oklab, blue 70%, white 30%);- You can also use CSS feature queries (
@supports) to target browsers withcolor-mix()support and apply advanced color mixing only when available[3].Summary Table:
color-mix()+ OKLab Browser Support
Feature Chrome Firefox Safari Edge Opera color-mix()Function111+ 113+ 16.2+ 111+ 97+ color-mix()with OKLab111+ 113+ 16.2+ 111+ 97+ Direct oklab()Color Usage111+ 113+ 16.2+ 111+ 97+ Conclusion
As of May 2025, CSS
color-mix()with OKLab color space is fully supported in all current versions of major browsers. Developers can confidently usecolor-mix(in oklab, ...)for perceptually accurate color blending, while still including fallbacks for legacy browsers[3][4][7].Citations:
- 1: https://developer.mozilla.org/en-US/docs/Web/CSS/color_value/color-mix
- 2: https://caniuse.com/?search=color-mix
- 3: https://developer.mozilla.org/en-US/blog/color-palettes-css-color-mix/
- 4: https://www.w3schools.com/cssref/func_color-mix.php
- 5: https://www.powermapper.com/products/sortsite/rules/bugcsscolormixfunction/
- 6: https://en.wikipedia.org/wiki/Oklab_color_space
- 7: https://developer.chrome.com/docs/css-ui/css-color-mix
- 8: https://css-tricks.com/color-mixing-with-animation-composition/
- 9: https://css-tricks.com/almanac/functions/o/oklab/
- 10: https://evilmartians.com/chronicles/oklch-in-css-why-quit-rgb-hsl
Browser support for CSS color-mix(in oklab) is now comprehensive
As of May 2025, all major evergreen browsers support
color-mix()in the OKLab color space (Chrome 111+, Edge 111+, Firefox 113+, Safari 16.2+, Opera 97+). You can confidently ship these surface utilities as-is.Optional (for legacy‐browser coverage):
- Provide a solid-color fallback before your
color-mix()declarations.- Or wrap advanced mixes in an
@supports (color-mix(in oklab, red 50%, white 50%)) { … }block.packages/project-builder-lib/src/web/hooks/useBlockUnsavedChangesNavigate.ts (1)
23-46: Excellent development diagnostic for form state debugging.This development-only diagnostic effectively identifies form state inconsistencies where the form is marked dirty but no individual fields are dirty. The implementation correctly:
- Uses conditional hook execution only in development mode
- Provides detailed error messaging with specific missing field names
- Uses proper ESLint rule exemption with justification
- Leverages existing toast notification system
The flattenObject utility usage helps identify nested field issues that could be hard to debug otherwise.
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/utils/session-cookie.ts (1)
17-42:Details
✅ Verification successful
Well-implemented session cookie naming with security considerations.
The function correctly implements environment-aware cookie naming:
Production (lines 20-22): Uses
__Host-prefix which provides important security benefits by requiring HTTPS, no Domain attribute, and Path=/. This prevents cookie injection attacks.Development (lines 23-41): Port-scoped cookies prevent conflicts in development environments. The URL parsing with proper error handling and fallback to
config.SERVER_PORTis robust.The use of origin/referer headers to handle reverse proxies in development is a thoughtful solution.
Please verify the security best practices for the
__Host-cookie prefix:
🌐 Web query:
What are the security benefits and requirements of using __Host- prefix for cookies?💡 Result:
The __Host- prefix is a security measure for cookies that provides several important protections by enforcing strict requirements on how cookies are configured and used.
Security Benefits of __Host- Prefix
The __Host- prefix provides multiple layers of security protection:
Protection against cookie injection by preventing cookies from being overwritten by insecure sources or compromised subdomains[2][3].
Domain locking ensures the cookie is only sent to the exact host that set it, not to any subdomains, reducing the attack surface[4][9].
Mitigation against session fixation attacks by preventing an attacker from setting a cookie that would be valid across multiple domains or subdomains[9].
Turns security issues into functional problems - if a developer accidentally removes security attributes from a cookie with the __Host- prefix, the cookie won't work at all rather than working insecurely, making the problem immediately obvious[1].
Forces secure-by-default implementations - if a cookie with this prefix works, it's correctly configured from a security standpoint[1].
Additional protection against Cross-Site Scripting (XSS) when combined with the HttpOnly flag, as it restricts where cookies can be sent[7].
Requirements for __Host- Prefix
For a cookie with the __Host- prefix to be accepted by browsers, it must meet all of the following strict conditions:
Must be set with the Secure attribute - ensuring the cookie is only sent over HTTPS connections[4][6][7].
Must be set from a secure origin - the cookie must be set from a URI with a secure scheme (HTTPS)[6][7].
Must not include a Domain attribute - this prevents the cookie from being sent to subdomains[4][6][9].
Must have Path attribute set to "/" - ensuring the cookie is sent to every request to the host[4][6][7].
If any of these conditions are not met, browsers will reject the cookie entirely. For example, all of the following cookie settings would be rejected:
Set-Cookie: __Host-SID=12345 Set-Cookie: __Host-SID=12345; Secure Set-Cookie: __Host-SID=12345; Domain=example.com Set-Cookie: __Host-SID=12345; Domain=example.com; Path=/ Set-Cookie: __Host-SID=12345; Secure; Domain=example.com; Path=/Only this format would be accepted from a secure origin:
Set-Cookie: __Host-SID=12345; Secure; Path=/Comparison with __Secure- Prefix
The __Host- prefix is more restrictive than the __Secure- prefix, which only requires:
- The cookie must be set with the Secure attribute
- The cookie must be set from a secure origin
The __Secure- prefix allows the use of the Domain attribute and doesn't restrict the Path, making it less restrictive but still providing some security benefits[4][9].
For maximum security, the most secure cookie configuration would be:
Set-Cookie: __Host-SID=<session token>; path=/; Secure; HttpOnly; SameSite=Strict[4]Citations:
- 1: https://www.sjoerdlangkemper.nl/2023/03/01/host-prefix-makes-cookie-problems-functional/
- 2: https://help.nextcloud.com/t/security-scan-host-prefix/9785
- 3: privacycg/CHIPS#30
- 4: https://owasp.org/www-project-web-security-testing-guide/v41/4-Web_Application_Security_Testing/06-Session_Management_Testing/02-Testing_for_Cookies_Attributes
- 5: https://www.invicti.com/white-papers/security-cookies-whitepaper/
- 6: https://greenbytes.de/tech/webdav/draft-ietf-httpbis-cookie-prefixes-latest.html
- 7: https://scotthelme.co.uk/tough-cookies/
- 8: https://privacysandbox.google.com/cookies/basics/cookie-attributes
- 9: https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/Cookies
- 10: https://www.wisp.blog/blog/understanding-httponly-cookies-and-security-best-practices
✅ Session cookie naming verified
The use of the
__Host-prefix in production fully aligns with its strict browser requirements (Secure; Path=/; no Domain) and delivers the documented security benefits—cookie injection protection, domain locking, session-fixation mitigation, and secure-by-default behavior. The development fallback logic correctly scopes cookies by port using robust URL parsing with sensible error handling.No further changes required.
plugins/baseplate-plugin-auth/src/auth/core/components/role-editor-form.tsx (1)
22-71: Excellent implementation with good practices.The component demonstrates several good practices:
- Proper TypeScript typing with generic constraints
- Clean separation of fixed vs. editable roles
- Effective use of react-hook-form's field array functionality
- Good accessibility with proper labeling
- Conditional rendering based on role properties
packages/project-builder-lib/src/schema/project-definition.ts (2)
1-1: Excellent validation standardization.The replacement of
DASHED_NAMEwithCASE_VALIDATORS.KEBAB_CASEimproves consistency across the codebase and uses a more standardized validation approach. The removal of default values fromversionandcliVersionmakes the schema requirements more explicit.This change aligns well with the broader validation consolidation mentioned in the AI summary and should improve maintainability.
Also applies to: 34-37
36-37:Details
✅ Verification successful
Verify the impact of removing default values.
The removal of default values from
versionandcliVersionfields means these are now required to be provided explicitly. Ensure this change doesn't break existing project definitions or initialization flows.
🏁 Script executed:
#!/bin/bash # Search for code that might rely on default values for these fields rg -A 3 -B 3 "version.*default|cliVersion.*default" --type ts # Look for project initialization code that might need updating rg -A 5 "projectDefinitionSchema|ProjectDefinition" --type ts | grep -E "(create|init|new)"Length of output: 80431
🏁 Script executed:
#!/bin/bash file="packages/project-builder-server/src/service/builder-service.ts" if [ -f "$file" ]; then echo "File found: $file" grep -n "protected _getInitialProjectDefinition" "$file" start_line=$(grep -n "protected _getInitialProjectDefinition" "$file" | cut -d: -f1) sed -n "${start_line},$((start_line + 50))p" "$file" else echo "File not found: $file" fiLength of output: 2131
No breaking impact from removed defaults
The
protected _getInitialProjectDefinitionin
packages/project-builder-server/src/service/builder-service.ts(lines 233 – 243) always emits both
version: '0.1.0'andcliVersion: this.cliVersionwhen creating a newproject.json. Since every new project file now explicitly includes those fields, dropping the Zod.default(...)calls in the schema will not cause validation errors or break any existing initialization flows.– packages/project-builder-server/src/service/builder-service.ts:233–243
• Returns initial JSON with explicitversionandcliVersionplugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/utils/cookie-signer.ts (1)
61-71: Approve the error handling approach.The error handling in this function is well implemented - it gracefully handles both signature verification failures and JSON parsing errors without throwing exceptions.
packages/project-builder-lib/src/definition/plugins/plugin-utils.ts (3)
59-59: Approve the bug fix for ID comparison.The change from
p.id === pluginEntityIdtopluginEntityId === p.idimproves consistency, though both comparisons are functionally equivalent. This ensures consistent comparison order throughout the codebase.
69-69: Approve the addition of configSchemaVersion tracking.Adding
configSchemaVersionto track the migration state is essential for the plugin migration system. This ensures that the configuration schema version is properly maintained.
46-46:Details
✅ Verification successful
Verify that all callers have been updated for the breaking change.
The addition of the
pluginImplementationStoreparameter is a breaking change to the function signature. Ensure all existing callers ofsetPluginConfighave been updated to provide this parameter.
🏁 Script executed:
#!/bin/bash # Description: Find all callers of setPluginConfig to verify they pass the new parameter # Expected: All callers should have been updated to pass pluginImplementationStore echo "Searching for setPluginConfig function calls..." rg -A 3 -B 1 "setPluginConfig\(" --type tsLength of output: 2185
I want to verify the updated signature of
setPluginConfigto confirm how many parameters it now requires and their order. Then I’ll check whether each caller includes the newpluginImplementationStoreargument.
🏁 Script executed:
#!/bin/bash echo "Inspecting setPluginConfig signature in plugin-utils.ts..." rg -A 10 "function setPluginConfig" packages/project-builder-lib/src/definition/plugins/plugin-utils.tsLength of output: 631
Gathering full argument lists at each call site to confirm whether the new parameter is included:
🏁 Script executed:
#!/bin/bash echo "=== auth0 auth-definition-editor.tsx ===" rg -A 6 -B 1 "PluginUtils.setPluginConfig" plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx echo "=== auth auth-definition-editor.tsx ===" rg -A 6 -B 1 "PluginUtils.setPluginConfig" plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx echo "=== storage-config.tsx ===" rg -A 6 -B 1 "PluginUtils.setPluginConfig" plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsxLength of output: 1140
All
setPluginConfigCallers UpdatedWe inspected the updated signature in
plugin-utils.ts(now requiringpluginImplementationStore) and verified all three call sites pass the new fourth argument (definitionContainer.pluginStore):
- plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx
- plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx
- plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx
No missing usages remain.
plugins/baseplate-plugin-auth/src/roles/schema.ts (2)
6-13: Approve the role schema definition.The schema correctly validates the required fields for individual roles with appropriate constraints (non-empty strings and boolean default).
24-36: Approve the duplicate validation logic.The duplicate detection logic is well implemented, using
indexOfto find the first occurrence and filtering for duplicates. The error message is clear and helpful.plugins/baseplate-plugin-auth/src/auth/core/components/auth-definition-editor.tsx (2)
1-30: LGTM: Well-structured imports and dependenciesThe imports are properly organized and include all necessary dependencies for the React form component. The separation between core library imports, UI components, and local utilities follows good practices.
85-116:Details
✅ Verification successful
Complex submit handler needs error handling verification
The submit handler performs multiple operations including feature creation, model merging, and plugin configuration. While the logic appears sound, ensure proper error handling is in place for each step.
Verify that error handling is properly implemented in the utility functions:
🏁 Script executed:
#!/bin/bash # Description: Check error handling in utility functions used by the submit handler # Check error handling in FeatureUtils.ensureFeatureByNameRecursively ast-grep --pattern $'ensureFeatureByNameRecursively($_, $_) { $$$ }' # Check error handling in createAndApplyModelMergerResults ast-grep --pattern $'createAndApplyModelMergerResults($_, $_, $_, $_) { $$$ }' # Check error handling in PluginUtils.setPluginConfig ast-grep --pattern $'setPluginConfig($_, $_, $_, $_) { $$$ }'Length of output: 218
🏁 Script executed:
#!/bin/bash # Locate utility implementations to inspect error handling rg -n "ensureFeatureByNameRecursively" -C5 rg -n "createAndApplyModelMergerResults" -C5 rg -n "setPluginConfig" -C5Length of output: 22063
🏁 Script executed:
#!/bin/bash # Inspect ensureFeatureByNameRecursively implementation rg -n "function ensureFeatureByNameRecursively" -C30 packages/project-builder-lib/src/definition/feature/feature-utils.ts # Inspect createAndApplyModelMergerResults implementation rg -n "export function createAndApplyModelMergerResults" -C30 packages/project-builder-lib/src/tools/model-merger/model-merger.ts # Inspect setPluginConfig implementation rg -n "function setPluginConfig" -C30 packages/project-builder-lib/src/definition/plugins/plugin-utils.tsLength of output: 5829
Error handling verified across utility functions
All three utilities invoked by the submit handler throw errors on failure, ensuring any issues bubble up into saveDefinitionWithFeedback for consistent user feedback:
- ensureFeatureByNameRecursively throws if it cannot construct a feature path
- createAndApplyModelMergerResults (and its helper) throw when a model can’t be applied
- setPluginConfig uses underlying throws (e.g. byIdOrThrow) for missing plugins
No additional error handling is required in the submit handler.
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.ts (3)
25-27: Descriptor schema validation is appropriateThe schema properly validates that
userSessionModelNameis a non-empty string, which is essential for the generator to function correctly.
45-96: Generator task structure is well-designedThe generator properly defines dependencies and uses the template system correctly. The import mapping and variable substitution follow good patterns for code generation.
75-92:Details
✅ Verification successful
Verify template file exists and is properly structured
Ensure the template file referenced in
FASTIFY_AUTH_MODULE_TS_TEMPLATES.servicesUserSessionServiceexists and has the expected structure.
🏁 Script executed:
#!/bin/bash # Description: Verify the template file exists and check its structure # Find and examine the template file fd -t f "ts-templates.js" plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/generated/ --exec cat {} # Also check if the template contains the expected variable placeholders rg "TPL_PRISMA_USER_SESSION" plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/Length of output: 1156
🏁 Script executed:
#!/bin/bash # Display the generated TS templates mapping to verify the key and path cat plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/generated/ts-templates.ts # Show the full content of the user-session service template to verify placeholders and structure cat plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.tsLength of output: 12046
Template file and placeholders verified
- The template
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.tsis present.- It includes all
TPL_PRISMA_USER_SESSIONplaceholders forcreate,delete,findUnique, andupdate.- The generated mapping in
generated/ts-templates.tscorrectly assignsTPL_PRISMA_USER_SESSIONinservicesUserSessionService.No further action required.
plugins/baseplate-plugin-auth/src/auth0/core/schema/plugin-definition.ts (3)
8-8: Good refactoring: Extracting roles schema improves modularityImporting
authRolesSchemafrom a dedicated roles module improves code organization and reusability across different authentication plugins.
21-21: Consistent use of external schema validationUsing the imported
authRolesSchemaensures consistent role validation across the authentication plugin ecosystem, which is a good architectural decision.
11-16:Details
✅ Verification successful
Verify consistency with migration logic
The restructuring from
userAccountModelReftomodelRefs.useraligns with the AI summary mentioning migration support. Ensure the migration logic properly handles this transformation.Verify that the migration logic exists and properly transforms the old structure:
🏁 Script executed:
#!/bin/bash # Description: Check for migration logic that handles the userAccountModelRef to modelRefs.user transformation # Search for migration files related to this plugin fd -t f "migrations.ts" plugins/baseplate-plugin-auth/src/auth0/ # Look for userAccountModelRef to modelRefs migration logic rg -A 10 -B 5 "userAccountModelRef.*modelRefs" plugins/baseplate-plugin-auth/src/auth0/Length of output: 220
🏁 Script executed:
#!/bin/bash # Display the contents of the migration file for review sed -n '1,200p' plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.tsLength of output: 560
Migration logic verified:
userAccountModelRef→modelRefs.user
Themove-modelsmigration in
plugins/baseplate-plugin-auth/src/auth0/core/schema/migrations.ts(version 1)
correctly removesuserAccountModelRefand sets:modelRefs: { user: typedConfig.userAccountModelRef, },No further action required.
packages/fastify-generators/src/generators/auth/placeholder-auth-service/placeholder-auth-service.generator.ts (4)
15-15: Empty descriptor schema is appropriate for placeholder generatorSince this is a placeholder generator for testing purposes, an empty schema makes sense as no specific configuration is needed.
17-21: Excellent documentation for generator purposeThe JSDoc comment clearly explains that this is a placeholder for testing, which helps developers understand when to use this generator.
37-59: Generator structure follows established patternsThe generator properly:
- Computes the service path within the app module
- Provides appropriate imports
- Uses the template system correctly
- Exports the service imports for use by other generators
This follows the established patterns seen in other generators.
47-56:Details
✅ Verification successful
Verify placeholder template generates valid stub code
Ensure the placeholder template creates a proper stub implementation that throws meaningful errors for unimplemented methods.
🏁 Script executed:
#!/bin/bash # Description: Verify the placeholder template structure and content # Find and examine the placeholder template fd -t f "ts-templates.js" packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ --exec cat {} # Check if the template contains proper error throwing for unimplemented methods rg -A 5 "throw.*Error\|NotImplementedError" packages/fastify-generators/src/generators/auth/placeholder-auth-service/Length of output: 245
🏁 Script executed:
#!/bin/bash # 1. Search for the template constant definition to locate the TS template file rg "AUTH_PLACEHOLDER_AUTH_SERVICE_TS_TEMPLATES" -t ts -C 5 packages/fastify-generators/src/generators/auth/placeholder-auth-service # 2. If that constant isn't found, list all files under the placeholder-auth-service folder fd -t f --max-depth 2 packages/fastify-generators/src/generators/auth/placeholder-auth-serviceLength of output: 5214
🏁 Script executed:
#!/bin/bash # Examine the generated TS templates for userSessionService stub cat packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ts-templates.ts # Search for error throwing patterns within the template rg -n "throw" packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ts-templates.ts rg -n "NotImplemented" packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/ts-templates.tsLength of output: 892
🏁 Script executed:
#!/bin/bash # List all template files in the generated folder fd . packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated -t f # Show the contents of the stub template for userSessionService cat packages/fastify-generators/src/generators/auth/placeholder-auth-service/generated/user-session.service.tsLength of output: 546
🏁 Script executed:
#!/bin/bash # Search for the stub template file across the repository fd user-session.service.ts -t f # If found, show its contents and look for error-throwing patterns fd user-session.service.ts -t f --exec cat {} \; | tee stub_contents.txt rg -n "throw" stub_contents.txt rg -n "NotImplemented" stub_contents.txtLength of output: 824
🏁 Script executed:
#!/bin/bash # Show the placeholder-auth-service template file content TEMPLATE_PATH="packages/fastify-generators/src/generators/auth/placeholder-auth-service/templates/user-session.service.ts" if [ -f "$TEMPLATE_PATH" ]; then echo "== Contents of user-session.service.ts ==" sed -n '1,200p' "$TEMPLATE_PATH" echo echo "== throw patterns ==" rg -n "throw" "$TEMPLATE_PATH" || echo "No throw found" echo echo "== NotImplemented patterns ==" rg -n "NotImplemented" "$TEMPLATE_PATH" || echo "No NotImplemented found" else echo "Template file not found at $TEMPLATE_PATH" fiLength of output: 2047
Placeholder stub methods correctly throw “Not implemented” errors
The generated stub at
packages/fastify-generators/src/generators/auth/placeholder-auth-service/templates/user-session.service.ts
includesthrow new Error('Not implemented')in both
getSessionInfoFromRequestgetSessionInfoFromTokenNo further changes are needed.
plugins/baseplate-plugin-auth/src/auth0/core/components/auth-definition-editor.tsx (1)
66-78: Potentially misleading diff preview
createModelMergerResults(modelRefs, desiredModels …)uses the livemodelRefsas both the “current” & “desired” identifiers (unless the refs are IDs).
For new plugins that reference models by name, the diff will always treat the model as new – even if the model already exists in the project under the same name.Passing the resolved model IDs for
current(when they already exist) gives a more accurate preview and prevents accidental duplicates.plugins/baseplate-plugin-auth/src/auth/core/schema/models.ts (1)
15-48: Overall model shape looks solidPrimary keys, timestamps and UUID generation are well-defined and match our
current conventions. 👍plugins/baseplate-plugin-storage/src/storage/core/components/storage-config.tsx (2)
36-52: Nice use of sensible defaults &useMemoAutomatically falling back to a default
Filemodel /storagefeature keeps
the UX smooth for first-time users. Good job.
80-87:Details
❌ Incorrect review comment
ensureFeatureByNameRecursivelyis called with an id, not a nameThe helper’s name (and its usage elsewhere) suggests it expects the feature
name. Passing the id risks:
- creating a duplicate feature named like the id string, or
- a runtime error if the helper validates the input.
Confirm the expected parameter; if it is indeed a name, convert first:
-const featureRef = FeatureUtils.ensureFeatureByNameRecursively( - draftConfig, - data.storageFeatureRef, -); +const featureRef = FeatureUtils.ensureFeatureByNameRecursively( + draftConfig, + FeatureUtils.getFeatureNameById(draftConfig, data.storageFeatureRef), +);
🏁 Script executed:
#!/bin/bash # Locate the definition of ensureFeatureByNameRecursively and any references to getFeatureNameById rg --color always -n 'ensureFeatureByNameRecursively' rg --color always -n 'getFeatureNameById'Length of output: 1640
🏁 Script executed:
#!/bin/bash # Display signature and surrounding context for ensureFeatureByNameRecursively rg -n -C3 "function ensureFeatureByNameRecursively" packages/project-builder-lib/src/definition/feature/feature-utils.ts # Display signature and surrounding context for getFeatureNameById rg -n -C3 "function getFeatureNameById" packages/project-builder-lib/src/definition/feature/feature-utils.tsLength of output: 627
🏁 Script executed:
#!/bin/bash # Show the full implementation of ensureFeatureByNameRecursively rg -n -A50 "function ensureFeatureByNameRecursively" packages/project-builder-lib/src/definition/feature/feature-utils.tsLength of output: 1610
Incorrect assumption:
ensureFeatureByNameRecursivelyalready accepts IDs
The implementation at lines 65–67 checksfeatureEntityType.isId(nameOrId)and immediately returns the input if it’s an ID, so passingdata.storageFeatureRef(the feature ID) is safe and will not create duplicates nor throw. You can ignore the suggested conversion.Likely an incorrect or invalid review comment.
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts (1)
71-80:idfield is set tosub; should it instead reference the DB session id?
AuthUserSessionInfo.idusually denotes a session identifier (see the cookie implementation later).
Here you populate it withverifiedJwt.sub, i.e. the AuthProvider subject, which:
- Is not unique per session (a user can create multiple concurrent sessions).
- Might clash with the cookie service where
idequals the DB row id.Please confirm the semantics; if an actual session id is required, either remove the field (optional) or persist a session entry in the DB and return its primary key.
| ?.filter( | ||
| (relation) => | ||
| relation.modelRef === storageDefinition.fileModelRef && | ||
| relation.modelRef === storageDefinition.modelRefs.file && |
There was a problem hiding this comment.
💡 Verification agent
🧩 Analysis chain
Verify consistent usage of the new modelRefs structure.
The change from storageDefinition.fileModelRef to storageDefinition.modelRefs.file represents a structural API change. Please ensure all references to the old fileModelRef property have been updated throughout the codebase.
🏁 Script executed:
#!/bin/bash
# Description: Verify that all usages of fileModelRef have been updated to use modelRefs.file
# Expected: No remaining references to the old fileModelRef property
# Search for any remaining references to fileModelRef
rg "fileModelRef" --type typescript --type javascript
# Search for the new modelRefs.file pattern to confirm it's being used consistently
rg "modelRefs\.file" --type typescript --type javascript -A 2 -B 2Length of output: 192
🏁 Script executed:
#!/bin/bash
# Corrected search for remaining references to fileModelRef and usage of modelRefs.file
# This uses filename globs instead of rg type filters.
# Search for any occurrences of the old flat property
rg "fileModelRef" -g "*.{ts,tsx,js,jsx}" -n
# Search for usages of the new nested property, with context
rg "modelRefs\.file" -g "*.{ts,tsx,js,jsx}" -n -A2 -B2Length of output: 5163
Update migration schema to use modelRefs.file
The nested modelRefs.file API is applied everywhere except in the plugin-config migration definitions—migrations.ts still uses the old fileModelRef key. Please update the migration to map and default the new nested property correctly.
• File: plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts
– Line 9: change the type from fileModelRef: string to a nested modelRefs.file: string
– Line 15: update the default from fileModelRef: undefined to modelRefs: { file: undefined }
– Line 18: replace file: typedConfig.fileModelRef with file: typedConfig.modelRefs.file
🤖 Prompt for AI Agents
In plugins/baseplate-plugin-storage/src/storage/core/schema/migrations.ts around
lines 9 to 18, update the migration schema to use the new nested modelRefs.file
structure instead of the old flat fileModelRef property. Change the type
definition from fileModelRef: string to modelRefs: { file: string }, update the
default value from fileModelRef: undefined to modelRefs: { file: undefined },
and replace all references like file: typedConfig.fileModelRef with file:
typedConfig.modelRefs.file to ensure consistent usage of the new API structure.
| @@ -0,0 +1,5 @@ | |||
| // @ts-nocheck | |||
There was a problem hiding this comment.
🛠️ Refactor suggestion
Consider removing or justifying the @ts-nocheck directive.
The @ts-nocheck directive disables all TypeScript checking for this file. While this might be intentional for a placeholder template, it could hide legitimate type issues and reduce code quality.
Consider either:
- Removing the directive if not needed
- Using more specific type suppressions like
@ts-expect-errorfor specific lines - Adding a comment explaining why TypeScript checking is disabled
🤖 Prompt for AI Agents
In
packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useLogOut.ts
at line 1, the file has a @ts-nocheck directive that disables all TypeScript
checking. To fix this, either remove the @ts-nocheck if type errors are not
expected, replace it with more targeted suppressions like @ts-expect-error on
specific lines where needed, or add a comment explaining why full TypeScript
checking is disabled to justify its presence.
| export function useRequiredUserId(): string { | ||
| throw new Error('Not implemented'); | ||
| } |
There was a problem hiding this comment.
🛠️ Refactor suggestion
Improve placeholder implementation to avoid runtime crashes.
Throwing errors in React hooks can cause component crashes and poor developer experience. Consider returning a fallback value or using console warnings instead.
-export function useRequiredUserId(): string {
- throw new Error('Not implemented');
-}
+/**
+ * Placeholder hook for required user ID.
+ * TODO: Implement actual authentication logic.
+ */
+export function useRequiredUserId(): string {
+ console.warn('useRequiredUserId is not implemented - using placeholder');
+ return 'placeholder-user-id';
+}This approach:
- Provides a working fallback during development
- Warns developers about the placeholder status
- Prevents component crashes
- Includes documentation for future implementers
🤖 Prompt for AI Agents
In
packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useRequiredUserId.ts
around lines 3 to 5, the current placeholder hook throws an error causing
runtime crashes. Replace the throw statement with a fallback return value like
an empty string or null, add a console warning to notify developers that this is
a placeholder implementation, and include a comment explaining that this is
temporary and should be properly implemented later. This prevents crashes while
signaling the need for future implementation.
| @@ -0,0 +1,5 @@ | |||
| // @ts-nocheck | |||
There was a problem hiding this comment.
Remove @ts-nocheck directive and implement proper TypeScript types.
The @ts-nocheck directive disables all TypeScript checking, which defeats the purpose of using TypeScript and can hide important type errors.
-// @ts-nocheck📝 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.
| // @ts-nocheck | |
| export function useRequiredUserId(): string { | |
| throw new Error('Not implemented'); | |
| } |
🤖 Prompt for AI Agents
In
packages/react-generators/src/generators/auth/placeholder-auth-hooks/templates/useRequiredUserId.ts
at line 1, remove the @ts-nocheck directive and replace it by adding proper
TypeScript type annotations throughout the file to ensure type safety and enable
TypeScript to perform its checks correctly.
| builder.queryField('currentUser', (t) => | ||
| t.prismaField({ | ||
| type: 'User', | ||
| nullable: true, | ||
| resolve: async (query, root, args, { auth }) => { | ||
| if (!auth.userId) { | ||
| return null; | ||
| } | ||
|
|
||
| return TPL_PRISMA_USER.findUniqueOrThrow({ | ||
| ...query, | ||
| where: { id: auth.userId }, | ||
| }); | ||
| }, | ||
| }), | ||
| ); |
There was a problem hiding this comment.
💡 Verification agent
🧩 Analysis chain
Verify template variables and approve query logic.
The GraphQL query implementation is well-structured with proper null handling for unauthenticated users. However, ensure that the template variables resolve correctly during code generation.
🏁 Script executed:
#!/bin/bash
# Verify template variables are properly defined in the generator
rg -A 3 -B 3 "TPL_PRISMA_USER|%pothosImports" --type tsLength of output: 18065
🏁 Script executed:
#!/bin/bash
# Check importMapProviders and '%pothosImports' mapping in generated templates
rg -C10 "importMapProviders" plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/generated/ts-templates.ts
rg -C3 "'%pothosImports'" plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/generated/ts-templates.tsLength of output: 3092
🏁 Script executed:
#!/bin/bash
# Inspect variable mappings for schema-user-session-queries in the auth module generator
rg -C5 "schema-user-session-queries" plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.tsLength of output: 131
Missing template variable mappings for user‐session schema templates
The TPL_PRISMA_USER (and for the payload template, TPL_USER_OBJECT_TYPE) placeholders are declared in your generated TS templates but never supplied in the generator—so codegen will fail to replace them. Please update auth-module.generator.ts to pass these Prisma fragments when registering the templates.
Locations to fix:
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.ts
Required changes (example sketch):
// around where you register the `schemaUserSessionQueries` template
{
template: schemaUserSessionQueries,
destination: 'schema/user-session.queries.ts',
- variables: {},
+ variables: {
+ TPL_PRISMA_USER: prismaOutput.getPrismaModelFragment(userModelName),
+ },
}
// and for `userSessionPayloadObjectType`
{
template: userSessionPayloadObjectType,
destination: 'schema/user-session-payload.object-type.ts',
- variables: { },
+ variables: {
+ TPL_PRISMA_USER: prismaOutput.getPrismaModelFragment(userModelName),
+ TPL_USER_OBJECT_TYPE: userObjectTypeName,
+ },
}Please verify and add the missing mappings so the %pothosImports and Prisma model fragments resolve correctly.
Committable suggestion skipped: line range outside the PR's diff.
🤖 Prompt for AI Agents
In
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/auth-module.generator.ts
around the section where templates are registered, the placeholders
TPL_PRISMA_USER and TPL_USER_OBJECT_TYPE used in the user-session schema
templates are not being supplied. To fix this, update the generator code to
include these missing template variable mappings by passing the appropriate
Prisma model fragments and import mappings when registering the templates. This
will ensure the code generation replaces these placeholders correctly and
prevents runtime errors.
| if (!userId) { | ||
| throw new Error(`Missing user id in JWT`); | ||
| } | ||
|
|
||
| const user = await TPL_USER_MODEL.findUnique({ where: { id: userId } }); | ||
|
|
||
| // create user if one does not exist already | ||
| if (!email) { | ||
| throw new Error(`Missing email claim in JWT`); | ||
| } |
There was a problem hiding this comment.
email validation is executed even when the user already exists
The email presence check happens before you know whether the user was found:
const user = await TPL_USER_MODEL.findUnique({ … });
if (!email) throw new Error('Missing email claim');
// ↖ unconditional
if (!user) {
// create user …
}If the user already exists in the DB (so creation is not required) an absent email claim should not be considered fatal – you already have the canonical e-mail in the DB.
- if (!email) {
- throw new Error(`Missing email claim in JWT`);
- }
- if (!user) {
+ if (!user) {
+ if (!email) {
+ throw new Error(`Missing email claim in JWT`);
+ }
// create user …🤖 Prompt for AI Agents
In
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts
around lines 47 to 56, the code checks for the presence of the email claim
before verifying if the user exists, causing an error if email is missing even
when the user is found. To fix this, move the email presence check inside the
block that handles user creation, so the email is only required when the user
does not already exist.
| @@ -0,0 +1,101 @@ | |||
| // @ts-nocheck | |||
There was a problem hiding this comment.
🛠️ Refactor suggestion
Remove blanket @ts-nocheck – we are losing type-safety where we need it most
Placing // @ts-nocheck at the top disables the whole TypeScript safety-net for this template.
Because the file relies on several dynamic placeholders (%xxxImports) the temptation to silence the compiler is understandable, yet we still want the compiler to catch everything else (e.g. wrong Prisma field names, forgotten await, etc.).
Suggestion: keep the comment, but scope-disable only the lines that truly fail to type-check once the placeholders are substituted (use @ts-expect-error or @ts-ignore on a per-line basis).
This preserves the developer UX without sacrificing safety.
🤖 Prompt for AI Agents
In
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/user-session.service.ts
at line 1, remove the blanket // @ts-nocheck comment that disables TypeScript
checking for the entire file. Instead, identify specific lines that fail
type-checking due to dynamic placeholders and add scoped comments like //
@ts-expect-error or // @ts-ignore only on those lines. This approach maintains
type safety for the rest of the file while allowing exceptions where necessary.
There was a problem hiding this comment.
@ts-nocheck is allowed in templates since they are not expected to be type-safe. Only when generated.
There was a problem hiding this comment.
Seems like the humans are having a chat. I'll hop back into my burrow for now. If you need me again, just tag @coderabbitai in a new comment, and I'll come hopping out!
| export const basePluginSchema = zEnt( | ||
| z.object({ | ||
| packageName: z.string(), | ||
| name: z.string(), | ||
| version: z.string(), | ||
| config: z.unknown(), | ||
| configSchemaVersion: z.number().optional(), | ||
| }), |
There was a problem hiding this comment.
🛠️ Refactor suggestion
config is typed as unknown, defeating downstream type-safety
While the later pluginWithConfigSchema intersection tightens the config shape, basePluginSchema still exports the config property as unknown, so consumers of BasePlugin lose intellisense and have to cast manually.
You can preserve widening while still providing real types:
config: z.never().optional(), // will be replaced in intersectionor export two separate schemas (raw + typed) to keep BasePlugin useful.
🤖 Prompt for AI Agents
In packages/project-builder-lib/src/schema/plugins/definition.ts around lines 8
to 15, the basePluginSchema defines the config property as z.unknown(), which
causes loss of type safety and intellisense for consumers of BasePlugin. To fix
this, change the config property type to z.never().optional() in
basePluginSchema so it acts as a placeholder that will be replaced in
intersections, preserving type safety and improving developer experience without
manual casting.
| // Check Origin header for non-GET/HEAD requests to prevent CSRF attacks | ||
| if ( | ||
| (req.method !== 'GET' || | ||
| req.headers.upgrade?.toLowerCase() === 'websocket') && | ||
| req.method !== 'HEAD' && | ||
| !verifyRequestOrigin(req, [req.host]) | ||
| ) { | ||
| throw new ForbiddenError('Invalid Origin header'); | ||
| } |
There was a problem hiding this comment.
🛠️ Refactor suggestion
req.host is not a documented Fastify property
Fastify exposes req.hostname (and req.headers.host). Using req.host will be undefined unless patched, making the origin check ineffective and potentially blocking all non-GET requests.
- !verifyRequestOrigin(req, [req.host])
+ !verifyRequestOrigin(req, [req.hostname])📝 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.
| // Check Origin header for non-GET/HEAD requests to prevent CSRF attacks | |
| if ( | |
| (req.method !== 'GET' || | |
| req.headers.upgrade?.toLowerCase() === 'websocket') && | |
| req.method !== 'HEAD' && | |
| !verifyRequestOrigin(req, [req.host]) | |
| ) { | |
| throw new ForbiddenError('Invalid Origin header'); | |
| } | |
| // Check Origin header for non-GET/HEAD requests to prevent CSRF attacks | |
| if ( | |
| (req.method !== 'GET' || | |
| req.headers.upgrade?.toLowerCase() === 'websocket') && | |
| req.method !== 'HEAD' && | |
| !verifyRequestOrigin(req, [req.hostname]) | |
| ) { | |
| throw new ForbiddenError('Invalid Origin header'); | |
| } |
🤖 Prompt for AI Agents
In
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts
around lines 161 to 169, replace the use of the undocumented property req.host
with req.hostname or req.headers.host, which are the correct Fastify properties.
This change ensures the origin check uses a valid host value, preventing it from
being undefined and blocking all non-GET requests incorrectly.
| ): { valid: boolean; newExpiry: Date | null } { | ||
| // check if session is expired | ||
| if (userSession.expiresAt < currentDate) { | ||
| return { valid: false, newExpiry: null }; | ||
| } | ||
|
|
||
| // check if session needs renewal | ||
| const shouldRenewBy = | ||
| userSession.renewedAt.getTime() + USER_SESSION_RENEWAL_THRESHOLD_SEC * 1000; | ||
|
|
||
| if (shouldRenewBy < currentDate.getTime()) { | ||
| const newExpiry = currentDate.getTime() + USER_SESSION_DURATION_SEC * 1000; | ||
| const maxExpiry = | ||
| USER_SESSION_MAX_LIFETIME_SEC === 0 | ||
| ? undefined | ||
| : userSession.createdAt.getTime() + | ||
| USER_SESSION_MAX_LIFETIME_SEC * 1000; | ||
| return { | ||
| valid: true, | ||
| newExpiry: new Date(Math.min(newExpiry, maxExpiry ?? newExpiry)), | ||
| }; | ||
| } | ||
|
|
There was a problem hiding this comment.
validateSessionExpiry may renew past the max-lifetime and immediately expire
When the session already exceeded USER_SESSION_MAX_LIFETIME_SEC, the computed newExpiry is clamped to maxExpiry, which is in the past.
The caller then sets a cookie with an expiry earlier than currentDate, effectively logging the user out on the next request.
Guard for this edge case:
- return { valid: true, newExpiry: new Date(Math.min(newExpiry, maxExpiry ?? newExpiry)) };
+ const clampedExpiry = new Date(Math.min(newExpiry, maxExpiry ?? newExpiry));
+ if (clampedExpiry <= currentDate) {
+ return { valid: false, newExpiry: null }; // cannot renew
+ }
+ return { valid: true, newExpiry: clampedExpiry };Committable suggestion skipped: line range outside the PR's diff.
🤖 Prompt for AI Agents
In
plugins/baseplate-plugin-auth/src/auth/generators/fastify/auth-module/templates/services/user-session.service.ts
between lines 58 and 80, the validateSessionExpiry function may return a
newExpiry date that is in the past if the session has already exceeded
USER_SESSION_MAX_LIFETIME_SEC, causing immediate logout. To fix this, add a
check after computing newExpiry and maxExpiry to verify if maxExpiry is defined
and less than or equal to currentDate; if so, return valid: false and newExpiry:
null to prevent renewing an expired session.
| const results = createModelMergerResults( | ||
| current, | ||
| desired, | ||
| definitionContainer, | ||
| { siblingModels }, | ||
| ); | ||
| return mapValues(results, (result, key) => | ||
| result | ||
| ? applyModelMergerResultInPlace( | ||
| draftConfig, | ||
| result, | ||
| definitionContainer, | ||
| { siblingModels }, | ||
| ) | ||
| : desired[key].name, | ||
| ); | ||
| } |
There was a problem hiding this comment.
Bug: createAndApplyModelMergerResults returns a name instead of an ID when no changes are detected
When result is undefined, the function falls back to desired[key].name.
Down-stream callers (e.g. UI editors and subsequent merger passes) expect the model ID so they can mutate the correct model. Returning a name silently breaks those flows and may cause duplicate-model inserts or look-ups by name that unexpectedly fail if names are not unique.
- ? applyModelMergerResultInPlace(
- draftConfig,
- result,
- definitionContainer,
- { siblingModels },
- )
- : desired[key].name,
+ ? applyModelMergerResultInPlace(
+ draftConfig,
+ result,
+ definitionContainer,
+ { siblingModels },
+ )
+ : (current[key] // prefer the current ID
+ ?? ModelUtils.byNameOrThrow( // fall back to definition look-up
+ draftConfig,
+ desired[key].name,
+ ).id),• Guarantees the caller always receives an ID
• Avoids accidental ID→name type mismatches
• Preserves behaviour when the model is genuinely new (current[key] is undefined and result is not generated – an impossible state and therefore safe).
📝 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.
| const results = createModelMergerResults( | |
| current, | |
| desired, | |
| definitionContainer, | |
| { siblingModels }, | |
| ); | |
| return mapValues(results, (result, key) => | |
| result | |
| ? applyModelMergerResultInPlace( | |
| draftConfig, | |
| result, | |
| definitionContainer, | |
| { siblingModels }, | |
| ) | |
| : desired[key].name, | |
| ); | |
| } | |
| const results = createModelMergerResults( | |
| current, | |
| desired, | |
| definitionContainer, | |
| { siblingModels }, | |
| ); | |
| return mapValues(results, (result, key) => | |
| result | |
| ? applyModelMergerResultInPlace( | |
| draftConfig, | |
| result, | |
| definitionContainer, | |
| { siblingModels }, | |
| ) | |
| : (current[key] // prefer the current ID | |
| ?? ModelUtils.byNameOrThrow( // fall back to definition look-up | |
| draftConfig, | |
| desired[key].name, | |
| ).id), | |
| ); | |
| } |
🤖 Prompt for AI Agents
In packages/project-builder-lib/src/tools/model-merger/model-merger.ts around
lines 419 to 435, the function returns desired[key].name when result is
undefined, but callers expect a model ID to correctly identify models. To fix
this, change the fallback to return the model ID from desired[key] instead of
the name, ensuring the function always returns an ID and preventing downstream
errors caused by ID-name mismatches.
There was a problem hiding this comment.
Actionable comments posted: 1
🔭 Outside diff range comments (1)
plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/templates/user-session.service.ts (1)
1-1:⚠️ Potential issueRemove the @ts-nocheck directive to enable TypeScript validation.
The
@ts-nocheckdirective disables all TypeScript checking for this file, which eliminates the benefits of static type checking and could hide potential runtime errors.-// @ts-nocheckConsider addressing any TypeScript errors that surface after removing this directive rather than suppressing them globally.
♻️ Duplicate comments (3)
packages/project-builder-lib/src/plugins/migrations/run-migrations.ts (3)
17-18: 🛠️ Refactor suggestionAvoid global
setAutoFreeze(false)side-effectsCalling
setAutoFreeze(false)at module scope disables Immer’s safety checks for every subsequentproducecall in the entire process, not just for this function. This reproduces a concern already raised in an earlier review.A low-risk fix is to confine the override to the local scope and restore the default immediately after producing the new state:
- setAutoFreeze(false); - return produce(projectDefinition, (draft) => { + setAutoFreeze(false); + const nextDefinition = produce(projectDefinition, (draft) => { /* …migration logic… */ }); + setAutoFreeze(true); + return nextDefinition;Alternatively, move the call inside the
producecallback to isolate the effect.
31-33: 🛠️ Refactor suggestionRemove unsafe
as unknowncast; enforce type-safe migrationsCasting
pluginDefinition.configtounknowndefeats TypeScript’s checks and was highlighted in a previous review. Define a generic interface for migrations (e.g.Migration<TConfig>) so thatmigrateaccepts and returns a strongly-typed configuration, eliminating the need for this cast and preventing runtime mismatches.
28-40: 🛠️ Refactor suggestionGuarantee deterministic migration order
Execution relies on
pluginMigrationsalready being sorted byversion. If the array is mis-ordered, migrations could run out of sequence. Either sort the array before iterating or validate ascending order; this was suggested previously but is still unaddressed.
🧹 Nitpick comments (1)
plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/templates/user-session.service.ts (1)
89-98: Review the manual header manipulation approach.The
getSessionInfoFromTokenmethod manually sets the authorization header, which is documented as a workaround but could be fragile. Consider whether there's a more robust approach to token verification.async getSessionInfoFromToken( req: FastifyRequest, token?: string | null, ): Promise<AuthUserSessionInfo | undefined> { - // We have to manually add the header to the request since we can't - // use server.jwt.verify due to an error - req.headers.authorization = token ?? undefined; - - return this.getSessionInfoFromRequest(req); + if (!token) { + return undefined; + } + + // Create a temporary request object with the token + const tempReq = { ...req, headers: { ...req.headers, authorization: token } }; + return this.getSessionInfoFromRequest(tempReq as FastifyRequest); }This approach avoids mutating the original request object.
📜 Review details
Configuration used: .coderabbit.yaml
Review profile: CHILL
Plan: Lite
📒 Files selected for processing (5)
packages/project-builder-lib/src/definition/project-definition-container.test-helper.ts(1 hunks)packages/project-builder-lib/src/plugins/migrations/run-migrations.ts(1 hunks)packages/project-builder-lib/src/plugins/spec/config-spec.ts(2 hunks)packages/project-builder-lib/src/schema/project-definition.ts(2 hunks)plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/templates/user-session.service.ts(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (2)
- packages/project-builder-lib/src/schema/project-definition.ts
- packages/project-builder-lib/src/plugins/spec/config-spec.ts
🧰 Additional context used
🧬 Code Graph Analysis (1)
packages/project-builder-lib/src/plugins/migrations/run-migrations.ts (4)
packages/project-builder-lib/src/schema/project-definition.ts (1)
ProjectDefinition(63-63)packages/project-builder-lib/src/plugins/schema/store.ts (1)
PluginImplementationStore(3-25)packages/project-builder-lib/src/plugins/spec/config-spec.ts (1)
pluginConfigSpec(89-91)packages/project-builder-lib/src/schema/plugins/entity-types.ts (1)
pluginEntityType(3-3)
🔇 Additional comments (3)
packages/project-builder-lib/src/definition/project-definition-container.test-helper.ts (1)
19-19:Details
❓ Verification inconclusive
Good alignment with schema updates.
Adding the
packageScopeproperty with an empty string default ensures test project definitions match the updated schema. This maintains consistency across the test suite.Please verify that existing tests still pass with this addition:
🏁 Script executed:
#!/bin/bash # Description: Check for any tests that might be affected by the packageScope addition # Expected: Tests should pass or any failures should be related to the schema change # Search for tests that might be creating ProjectDefinition objects manually rg -A 10 -B 5 "ProjectDefinition.*\{" --type ts --type js # Look for any tests that might be checking for specific property counts or structures rg -A 5 "Object\.keys.*ProjectDefinition|Object\.entries.*ProjectDefinition" --type ts --type jsLength of output: 66970
Approve addition of
packageScope—matches updated schemaNo tests appear to manually inspect the raw
ProjectDefinitionshape or count its keys:
- Scanned for
Object.keys/entriesonProjectDefinition– no matches.- No other manual constructions of
ProjectDefinitionoutside the test helper.Please run the full test suite to confirm there are no regressions.
plugins/baseplate-plugin-auth/src/auth0/generators/fastify/auth0-module/templates/user-session.service.ts (2)
55-57: Good optimization: Email validation moved to user creation block.Moving the email validation inside the user creation conditional block is a good optimization that improves performance by only validating the email claim when it's actually needed for creating new users.
59-68:Details
❓ Verification inconclusive
Verify the race condition handling approach.
The use of
createManywithskipDuplicates: trueis intended to handle race conditions, but this approach may not work as expected in all database systems.Consider whether
upsertmight be more appropriate for handling concurrent user creation scenarios, depending on your database and requirements.
🏁 Script executed:
#!/bin/bash # Description: Check if Prisma's createMany with skipDuplicates is used consistently across the codebase # Expected: Find other usages to verify this is a standard pattern echo "Searching for createMany usage patterns..." rg -A 3 -B 1 "createMany.*skipDuplicates" echo -e "\nSearching for alternative user creation patterns..." rg -A 5 "\.create.*user|\.upsert.*user" --type tsLength of output: 309
Confirm race‐condition strategy for user creation
I didn’t find any other occurrences of
createMany({ skipDuplicates: true })orupsertin the repo. Since the behavior ofskipDuplicatescan vary by database provider, please verify that this approach meets your concurrency requirements. Consider the following to ensure robust handling:
- Ensure your database has a unique constraint on
auth0Id(and/orid).- Switch to a single‐call atomic upsert, for example:
await prisma.user.upsert({ where: { auth0Id: verifiedJwt.sub }, create: { id: userId, auth0Id: verifiedJwt.sub, email }, update: {}, });- Alternatively, use a
createinside a transaction with retry logic on unique‐constraint failures.
Note: This is part 1 of the implementation but wanted to get a version in before we do a mega-commit
Summary by CodeRabbit
New Features
Improvements
Bug Fixes
Documentation
Chores