Skip to content

Conversation

@jvega190
Copy link
Member

@jvega190 jvega190 commented Jan 15, 2026

craftercms/craftercms#8507

Summary by CodeRabbit

  • Improvements
    • Forms engine now lets you specify an alternative content type/template when updating existing items, enabling flexible content-type reassignment during edits.
    • The form flow will mark edits as having pending changes when an alternative content type/template is applied, improving clarity in edit dialogs.

✏️ Tip: You can customize this high-level summary in your review settings.

@coderabbitai
Copy link

coderabbitai bot commented Jan 15, 2026

Walkthrough

Introduces an optional changeTypeId that is passed from the system action into the FormsEngine and into fetchUpdateRequirements, allowing the content-type used when calculating update requirements to be overridden.

Changes

Cohort / File(s) Summary
FormsEngine component
ui/app/src/components/FormsEngine/FormsEngine.tsx
Added changeTypeId?: string to UpdateModeProps.update; useMount sets hasPendingChanges when update.changeTypeId is present; changeTypeId propagated into fetchUpdateRequirements call.
Form utilities
ui/app/src/components/FormsEngine/lib/formUtils.tsx
fetchUpdateRequirements signature extended with optional changeTypeId; content-type lookup changed to contentTypesById[changeTypeId ?? item.contentTypeId].
System actions
ui/app/src/utils/system.ts
pickShowContentFormAction now includes changeTypeId: oldProps.changeTemplate in the update payload when not creating new content.

Sequence Diagram(s)

mermaid
sequenceDiagram
participant System as System Action
participant UI as FormsEngine Component
participant Utils as fetchUpdateRequirements
System->>UI: dispatch show content form with update{ path, changeTypeId }
UI->>UI: useMount -> set hasPendingChanges if changeTypeId present
UI->>Utils: fetchUpdateRequirements(siteId, path, ..., contentTypesById, changeTypeId)
Utils->>Utils: resolve contentType = contentTypesById[changeTypeId ?? item.contentTypeId]
Utils-->>UI: return FormRequirementsResponse
UI-->>System: render form with resolved requirements

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

Suggested reviewers

  • sumerjabri
  • rart
