-
Notifications
You must be signed in to change notification settings - Fork 112
fix: update WebsiteDialog form state handling. #251
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
@sbansal1999 is attempting to deploy a commit to the Databuddy OSS Team on Vercel. A member of the Team first needs to authorize it. |
WalkthroughUpdated the website dialog form to trim and validate Changes
Sequence Diagram(s)(omitted) Estimated Code Review Effort🎯 3 (Moderate) | ⏱️ ~20 minutes Possibly Related PRs
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
📜 Recent review detailsConfiguration used: Repository UI Review profile: ASSERTIVE Plan: Pro 📒 Files selected for processing (1)
🧰 Additional context used📓 Path-based instructions (13)**/*.{ts,tsx,js,jsx,vue}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{html,htm,tsx,jsx,vue}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{ts,tsx,js,jsx}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{ts,tsx,js,jsx,css,scss,sass,less}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{tsx,jsx,vue}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{tsx,jsx}📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Files:
**/*.{ts,tsx,jsx}📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Files:
**/*.{ts,tsx}📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Files:
!(**/pages/_document.{ts,tsx,jsx})**/*.{ts,tsx,jsx}📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Files:
**/*.{ts,tsx,html,css}📄 CodeRabbit inference engine (.cursor/rules/use-bun-instead-of-node-vite-npm-pnpm.mdc)
Files:
**/*.{jsx,tsx}📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
Files:
**/*.{js,jsx,ts,tsx}📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
Files:
🧠 Learnings (3)📓 Common learnings📚 Learning: 2025-12-02T22:55:00.415ZApplied to files:
📚 Learning: 2025-12-02T22:57:07.791ZApplied to files:
🧬 Code graph analysis (1)apps/dashboard/components/website-dialog.tsx (1)
🔇 Additional comments (6)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
📜 Review details
Configuration used: Repository UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/components/website-dialog.tsx
🧰 Additional context used
📓 Path-based instructions (13)
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,vue}: Never block paste in<input>or<textarea>elements
Enter submits focused text input; in<textarea>, ⌘/Ctrl+Enter submits; Enter adds newline
Compatible with password managers and 2FA; allow pasting one-time codes
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{html,htm,tsx,jsx,vue}: Useautocompleteattribute with meaningfulname; use correcttypeandinputmode
Disable spellcheck for email/code/username inputs usingspellcheck="false"
Links are<a>or<Link>components for navigation; support Cmd/Ctrl/middle-click
Use politearia-livefor toasts and inline validation feedback
Autofocus on desktop when there's a single primary input; rarely on mobile to avoid layout shift
<title>tag must match current context
Use redundant status cues (not color-only); icon-only elements have text labels
Use accurate accessible names viaaria-label; mark decorative elements witharia-hidden; verify in Accessibility Tree
Icon-only buttons must have descriptivearia-label
Prefer native semantics (button,a,label,table) before ARIA
Use non-breaking spaces to glue terms:10 MB,⌘ + K,Vercel SDK
Preload only above-the-fold images; lazy-load the rest
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx}: Trim values to handle text expansion and trailing spaces in form submissions
URL reflects state (deep-link filters/tabs/pagination/expanded panels); prefer libraries likenuqs
Back/Forward buttons restore scroll position
Delay first tooltip in a group; subsequent peers have no delay
Use locale-aware formatting for dates, times, numbers, and currency
Batch layout reads/writes; avoid unnecessary reflows/repaints
Virtualize large lists using libraries likevirtua
**/*.{ts,tsx,js,jsx}: Don't useaccessKeyattribute on any HTML element.
Don't setaria-hidden="true"on focusable elements.
Don't add ARIA roles, states, and properties to elements that don't support them.
Don't use distracting elements like<marquee>or<blink>.
Only use thescopeprop on<th>elements.
Don't assign non-interactive ARIA roles to interactive HTML elements.
Make sure label elements have text content and are associated with an input.
Don't assign interactive ARIA roles to non-interactive HTML elements.
Don't assigntabIndexto non-interactive HTML elements.
Don't use positive integers fortabIndexproperty.
Don't include "image", "picture", or "photo" in img alt prop.
Don't use explicit role property that's the same as the implicit/default role.
Make static elements with click handlers use a valid role attribute.
Always include atitleelement for SVG elements.
Give all elements requiring alt text meaningful information for screen readers.
Make sure anchors have content that's accessible to screen readers.
AssigntabIndexto non-interactive HTML elements witharia-activedescendant.
Include all required ARIA attributes for elements with ARIA roles.
Make sure ARIA properties are valid for the element's supported roles.
Always include atypeattribute for button elements.
Make elements with interactive roles and handlers focusable.
Give heading elements content that's accessible to screen readers (not hidden witharia-hidden).
Always include...
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}: No dead zones on checkboxes/radios; label and control share one generous hit target
Usescroll-margin-topon headings for anchored links; include 'Skip to content' link; use hierarchical<h1>–<h6>
Prevent Cumulative Layout Shift (CLS) from images by using explicit dimensions or reserved space
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx,css,scss,sass,less}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,css,scss,sass,less}: During drag operations, disable text selection and setinerton dragged element and containers
Animations must be interruptible and input-driven; avoid autoplay
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Don't ship the schema—visuals may omit labels but accessible names must still exist
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Prefer uncontrolled inputs; make controlled loops cheap (optimize keystroke cost)
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx,jsx}: Use semantic elements instead of role attributes in JSX.
Don't use unnecessary fragments.
Don't pass children as props.
Don't use the return value of React.render.
Make sure all dependencies are correctly specified in React hooks.
Make sure all React hooks are called from the top level of component functions.
Don't forget key props in iterators and collection literals.
Don't destructure props inside JSX components in Solid projects.
Don't define React components inside other components.
Don't use event handlers on non-interactive elements.
Don't assign to React component props.
Don't use bothchildrenanddangerouslySetInnerHTMLprops on the same element.
Don't use dangerous JSX props.
Don't use Array index in keys.
Don't insert comments as text nodes.
Don't assign JSX properties multiple times.
Don't add extra closing tags for components without children.
Use<>...</>instead of<Fragment>...</Fragment>.
Watch out for possible "wrong" semicolons inside JSX elements.
Make sure void (self-closing) elements don't have children.
Don't usetarget="_blank"withoutrel="noopener".
Don't use<img>elements in Next.js projects.
Don't use<head>elements in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx}: Don't use primitive type aliases or misleading types.
Don't use empty type parameters in type aliases and interfaces.
Don't use any or unknown as type constraints.
Don't return a value from a function with the return type 'void'.
Don't use the TypeScript directive @ts-ignore.
Don't use TypeScript enums.
Don't add type annotations to variables, parameters, and class properties that are initialized with literal expressions.
Don't use TypeScript namespaces.
Don't use non-null assertions with the!postfix operator.
Don't use parameter properties in class constructors.
Don't use user-defined types.
Useas constinstead of literal types and type annotations.
Use eitherT[]orArray<T>consistently.
Initialize each enum member value explicitly.
Useexport typefor types.
Useimport typefor types.
Make sure all enum members are literal values.
Don't use TypeScript const enum.
Don't declare empty interfaces.
Don't let variables evolve into any type through reassignments.
Don't use the any type.
Don't misuse the non-null assertion operator (!) in TypeScript files.
Don't use implicit any type on variable declarations.
Don't merge interfaces and classes unsafely.
Don't use overload signatures that aren't next to each other.
Use the namespace keyword instead of the module keyword to declare TypeScript namespaces.
Use consistent accessibility modifiers on class properties and methods.
Use function types instead of object types with call signatures.
Don't use void type outside of generic or return types.
**/*.{ts,tsx}: Do NOT use types 'any', 'unknown' or 'never'. Use proper explicit types
Suffix functions with 'Action' in types, like 'type Test = { testAction }'
Files:
apps/dashboard/components/website-dialog.tsx
!(**/pages/_document.{ts,tsx,jsx})**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Don't import next/document outside of pages/_document.jsx in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,html,css}
📄 CodeRabbit inference engine (.cursor/rules/use-bun-instead-of-node-vite-npm-pnpm.mdc)
Use
bun build <file.html|file.ts|file.css>instead ofwebpackoresbuildfor bundling
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{jsx,tsx}: When using 'text-right' utility class, always add 'text-balance' to prevent poor text layout
Think about mobile responsiveness when doing any UI tasks or changes
Always use 'rounded' Tailwind class, never 'rounded-xl' or 'rounded-md'
Don't use lucide for icons, ONLY use phosphor icons. Use width='duotone' for most icons, use fill for arrows, and don't add width attribute for plus icons
Decouple state management, data transformations, and API interactions from the React lifecycle in View Components
Simplify data flow to eliminate prop drilling and callback hell in components
Prioritize modularity and testability in all components
ALWAYS use error boundaries properly in React applications
Use 'Icon' suffix at the end of phosphor react icon imports, like CaretIcon not Caret. This is the default import, NOT as a named import
Almost NEVER use useEffect unless it's critical
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{js,jsx,ts,tsx}: Split off components, utils, and reusable code to ensure better loading speed and less complexity
Use lower-case-like-this naming convention for variables, functions, and identifiers
NEVER add placeholders, mock data, or anything similar to production code
Use Dayjs for date handling, NEVER use date-fns. Use Tanstack query for hooks, NEVER use SWR
Use json.stringify() when adding debugging code
Never use barrel exports or create index files
Files:
apps/dashboard/components/website-dialog.tsx
🧠 Learnings (2)
📚 Learning: 2025-12-02T22:55:00.415Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
Applied to files:
apps/dashboard/components/website-dialog.tsx
📚 Learning: 2025-12-02T22:57:07.791Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/ultracite.mdc:0-0
Timestamp: 2025-12-02T22:57:07.791Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Use valid ARIA state and property values.
Applied to files:
apps/dashboard/components/website-dialog.tsx
🧬 Code graph analysis (1)
apps/dashboard/components/website-dialog.tsx (1)
packages/validation/src/regexes.ts (1)
WEBSITE_NAME_REGEX(15-15)
🔇 Additional comments (2)
apps/dashboard/components/website-dialog.tsx (2)
82-82: LGTM! Appropriate validation mode.Setting
mode: "onBlur"provides a good balance between user experience and validation feedback timing. Validation will trigger when users leave a field, which is less disruptive thanonChangemode while still providing timely feedback.
165-168: LGTM! Correct formState destructuring pattern.This implementation correctly follows React Hook Form best practices. Destructuring
isValidandisDirtyfromform.formStateensures the component re-renders when form validation state changes. The explanatory comment and documentation link are helpful for future maintainers.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
apps/dashboard/components/website-dialog.tsx (1)
126-158: Critical: Submit handler doesn't receive transformed/trimmed values.The
handleSubmitfunction usesform.getValues()to retrieve form data, but this returns the raw form state, not the validated and transformed values from Zod. Since the name field uses.trim()in its schema, the transformation only occurs during validation—it doesn't mutate the form state.Impact:
- If a user enters
" My Website ", validation passes (Zod trims it to"My Website"internally), butform.getValues()returns the untrimmed value" My Website ".- The server receives the untrimmed value, violating the coding guideline to trim form submissions.
- This is inconsistent with the domain field, which manually trims in
onChangebefore updating form state.Fix: Update the signature to accept the validated data parameter:
🔎 Proposed fix
-const handleSubmit = async () => { - const formData = form.getValues(); +const handleSubmit = async (data: FormData) => { const submissionData: CreateWebsiteData = { - name: formData.name, - domain: formData.domain, + name: data.name, // Now uses the trimmed value from Zod + domain: data.domain, organizationId: activeOrganization?.id, }; try { if (website?.id) { const updateData: UpdateWebsiteInput = { id: website.id, - name: formData.name, - domain: formData.domain, + name: data.name, + domain: data.domain, }; // ... rest unchangedBased on learnings, trim values to handle text expansion and trailing spaces in form submissions.
📜 Review details
Configuration used: Repository UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/components/website-dialog.tsx
🧰 Additional context used
📓 Path-based instructions (13)
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,vue}: Never block paste in<input>or<textarea>elements
Enter submits focused text input; in<textarea>, ⌘/Ctrl+Enter submits; Enter adds newline
Compatible with password managers and 2FA; allow pasting one-time codes
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{html,htm,tsx,jsx,vue}: Useautocompleteattribute with meaningfulname; use correcttypeandinputmode
Disable spellcheck for email/code/username inputs usingspellcheck="false"
Links are<a>or<Link>components for navigation; support Cmd/Ctrl/middle-click
Use politearia-livefor toasts and inline validation feedback
Autofocus on desktop when there's a single primary input; rarely on mobile to avoid layout shift
<title>tag must match current context
Use redundant status cues (not color-only); icon-only elements have text labels
Use accurate accessible names viaaria-label; mark decorative elements witharia-hidden; verify in Accessibility Tree
Icon-only buttons must have descriptivearia-label
Prefer native semantics (button,a,label,table) before ARIA
Use non-breaking spaces to glue terms:10 MB,⌘ + K,Vercel SDK
Preload only above-the-fold images; lazy-load the rest
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx}: Trim values to handle text expansion and trailing spaces in form submissions
URL reflects state (deep-link filters/tabs/pagination/expanded panels); prefer libraries likenuqs
Back/Forward buttons restore scroll position
Delay first tooltip in a group; subsequent peers have no delay
Use locale-aware formatting for dates, times, numbers, and currency
Batch layout reads/writes; avoid unnecessary reflows/repaints
Virtualize large lists using libraries likevirtua
**/*.{ts,tsx,js,jsx}: Don't useaccessKeyattribute on any HTML element.
Don't setaria-hidden="true"on focusable elements.
Don't add ARIA roles, states, and properties to elements that don't support them.
Don't use distracting elements like<marquee>or<blink>.
Only use thescopeprop on<th>elements.
Don't assign non-interactive ARIA roles to interactive HTML elements.
Make sure label elements have text content and are associated with an input.
Don't assign interactive ARIA roles to non-interactive HTML elements.
Don't assigntabIndexto non-interactive HTML elements.
Don't use positive integers fortabIndexproperty.
Don't include "image", "picture", or "photo" in img alt prop.
Don't use explicit role property that's the same as the implicit/default role.
Make static elements with click handlers use a valid role attribute.
Always include atitleelement for SVG elements.
Give all elements requiring alt text meaningful information for screen readers.
Make sure anchors have content that's accessible to screen readers.
AssigntabIndexto non-interactive HTML elements witharia-activedescendant.
Include all required ARIA attributes for elements with ARIA roles.
Make sure ARIA properties are valid for the element's supported roles.
Always include atypeattribute for button elements.
Make elements with interactive roles and handlers focusable.
Give heading elements content that's accessible to screen readers (not hidden witharia-hidden).
Always include...
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}: No dead zones on checkboxes/radios; label and control share one generous hit target
Usescroll-margin-topon headings for anchored links; include 'Skip to content' link; use hierarchical<h1>–<h6>
Prevent Cumulative Layout Shift (CLS) from images by using explicit dimensions or reserved space
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx,css,scss,sass,less}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,css,scss,sass,less}: During drag operations, disable text selection and setinerton dragged element and containers
Animations must be interruptible and input-driven; avoid autoplay
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Don't ship the schema—visuals may omit labels but accessible names must still exist
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Prefer uncontrolled inputs; make controlled loops cheap (optimize keystroke cost)
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx,jsx}: Use semantic elements instead of role attributes in JSX.
Don't use unnecessary fragments.
Don't pass children as props.
Don't use the return value of React.render.
Make sure all dependencies are correctly specified in React hooks.
Make sure all React hooks are called from the top level of component functions.
Don't forget key props in iterators and collection literals.
Don't destructure props inside JSX components in Solid projects.
Don't define React components inside other components.
Don't use event handlers on non-interactive elements.
Don't assign to React component props.
Don't use bothchildrenanddangerouslySetInnerHTMLprops on the same element.
Don't use dangerous JSX props.
Don't use Array index in keys.
Don't insert comments as text nodes.
Don't assign JSX properties multiple times.
Don't add extra closing tags for components without children.
Use<>...</>instead of<Fragment>...</Fragment>.
Watch out for possible "wrong" semicolons inside JSX elements.
Make sure void (self-closing) elements don't have children.
Don't usetarget="_blank"withoutrel="noopener".
Don't use<img>elements in Next.js projects.
Don't use<head>elements in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx}: Don't use primitive type aliases or misleading types.
Don't use empty type parameters in type aliases and interfaces.
Don't use any or unknown as type constraints.
Don't return a value from a function with the return type 'void'.
Don't use the TypeScript directive @ts-ignore.
Don't use TypeScript enums.
Don't add type annotations to variables, parameters, and class properties that are initialized with literal expressions.
Don't use TypeScript namespaces.
Don't use non-null assertions with the!postfix operator.
Don't use parameter properties in class constructors.
Don't use user-defined types.
Useas constinstead of literal types and type annotations.
Use eitherT[]orArray<T>consistently.
Initialize each enum member value explicitly.
Useexport typefor types.
Useimport typefor types.
Make sure all enum members are literal values.
Don't use TypeScript const enum.
Don't declare empty interfaces.
Don't let variables evolve into any type through reassignments.
Don't use the any type.
Don't misuse the non-null assertion operator (!) in TypeScript files.
Don't use implicit any type on variable declarations.
Don't merge interfaces and classes unsafely.
Don't use overload signatures that aren't next to each other.
Use the namespace keyword instead of the module keyword to declare TypeScript namespaces.
Use consistent accessibility modifiers on class properties and methods.
Use function types instead of object types with call signatures.
Don't use void type outside of generic or return types.
**/*.{ts,tsx}: Do NOT use types 'any', 'unknown' or 'never'. Use proper explicit types
Suffix functions with 'Action' in types, like 'type Test = { testAction }'
Files:
apps/dashboard/components/website-dialog.tsx
!(**/pages/_document.{ts,tsx,jsx})**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Don't import next/document outside of pages/_document.jsx in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,html,css}
📄 CodeRabbit inference engine (.cursor/rules/use-bun-instead-of-node-vite-npm-pnpm.mdc)
Use
bun build <file.html|file.ts|file.css>instead ofwebpackoresbuildfor bundling
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{jsx,tsx}: When using 'text-right' utility class, always add 'text-balance' to prevent poor text layout
Think about mobile responsiveness when doing any UI tasks or changes
Always use 'rounded' Tailwind class, never 'rounded-xl' or 'rounded-md'
Don't use lucide for icons, ONLY use phosphor icons. Use width='duotone' for most icons, use fill for arrows, and don't add width attribute for plus icons
Decouple state management, data transformations, and API interactions from the React lifecycle in View Components
Simplify data flow to eliminate prop drilling and callback hell in components
Prioritize modularity and testability in all components
ALWAYS use error boundaries properly in React applications
Use 'Icon' suffix at the end of phosphor react icon imports, like CaretIcon not Caret. This is the default import, NOT as a named import
Almost NEVER use useEffect unless it's critical
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{js,jsx,ts,tsx}: Split off components, utils, and reusable code to ensure better loading speed and less complexity
Use lower-case-like-this naming convention for variables, functions, and identifiers
NEVER add placeholders, mock data, or anything similar to production code
Use Dayjs for date handling, NEVER use date-fns. Use Tanstack query for hooks, NEVER use SWR
Use json.stringify() when adding debugging code
Never use barrel exports or create index files
Files:
apps/dashboard/components/website-dialog.tsx
🧠 Learnings (3)
📓 Common learnings
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
📚 Learning: 2025-12-02T22:55:00.415Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
Applied to files:
apps/dashboard/components/website-dialog.tsx
📚 Learning: 2025-12-02T22:57:07.791Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/ultracite.mdc:0-0
Timestamp: 2025-12-02T22:57:07.791Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Use valid ARIA state and property values.
Applied to files:
apps/dashboard/components/website-dialog.tsx
🧬 Code graph analysis (1)
apps/dashboard/components/website-dialog.tsx (1)
packages/validation/src/regexes.ts (1)
WEBSITE_NAME_REGEX(15-15)
🔇 Additional comments (4)
apps/dashboard/components/website-dialog.tsx (4)
3-3: LGTM: Clean import of shared validation regex.Importing
WEBSITE_NAME_REGEXfrom the validation package promotes consistency across the codebase.
45-49: LGTM: Validation schema correctly implements trimming and regex.The name field validation properly:
- Trims whitespace before validation (per coding guidelines)
- Applies
WEBSITE_NAME_REGEXwith an accurate, user-friendly error message- Rejects empty strings after trimming
This addresses the previous review feedback about incomplete error messages and missing trimming.
80-80: LGTM: Appropriate validation timing.Setting
mode: "onBlur"provides good UX by validating after users complete their input rather than while they type.
163-166: LGTM: Correct formState access pattern with helpful documentation.Destructuring
isValidandisDirtyfromform.formStateensures proper re-renders when these values change, following React Hook Form best practices. The inline comment and documentation link provide clear guidance for future maintainers.
4ed1ff7 to
f678943
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
📜 Review details
Configuration used: Repository UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/components/website-dialog.tsx
🧰 Additional context used
📓 Path-based instructions (13)
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,vue}: Never block paste in<input>or<textarea>elements
Enter submits focused text input; in<textarea>, ⌘/Ctrl+Enter submits; Enter adds newline
Compatible with password managers and 2FA; allow pasting one-time codes
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{html,htm,tsx,jsx,vue}: Useautocompleteattribute with meaningfulname; use correcttypeandinputmode
Disable spellcheck for email/code/username inputs usingspellcheck="false"
Links are<a>or<Link>components for navigation; support Cmd/Ctrl/middle-click
Use politearia-livefor toasts and inline validation feedback
Autofocus on desktop when there's a single primary input; rarely on mobile to avoid layout shift
<title>tag must match current context
Use redundant status cues (not color-only); icon-only elements have text labels
Use accurate accessible names viaaria-label; mark decorative elements witharia-hidden; verify in Accessibility Tree
Icon-only buttons must have descriptivearia-label
Prefer native semantics (button,a,label,table) before ARIA
Use non-breaking spaces to glue terms:10 MB,⌘ + K,Vercel SDK
Preload only above-the-fold images; lazy-load the rest
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx}: Trim values to handle text expansion and trailing spaces in form submissions
URL reflects state (deep-link filters/tabs/pagination/expanded panels); prefer libraries likenuqs
Back/Forward buttons restore scroll position
Delay first tooltip in a group; subsequent peers have no delay
Use locale-aware formatting for dates, times, numbers, and currency
Batch layout reads/writes; avoid unnecessary reflows/repaints
Virtualize large lists using libraries likevirtua
**/*.{ts,tsx,js,jsx}: Don't useaccessKeyattribute on any HTML element.
Don't setaria-hidden="true"on focusable elements.
Don't add ARIA roles, states, and properties to elements that don't support them.
Don't use distracting elements like<marquee>or<blink>.
Only use thescopeprop on<th>elements.
Don't assign non-interactive ARIA roles to interactive HTML elements.
Make sure label elements have text content and are associated with an input.
Don't assign interactive ARIA roles to non-interactive HTML elements.
Don't assigntabIndexto non-interactive HTML elements.
Don't use positive integers fortabIndexproperty.
Don't include "image", "picture", or "photo" in img alt prop.
Don't use explicit role property that's the same as the implicit/default role.
Make static elements with click handlers use a valid role attribute.
Always include atitleelement for SVG elements.
Give all elements requiring alt text meaningful information for screen readers.
Make sure anchors have content that's accessible to screen readers.
AssigntabIndexto non-interactive HTML elements witharia-activedescendant.
Include all required ARIA attributes for elements with ARIA roles.
Make sure ARIA properties are valid for the element's supported roles.
Always include atypeattribute for button elements.
Make elements with interactive roles and handlers focusable.
Give heading elements content that's accessible to screen readers (not hidden witharia-hidden).
Always include...
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}: No dead zones on checkboxes/radios; label and control share one generous hit target
Usescroll-margin-topon headings for anchored links; include 'Skip to content' link; use hierarchical<h1>–<h6>
Prevent Cumulative Layout Shift (CLS) from images by using explicit dimensions or reserved space
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx,css,scss,sass,less}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,css,scss,sass,less}: During drag operations, disable text selection and setinerton dragged element and containers
Animations must be interruptible and input-driven; avoid autoplay
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Don't ship the schema—visuals may omit labels but accessible names must still exist
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Prefer uncontrolled inputs; make controlled loops cheap (optimize keystroke cost)
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx,jsx}: Use semantic elements instead of role attributes in JSX.
Don't use unnecessary fragments.
Don't pass children as props.
Don't use the return value of React.render.
Make sure all dependencies are correctly specified in React hooks.
Make sure all React hooks are called from the top level of component functions.
Don't forget key props in iterators and collection literals.
Don't destructure props inside JSX components in Solid projects.
Don't define React components inside other components.
Don't use event handlers on non-interactive elements.
Don't assign to React component props.
Don't use bothchildrenanddangerouslySetInnerHTMLprops on the same element.
Don't use dangerous JSX props.
Don't use Array index in keys.
Don't insert comments as text nodes.
Don't assign JSX properties multiple times.
Don't add extra closing tags for components without children.
Use<>...</>instead of<Fragment>...</Fragment>.
Watch out for possible "wrong" semicolons inside JSX elements.
Make sure void (self-closing) elements don't have children.
Don't usetarget="_blank"withoutrel="noopener".
Don't use<img>elements in Next.js projects.
Don't use<head>elements in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx}: Don't use primitive type aliases or misleading types.
Don't use empty type parameters in type aliases and interfaces.
Don't use any or unknown as type constraints.
Don't return a value from a function with the return type 'void'.
Don't use the TypeScript directive @ts-ignore.
Don't use TypeScript enums.
Don't add type annotations to variables, parameters, and class properties that are initialized with literal expressions.
Don't use TypeScript namespaces.
Don't use non-null assertions with the!postfix operator.
Don't use parameter properties in class constructors.
Don't use user-defined types.
Useas constinstead of literal types and type annotations.
Use eitherT[]orArray<T>consistently.
Initialize each enum member value explicitly.
Useexport typefor types.
Useimport typefor types.
Make sure all enum members are literal values.
Don't use TypeScript const enum.
Don't declare empty interfaces.
Don't let variables evolve into any type through reassignments.
Don't use the any type.
Don't misuse the non-null assertion operator (!) in TypeScript files.
Don't use implicit any type on variable declarations.
Don't merge interfaces and classes unsafely.
Don't use overload signatures that aren't next to each other.
Use the namespace keyword instead of the module keyword to declare TypeScript namespaces.
Use consistent accessibility modifiers on class properties and methods.
Use function types instead of object types with call signatures.
Don't use void type outside of generic or return types.
**/*.{ts,tsx}: Do NOT use types 'any', 'unknown' or 'never'. Use proper explicit types
Suffix functions with 'Action' in types, like 'type Test = { testAction }'
Files:
apps/dashboard/components/website-dialog.tsx
!(**/pages/_document.{ts,tsx,jsx})**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Don't import next/document outside of pages/_document.jsx in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,html,css}
📄 CodeRabbit inference engine (.cursor/rules/use-bun-instead-of-node-vite-npm-pnpm.mdc)
Use
bun build <file.html|file.ts|file.css>instead ofwebpackoresbuildfor bundling
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{jsx,tsx}: When using 'text-right' utility class, always add 'text-balance' to prevent poor text layout
Think about mobile responsiveness when doing any UI tasks or changes
Always use 'rounded' Tailwind class, never 'rounded-xl' or 'rounded-md'
Don't use lucide for icons, ONLY use phosphor icons. Use width='duotone' for most icons, use fill for arrows, and don't add width attribute for plus icons
Decouple state management, data transformations, and API interactions from the React lifecycle in View Components
Simplify data flow to eliminate prop drilling and callback hell in components
Prioritize modularity and testability in all components
ALWAYS use error boundaries properly in React applications
Use 'Icon' suffix at the end of phosphor react icon imports, like CaretIcon not Caret. This is the default import, NOT as a named import
Almost NEVER use useEffect unless it's critical
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{js,jsx,ts,tsx}: Split off components, utils, and reusable code to ensure better loading speed and less complexity
Use lower-case-like-this naming convention for variables, functions, and identifiers
NEVER add placeholders, mock data, or anything similar to production code
Use Dayjs for date handling, NEVER use date-fns. Use Tanstack query for hooks, NEVER use SWR
Use json.stringify() when adding debugging code
Never use barrel exports or create index files
Files:
apps/dashboard/components/website-dialog.tsx
🧠 Learnings (2)
📓 Common learnings
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
📚 Learning: 2025-12-02T22:55:00.415Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
Applied to files:
apps/dashboard/components/website-dialog.tsx
🧬 Code graph analysis (1)
apps/dashboard/components/website-dialog.tsx (1)
packages/validation/src/regexes.ts (1)
WEBSITE_NAME_REGEX(15-15)
🔇 Additional comments (5)
apps/dashboard/components/website-dialog.tsx (5)
3-3: LGTM: Proper imports for validation and typing.The imports are correctly added and used throughout the file.
Also applies to: 6-6
45-49: LGTM: Proper name validation with trimming.The name field validation now correctly:
- Trims input to handle trailing spaces (per coding guidelines)
- Validates against
WEBSITE_NAME_REGEX- Provides an accurate error message listing all allowed characters
This addresses the previous review feedback.
80-80: LGTM: Appropriate validation mode.Setting
mode: "onBlur"provides better UX by validating fields after users finish editing, rather than on every keystroke.
126-126: LGTM: Proper typing for submit handler.Using
SubmitHandler<FormData>improves type safety and aligns with React Hook Form best practices.
162-165: LGTM: Correct formState destructuring pattern.Destructuring
isValidandisDirtyfromform.formStateis essential for proper re-renders. Direct property access (e.g.,form.formState.isValid) doesn't subscribe to state updates in React Hook Form. The comment appropriately documents this important pattern.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
apps/dashboard/components/website-dialog.tsx (1)
95-95: Replaceunknowntype with explicit error interface.The
unknowntype violates the coding guidelines which require explicit types. Define a proper error interface for API errors and use type guards instead of type assertions.🔎 Proposed fix
Add an explicit error interface near the top of the file:
interface UpdateWebsiteInput { id: string; name: string; domain?: string; isPublic?: boolean; } interface CreateWebsiteData { name: string; domain: string; subdomain?: string; organizationId?: string; } +interface ApiError { + data?: { + code?: string; + }; + message?: string; +} + +function isApiError(error: object): error is ApiError { + return 'message' in error || 'data' in error; +}Then update the error handling:
-const getErrorMessage = (error: unknown, isEditingMode: boolean): string => { +const getErrorMessage = (error: object, isEditingMode: boolean): string => { const defaultMessage = `Failed to ${isEditingMode ? "update" : "create"} website.`; - const rpcError = error as { - data?: { code?: string }; - message?: string; - }; + if (!isApiError(error)) { + return defaultMessage; + } - if (rpcError?.data?.code) { - switch (rpcError.data.code) { + if (error.data?.code) { + switch (error.data.code) { case "CONFLICT": return "A website with this domain already exists."; case "FORBIDDEN": return ( - rpcError.message || + error.message || "You do not have permission to perform this action." ); case "UNAUTHORIZED": return "You must be logged in to perform this action."; case "BAD_REQUEST": return ( - rpcError.message || "Invalid request. Please check your input." + error.message || "Invalid request. Please check your input." ); default: - return rpcError.message || defaultMessage; + return error.message || defaultMessage; } } - return rpcError?.message || defaultMessage; + return error.message || defaultMessage; };And in the catch block:
- } catch (error: unknown) { + } catch (error) { - const message = getErrorMessage(error, !!website?.id); + const message = getErrorMessage(error as object, !!website?.id); toast.error(message); }As per coding guidelines, "Do NOT use types 'any', 'unknown' or 'never'. Use proper explicit types."
Also applies to: 153-153
📜 Review details
Configuration used: Repository UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (1)
apps/dashboard/components/website-dialog.tsx
🧰 Additional context used
📓 Path-based instructions (13)
**/*.{ts,tsx,js,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,vue}: Never block paste in<input>or<textarea>elements
Enter submits focused text input; in<textarea>, ⌘/Ctrl+Enter submits; Enter adds newline
Compatible with password managers and 2FA; allow pasting one-time codes
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{html,htm,tsx,jsx,vue}: Useautocompleteattribute with meaningfulname; use correcttypeandinputmode
Disable spellcheck for email/code/username inputs usingspellcheck="false"
Links are<a>or<Link>components for navigation; support Cmd/Ctrl/middle-click
Use politearia-livefor toasts and inline validation feedback
Autofocus on desktop when there's a single primary input; rarely on mobile to avoid layout shift
<title>tag must match current context
Use redundant status cues (not color-only); icon-only elements have text labels
Use accurate accessible names viaaria-label; mark decorative elements witharia-hidden; verify in Accessibility Tree
Icon-only buttons must have descriptivearia-label
Prefer native semantics (button,a,label,table) before ARIA
Use non-breaking spaces to glue terms:10 MB,⌘ + K,Vercel SDK
Preload only above-the-fold images; lazy-load the rest
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx}: Trim values to handle text expansion and trailing spaces in form submissions
URL reflects state (deep-link filters/tabs/pagination/expanded panels); prefer libraries likenuqs
Back/Forward buttons restore scroll position
Delay first tooltip in a group; subsequent peers have no delay
Use locale-aware formatting for dates, times, numbers, and currency
Batch layout reads/writes; avoid unnecessary reflows/repaints
Virtualize large lists using libraries likevirtua
**/*.{ts,tsx,js,jsx}: Don't useaccessKeyattribute on any HTML element.
Don't setaria-hidden="true"on focusable elements.
Don't add ARIA roles, states, and properties to elements that don't support them.
Don't use distracting elements like<marquee>or<blink>.
Only use thescopeprop on<th>elements.
Don't assign non-interactive ARIA roles to interactive HTML elements.
Make sure label elements have text content and are associated with an input.
Don't assign interactive ARIA roles to non-interactive HTML elements.
Don't assigntabIndexto non-interactive HTML elements.
Don't use positive integers fortabIndexproperty.
Don't include "image", "picture", or "photo" in img alt prop.
Don't use explicit role property that's the same as the implicit/default role.
Make static elements with click handlers use a valid role attribute.
Always include atitleelement for SVG elements.
Give all elements requiring alt text meaningful information for screen readers.
Make sure anchors have content that's accessible to screen readers.
AssigntabIndexto non-interactive HTML elements witharia-activedescendant.
Include all required ARIA attributes for elements with ARIA roles.
Make sure ARIA properties are valid for the element's supported roles.
Always include atypeattribute for button elements.
Make elements with interactive roles and handlers focusable.
Give heading elements content that's accessible to screen readers (not hidden witharia-hidden).
Always include...
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{css,scss,sass,less,html,htm,tsx,jsx,vue}: No dead zones on checkboxes/radios; label and control share one generous hit target
Usescroll-margin-topon headings for anchored links; include 'Skip to content' link; use hierarchical<h1>–<h6>
Prevent Cumulative Layout Shift (CLS) from images by using explicit dimensions or reserved space
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,js,jsx,css,scss,sass,less}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
**/*.{ts,tsx,js,jsx,css,scss,sass,less}: During drag operations, disable text selection and setinerton dragged element and containers
Animations must be interruptible and input-driven; avoid autoplay
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx,vue}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Don't ship the schema—visuals may omit labels but accessible names must still exist
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/guidelines.mdc)
Prefer uncontrolled inputs; make controlled loops cheap (optimize keystroke cost)
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx,jsx}: Use semantic elements instead of role attributes in JSX.
Don't use unnecessary fragments.
Don't pass children as props.
Don't use the return value of React.render.
Make sure all dependencies are correctly specified in React hooks.
Make sure all React hooks are called from the top level of component functions.
Don't forget key props in iterators and collection literals.
Don't destructure props inside JSX components in Solid projects.
Don't define React components inside other components.
Don't use event handlers on non-interactive elements.
Don't assign to React component props.
Don't use bothchildrenanddangerouslySetInnerHTMLprops on the same element.
Don't use dangerous JSX props.
Don't use Array index in keys.
Don't insert comments as text nodes.
Don't assign JSX properties multiple times.
Don't add extra closing tags for components without children.
Use<>...</>instead of<Fragment>...</Fragment>.
Watch out for possible "wrong" semicolons inside JSX elements.
Make sure void (self-closing) elements don't have children.
Don't usetarget="_blank"withoutrel="noopener".
Don't use<img>elements in Next.js projects.
Don't use<head>elements in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
**/*.{ts,tsx}: Don't use primitive type aliases or misleading types.
Don't use empty type parameters in type aliases and interfaces.
Don't use any or unknown as type constraints.
Don't return a value from a function with the return type 'void'.
Don't use the TypeScript directive @ts-ignore.
Don't use TypeScript enums.
Don't add type annotations to variables, parameters, and class properties that are initialized with literal expressions.
Don't use TypeScript namespaces.
Don't use non-null assertions with the!postfix operator.
Don't use parameter properties in class constructors.
Don't use user-defined types.
Useas constinstead of literal types and type annotations.
Use eitherT[]orArray<T>consistently.
Initialize each enum member value explicitly.
Useexport typefor types.
Useimport typefor types.
Make sure all enum members are literal values.
Don't use TypeScript const enum.
Don't declare empty interfaces.
Don't let variables evolve into any type through reassignments.
Don't use the any type.
Don't misuse the non-null assertion operator (!) in TypeScript files.
Don't use implicit any type on variable declarations.
Don't merge interfaces and classes unsafely.
Don't use overload signatures that aren't next to each other.
Use the namespace keyword instead of the module keyword to declare TypeScript namespaces.
Use consistent accessibility modifiers on class properties and methods.
Use function types instead of object types with call signatures.
Don't use void type outside of generic or return types.
**/*.{ts,tsx}: Do NOT use types 'any', 'unknown' or 'never'. Use proper explicit types
Suffix functions with 'Action' in types, like 'type Test = { testAction }'
Files:
apps/dashboard/components/website-dialog.tsx
!(**/pages/_document.{ts,tsx,jsx})**/*.{ts,tsx,jsx}
📄 CodeRabbit inference engine (.cursor/rules/ultracite.mdc)
Don't import next/document outside of pages/_document.jsx in Next.js projects.
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{ts,tsx,html,css}
📄 CodeRabbit inference engine (.cursor/rules/use-bun-instead-of-node-vite-npm-pnpm.mdc)
Use
bun build <file.html|file.ts|file.css>instead ofwebpackoresbuildfor bundling
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{jsx,tsx}: When using 'text-right' utility class, always add 'text-balance' to prevent poor text layout
Think about mobile responsiveness when doing any UI tasks or changes
Always use 'rounded' Tailwind class, never 'rounded-xl' or 'rounded-md'
Don't use lucide for icons, ONLY use phosphor icons. Use width='duotone' for most icons, use fill for arrows, and don't add width attribute for plus icons
Decouple state management, data transformations, and API interactions from the React lifecycle in View Components
Simplify data flow to eliminate prop drilling and callback hell in components
Prioritize modularity and testability in all components
ALWAYS use error boundaries properly in React applications
Use 'Icon' suffix at the end of phosphor react icon imports, like CaretIcon not Caret. This is the default import, NOT as a named import
Almost NEVER use useEffect unless it's critical
Files:
apps/dashboard/components/website-dialog.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/01-MUST-DO.mdc)
**/*.{js,jsx,ts,tsx}: Split off components, utils, and reusable code to ensure better loading speed and less complexity
Use lower-case-like-this naming convention for variables, functions, and identifiers
NEVER add placeholders, mock data, or anything similar to production code
Use Dayjs for date handling, NEVER use date-fns. Use Tanstack query for hooks, NEVER use SWR
Use json.stringify() when adding debugging code
Never use barrel exports or create index files
Files:
apps/dashboard/components/website-dialog.tsx
🧠 Learnings (3)
📓 Common learnings
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
📚 Learning: 2025-12-02T22:55:00.415Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/guidelines.mdc:0-0
Timestamp: 2025-12-02T22:55:00.415Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Trim values to handle text expansion and trailing spaces in form submissions
Applied to files:
apps/dashboard/components/website-dialog.tsx
📚 Learning: 2025-12-02T22:57:07.791Z
Learnt from: CR
Repo: databuddy-analytics/Databuddy PR: 0
File: .cursor/rules/ultracite.mdc:0-0
Timestamp: 2025-12-02T22:57:07.791Z
Learning: Applies to **/*.{ts,tsx,js,jsx} : Use `String.trimStart()` and `String.trimEnd()` over `String.trimLeft()` and `String.trimRight()`.
Applied to files:
apps/dashboard/components/website-dialog.tsx
🧬 Code graph analysis (1)
apps/dashboard/components/website-dialog.tsx (1)
packages/validation/src/regexes.ts (1)
WEBSITE_NAME_REGEX(15-15)
🔇 Additional comments (6)
apps/dashboard/components/website-dialog.tsx (6)
3-6: LGTM!The new imports for
WEBSITE_NAME_REGEXandSubmitHandlerare correctly added and properly utilized in the validation schema and submit handler respectively.
45-49: LGTM!The name field validation correctly implements trimming and regex validation with an accurate error message that describes all allowed characters. This addresses the previous review feedback appropriately.
Based on learnings, trim values to handle text expansion and trailing spaces in form submissions.
80-80: LGTM!The
onBlurvalidation mode is a good UX choice that validates fields after users complete input, striking the right balance between immediate feedback and not interrupting typing.
126-157: LGTM!The properly typed
SubmitHandler<FormData>with theformDataparameter follows React Hook Form best practices and improves type safety throughout the submission logic.
162-165: LGTM!Excellent adherence to React Hook Form best practices by destructuring
isValidandisDirtyfromformStateto ensure proper re-renders. The explanatory comment with documentation link is helpful for maintainability.
87-93: LGTM!This
useEffectis a legitimate critical use case for synchronizing form state with the website prop during edit mode. Without it, the form wouldn't populate with existing data when editing a website.
Description
This pull request updates the website dialog form validation and improves the handling of form state in the
WebsiteDialogcomponent. The most important changes include enforcing a stricter validation rule for website names, using the correct form state properties for submit button logic, and ensuring validation occurs on blur.Validation improvements:
namefield in the form schema to use theWEBSITE_NAME_REGEXpattern, enforcing allowed characters for website names.WEBSITE_NAME_REGEXfrom@databuddy/validationto centralize validation logic.Form state handling:
"onBlur"to trigger validation when fields lose focus.isValidandisDirtyfromform.formState, following React Hook Form best practices for triggering re-renders.Checklist
Summary by CodeRabbit
✏️ Tip: You can customize this high-level summary in your review settings.