🚥 Pre-merge checks | ✅ 1 | ❌ 2
❌ Failed checks (1 warning, 1 inconclusive)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 75.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Description check ❓ Inconclusive The description provides only a ticket reference URL without additional context, detail, or information about the changes, objectives, or testing. Expand the description to explain what the change content type functionality does, why it was needed, and any relevant testing or implementation notes.
✅ Passed checks (1 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly identifies the main feature being implemented: change content type functionality for FE2, with reference to the ticket number.

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

✨ Finishing touches
  • 📝 Generate docstrings


📜 Recent review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 704470b and 33e0ba7.

📒 Files selected for processing (1)
  • ui/app/src/components/FormsEngine/lib/formUtils.tsx
🚧 Files skipped from review as they are similar to previous changes (1)
  • ui/app/src/components/FormsEngine/lib/formUtils.tsx
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Codacy Static Code Analysis

✏️ Tip: You can disable this entire section by setting review_details to false in your review settings.


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

❤️ Share

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

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

Caution

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

⚠️ Outside diff range comments (1)
ui/app/src/components/FormsEngine/lib/formUtils.tsx (1)

379-393: Type mismatch: changeTypeId should allow undefined.

The parameter type is string, but the caller in FormsEngine.tsx (line 451) passes update.changeTypeId which is string | undefined. This will cause a TypeScript error in strict mode.

🔧 Suggested fix
 export function fetchUpdateRequirements({
 	siteId,
 	path,
 	modelId,
 	readonly,
 	contentTypesById,
 	changeTypeId
 }: {
 	siteId: string;
 	path: string;
 	modelId: string;
 	readonly: boolean;
 	contentTypesById: LookupTable<ContentType>;
-	changeTypeId: string;
+	changeTypeId?: string;
 }): Observable<FormRequirementsResponse> {
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a696155 and 704470b.

📒 Files selected for processing (3)
  • ui/app/src/components/FormsEngine/FormsEngine.tsx
  • ui/app/src/components/FormsEngine/lib/formUtils.tsx
  • ui/app/src/utils/system.ts
🧰 Additional context used
🧠 Learnings (7)
📚 Learning: 2025-08-19T20:34:01.813Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4600
File: ui/app/src/components/PluginManagement/PluginManagement.tsx:361-361
Timestamp: 2025-08-19T20:34:01.813Z
Learning: In the EnhancedDialog migration, only dialog components that have been refactored to use context-based state management should have their onSubmittingAndOrPendingChange prop renamed to updateSubmittingOrHasPendingChanges. Components that haven't been migrated to the new EnhancedDialog context system should continue using the original onSubmittingAndOrPendingChange prop name.

Applied to files:

  • ui/app/src/components/FormsEngine/FormsEngine.tsx
  • ui/app/src/utils/system.ts
📚 Learning: 2025-08-19T18:43:20.285Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4600
File: ui/app/src/components/CreatePreviewTokenDialog/CreatePreviewTokenDialog.tsx:149-151
Timestamp: 2025-08-19T18:43:20.285Z
Learning: The useUpdateRefs hook in ui/app/src/hooks/useUpdateRefs.ts has both a named export and a default export, so both import styles (default import and named import) are valid and will work correctly.

Applied to files:

  • ui/app/src/components/FormsEngine/FormsEngine.tsx
📚 Learning: 2025-08-19T18:43:20.285Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4600
File: ui/app/src/components/CreatePreviewTokenDialog/CreatePreviewTokenDialog.tsx:149-151
Timestamp: 2025-08-19T18:43:20.285Z
Learning: The useUpdateRefs hook in ui/app/src/hooks/useUpdateRefs.ts has both a named export (export function useUpdateRefs) and a default export (export default useUpdateRefs), making both import styles valid: default import and named import.

Applied to files:

  • ui/app/src/components/FormsEngine/FormsEngine.tsx
📚 Learning: 2025-12-11T21:18:51.227Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4708
File: ui/app/src/components/PreviewAudiencesPanel/PreviewAudiencesPanel.tsx:72-74
Timestamp: 2025-12-11T21:18:51.227Z
Learning: When reviewing components in ui/app/src/components, verify that props expecting a title (e.g., EmptyState) allow ReactNode or MessageDescriptor (e.g., React elements like FormattedMessage and MessageDescriptor objects). Ensure TS types reflect ReactNode | MessageDescriptor where appropriate, and audit usages to avoid passing incompatible values. Update tests or PropTypes/TypeScript types as needed to maintain correct typing and rendering behavior.

Applied to files:

  • ui/app/src/components/FormsEngine/FormsEngine.tsx
  • ui/app/src/components/FormsEngine/lib/formUtils.tsx
📚 Learning: 2025-08-27T23:08:05.012Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4451
File: ui/app/src/components/ContentTypeManagement/utils.ts:253-264
Timestamp: 2025-08-27T23:08:05.012Z
Learning: In the ContentTypeManagement utils.ts reverseTypeFieldValuesObject function, properties that are not available in the descriptor values should be removed/cleaned up, not preserved. This keeps the field configuration in sync with the current descriptor definitions and prevents accumulation of obsolete properties.

Applied to files:

  • ui/app/src/components/FormsEngine/lib/formUtils.tsx
  • ui/app/src/utils/system.ts
📚 Learning: 2025-12-22T18:26:52.231Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4663
File: ui/app/src/components/FormsEngine/FormsEngine.tsx:147-147
Timestamp: 2025-12-22T18:26:52.231Z
Learning: In useSaveForm.tsx for shared content creation/updates, the path variable is computed (lines 111-114) but needs to be passed to the onSave callback on line 123. For embedded components, path doesn't exist and shouldn't be set. NodeSelector.tsx expects result.path for shared content to use as the item key.

Applied to files:

  • ui/app/src/utils/system.ts
📚 Learning: 2025-08-19T20:31:06.188Z
Learnt from: jvega190
Repo: craftercms/studio-ui PR: 4600
File: ui/app/src/components/DeletePluginDialog/utils.ts:29-31
Timestamp: 2025-08-19T20:31:06.188Z
Learning: In the CrafterCMS studio-ui codebase, not all usages of `onSubmittingAndOrPendingChange` should be migrated to use the EnhancedDialog context API. Some components are intentionally meant to continue using the legacy prop pattern, particularly parent/management components that pass handlers down to child dialogs.

Applied to files:

  • ui/app/src/utils/system.ts
🧬 Code graph analysis (2)
ui/app/src/components/FormsEngine/FormsEngine.tsx (1)
ui/app/src/hooks/useMount.ts (1)
  • useMount (19-22)
ui/app/src/components/FormsEngine/lib/formUtils.tsx (2)
ui/app/src/models/LookupTable.ts (1)
  • LookupTable (17-17)
ui/app/src/models/ContentType.ts (1)
  • ContentType (166-191)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
  • GitHub Check: Travis CI - Pull Request
  • GitHub Check: Codacy Static Code Analysis
🔇 Additional comments (6)
ui/app/src/components/FormsEngine/FormsEngine.tsx (4)

122-122: LGTM!

Import of useMount is appropriate for the one-time initialization of pending changes state when changeTypeId is present.


153-160: LGTM!

The optional changeTypeId property correctly extends UpdateModeProps while maintaining backward compatibility.


445-452: LGTM!

The changeTypeId parameter is correctly propagated to fetchUpdateRequirements, enabling content type override during the update flow.


620-625: LGTM!

The useMount hook correctly initializes hasPendingChanges to true when changeTypeId is present, ensuring the user is prompted to save the content type change. The optional chaining (update?.changeTypeId) safely handles create and repeat modes where update is undefined.

ui/app/src/components/FormsEngine/lib/formUtils.tsx (1)

423-427: LGTM!

The content type resolution correctly uses changeTypeId when provided, falling back to item.contentTypeId. The error handling for missing content types is properly maintained.

ui/app/src/utils/system.ts (1)

121-131: LGTM! The mapping from changeTemplate to changeTypeId is correct.

Verification confirms changeTemplate exists on LegacyFormDialogProps as an optional string property, and it correctly maps to changeTypeId on UpdateModeProps for the update mode of the FormsEngine. Both properties are type-compatible.

✏️ Tip: You can disable this entire section by setting review_details to false in your review settings.

@jvega190
Copy link
Member Author

Outside diff range comments addressed

@jvega190 jvega190 marked this pull request as ready for review January 16, 2026 17:47
@jvega190 jvega190 requested a review from rart as a code owner January 16, 2026 17:47
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant