Skip to content

Comments

Add ultracite/biome#569

Merged
elie222 merged 3 commits intomainfrom
chore/ultracite
Jul 15, 2025
Merged

Add ultracite/biome#569
elie222 merged 3 commits intomainfrom
chore/ultracite

Conversation

@elie222
Copy link
Owner

@elie222 elie222 commented Jul 14, 2025

I disabled a lot of rules as it will lead to a big merge conflict with staging if we add all rules now. Once staging is merged in we can delete most of the disabled lint rules.

Summary by CodeRabbit

  • New Features

    • Introduced Ultracite configuration with comprehensive coding standards for JavaScript and TypeScript projects.
    • Added a strict TypeScript configuration enabling strict null checks.
  • Chores

    • Removed all ESLint and Prettier configurations, dependencies, and related files.
    • Updated formatting and linting tools to use Biome and Ultracite.
    • Updated VSCode settings for consistent formatting and auto-fixing on save.
    • Enhanced pre-commit hook to include Ultracite formatting.
    • Cleaned up Dockerfile and project documentation to reflect tool changes.
  • Style

    • Applied minor formatting improvements across code, configuration, and documentation files.
  • Bug Fixes

    • Fixed comment syntax in code documentation.
  • Refactor

    • Simplified code syntax and improved type safety in several utility and component files.
  • Tests

    • Minor syntax improvements and removal of unused imports in test files.

@vercel
Copy link

vercel bot commented Jul 14, 2025

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Updated (UTC)
inbox-zero ✅ Ready (Inspect) Visit Preview Jul 14, 2025 11:02pm

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Jul 14, 2025

Walkthrough

This update removes all ESLint-related configuration, packages, and documentation from the repository, replacing linting and formatting tools with Biome and Ultracite. It introduces a stricter TypeScript null checking policy, updates project formatting and VSCode settings, and makes minor syntax, style, and formatting improvements throughout the codebase.

Changes

File(s) / Path(s) Change Summary
.eslintrc.js, apps/web/.eslintrc.json, packages/eslint-config/* Removed all ESLint configuration files and the internal ESLint config package.
package.json, apps/web/package.json, biome.json, .vscode/settings.json, .husky/pre-commit, .cursor/rules/ultracite.mdc, .cursor/rules/project-structure.mdc Replaced ESLint/Prettier with Biome and Ultracite; updated lint-staged, VSCode, and pre-commit settings; added Ultracite rules.
tsconfig.json Added with "strictNullChecks": true for stricter TypeScript null handling.
docker/Dockerfile.prod Stopped copying packages/eslint-config/package.json during build.
apps/web/utils/error.ts, apps/web/utils/redis/subscriber.ts, apps/web/utils/assess.ts Simplified function/class signatures by removing explicit access modifiers or multi-line declarations.
apps/web/utils/actions/admin.ts, apps/web/app/api/user/stats/day/route.ts Removed unnecessary explicit undefined initializations.
apps/web/app/api/google/webhook/process-history-item.test.ts, apps/web/app/api/lemon-squeezy/webhook/route.ts, apps/web/__tests__/ai-extract-from-email-history.test.ts Refactored to use ES6 object property shorthand.
apps/web/components/assistant-chat/message.tsx Added key prop to <Skeleton> component in list rendering.
apps/web/components/assistant-chat/message-editor.tsx Disabled a Biome linter rule with a comment directive.
apps/web/components/TabSelect.tsx Removed aria-selected attribute from button.
apps/web/app/(app)/[emailAccountId]/assistant/group/ViewGroup.tsx Removed void operator from form submission handler.
apps/web/__tests__/ai/reply/draft-with-knowledge.test.ts Removed unused type import.
apps/web/components/editor/SimpleRichTextEditor.css Reformatted CSS selectors for improved readability.
apps/web/styles/globals.css, turbo.json, apps/web/app/manifest.json Removed trailing whitespace or added newline for formatting consistency.
apps/web/sanity.cli.ts, apps/web/postcss.config.js, apps/web/vitest.config.mts Fixed comment or statement termination and formatting.
apps/web/app/(marketing) Updated subproject commit reference.

Sequence Diagram(s)

sequenceDiagram
    participant Developer
    participant Pre-commit Hook
    participant Ultracite
    participant Biome
    participant VSCode

    Developer->>Pre-commit Hook: Stage changes & commit
    Pre-commit Hook->>Ultracite: Run format (npx ultracite format)
    Pre-commit Hook->>lint-staged: Run on staged files
    VSCode->>Biome: Format on save/paste
    VSCode->>Ultracite: (optionally) Run formatting via tasks
Loading

Possibly related PRs

  • Add UI for cursor rules style prompt #227: Removes the ESLint config package and its usage, including deleting packages/eslint-config/next.js and apps/web/.eslintrc.json, directly related to ESLint config removal in this PR.

Poem

🐇✨
A rabbit hops, the code is neat,
ESLint and Prettier take their seat.
Biome and Ultracite now lead the way,
Formatting files in a snappy ballet.
With strict null checks and cleaner style,
This codebase will run for many a mile!
🐇✨


📜 Recent review details

Configuration used: .coderabbit.yaml
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e85824d and 7d98382.

📒 Files selected for processing (1)
  • apps/web/utils/error.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • apps/web/utils/error.ts
⏰ 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). (3)
  • GitHub Check: Jit Security
  • GitHub Check: claude-review
  • GitHub Check: Analyze (javascript-typescript)
✨ Finishing Touches
  • 📝 Generate Docstrings

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
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Explain this complex logic.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai explain this code block.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and explain its main purpose.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Support

Need 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)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR.
  • @coderabbitai generate sequence diagram to generate a sequence diagram of the changes in this PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

@claude
Copy link

claude bot commented Jul 14, 2025

Claude finished @elie222's task —— View job


PR Review: ESLint to Biome Migration

Reviewing this major migration from ESLint to Biome. Here's my analysis progress:

  • Review Biome configuration (biome.json)
  • Analyze removed ESLint configurations
  • Check package.json changes and dependency updates
  • Review formatting changes across codebase
  • Examine new Cursor rules and documentation
  • Check pre-commit hook updates
  • Assess security and performance implications
  • Provide comprehensive feedback

Summary

This PR successfully migrates the inbox-zero codebase from ESLint to Biome, implementing the "Ultracite" configuration standard. The migration appears well-executed with comprehensive configuration and documentation.

✅ Strengths

  1. Complete Migration: Properly removes all ESLint configurations (.eslintrc.js, apps/web/.eslintrc.json, entire packages/eslint-config/ package)

  2. Comprehensive Biome Configuration: biome.json:115 extends "ultracite" with extensive rule customizations that appropriately disable overly strict rules while maintaining code quality

  3. Updated Tooling Integration:

    • Pre-commit hooks updated (.husky/pre-commit:4) to use npx ultracite format
    • VSCode settings (.vscode/settings.json:4,11,18) properly configured for Biome formatting
    • Package scripts (root package.json:11-12) include new format commands
  4. Excellent Documentation: The new .cursor/rules/ultracite.mdc provides comprehensive guidelines covering accessibility, React best practices, TypeScript conventions, and security

  5. Performance Benefits: Biome provides significantly faster linting/formatting than ESLint

⚠️ Areas for Attention

  1. Many Disabled Rules: The Biome configuration disables many recommended rules (54 total disabled rules). While this enables easier migration, consider gradually re-enabling rules that provide value:

    • correctness.noUnusedImports: "off" (biome.json:62) - unused imports should typically be cleaned up
    • correctness.noUnusedVariables: "off" (biome.json:61) - unused variables can indicate dead code
    • style.useFilenamingConvention: "off" (biome.json:12) - consistent file naming improves maintainability
  2. Linting Workflow: The turbo configuration (turbo.json:127) shows an empty lint task, but it's unclear how Biome linting is integrated into the build process

  3. Missing Error Handling: No apparent fallback if Biome formatting fails in pre-commit hooks

🔍 Security & Performance Analysis

Security: ✅ Clean migration with no security concerns

  • Biome is a well-maintained tool by the Babel team
  • Configuration doesn't expose sensitive data
  • No suspicious dependencies added

Performance: ✅ Significant improvements expected

  • Biome is ~100x faster than ESLint for similar operations
  • Reduced dependency tree (removed entire ESLint ecosystem)
  • Bundle size reduction from fewer dev dependencies

📝 Minor Suggestions

  1. Consider Re-enabling Select Rules:

    "correctness": {
      "noUnusedImports": "warn", // Instead of "off"
      "noUnusedVariables": "warn", // Instead of "off"
    }
  2. Add Biome to Turbo Pipeline: Update turbo.json to include Biome linting:

    "lint": {
      "dependsOn": ["^lint"],
      "outputs": []
    }
  3. Document Migration: Consider adding a brief migration note to explain the switch from ESLint to Biome for team members

🎯 Overall Assessment

Excellent migration that modernizes the tooling stack with significant performance benefits. The Ultracite configuration provides comprehensive code quality standards while remaining practical for a large codebase. The extensive documentation in .cursor/rules/ultracite.mdc is particularly valuable for maintaining consistency.

Recommendation: ✅ Approve with minor suggestions

The migration is well-executed and ready for production. The disabled rules can be addressed incrementally in future PRs as the team adapts to Biome's more opinionated defaults.


@elie222 elie222 mentioned this pull request Jul 14, 2025
@socket-security
Copy link

socket-security bot commented Jul 14, 2025

Review the following changes in direct dependencies. Learn more about Socket for GitHub.

Diff Package Supply Chain
Security
Vulnerability Quality Maintenance License
Addedcapital-case@​2.0.01001006276100
Addedclass-variance-authority@​0.7.11001006577100
Addedcheerio@​1.0.09910010083100
Updated@​biomejs/​biome@​1.9.4 ⏵ 2.1.1100 +710010099100

View full report

Copy link
Contributor

@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: 5

🧹 Nitpick comments (4)
apps/web/sanity.cli.ts (1)

1-4: Good catch on the comment terminator – consider validating env vars as well

The */ fix prevents malformed JSDoc parsing. While touching this header, it’s worth asserting that projectId and dataset are defined before exporting the config to avoid Sanity CLI runtime failures in mis-configured environments.

+if (!projectId || !dataset) {
+  throw new Error("Sanity CLI requires NEXT_PUBLIC_SANITY_PROJECT_ID and NEXT_PUBLIC_SANITY_DATASET");
+}
apps/web/components/assistant-chat/message-editor.tsx (1)

34-34: Complete the explanation for the lint rule suppression.

The biome-ignore comment contains a placeholder <explanation> that should be replaced with a proper explanation for why the useExhaustiveDependencies rule is being disabled.

-  // biome-ignore lint/correctness/useExhaustiveDependencies: <explanation>
+  // biome-ignore lint/correctness/useExhaustiveDependencies: adjustHeight is stable and only needed to run once on mount
package.json (1)

24-26: Duplicate formatting on pre-commit – lint-staged already runs Ultracite.

Running npx ultracite format inside lint-staged and again inside the Husky hook wastes time and may create merge-index churn.

If Husky executes lint-staged, drop the explicit ultracite format step in one place to avoid double work.

biome.json (1)

88-93: Formatter config duplicates rules – keep it in one place.

"javascript.formatter" overrides quoteStyle & trailingCommas, but Biome already respects the top-level formatter options.
Unless you need language-specific overrides, prefer a single source of truth:

-  "javascript": {
-    "formatter": {
-      "quoteStyle": "double",
-      "trailingCommas": "all"
-    }
-  },
+  // Remove block above – configure via top-level "formatter" or .editorconfig
📜 Review details

Configuration used: .coderabbit.yaml
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between f650225 and e85824d.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (37)
  • .cursor/rules/project-structure.mdc (1 hunks)
  • .cursor/rules/ultracite.mdc (1 hunks)
  • .eslintrc.js (0 hunks)
  • .husky/pre-commit (1 hunks)
  • .vscode/settings.json (1 hunks)
  • apps/web/.eslintrc.json (0 hunks)
  • apps/web/__tests__/ai-extract-from-email-history.test.ts (1 hunks)
  • apps/web/__tests__/ai/reply/draft-with-knowledge.test.ts (0 hunks)
  • apps/web/app/(app)/[emailAccountId]/assistant/group/ViewGroup.tsx (1 hunks)
  • apps/web/app/(marketing) (1 hunks)
  • apps/web/app/api/google/webhook/process-history-item.test.ts (1 hunks)
  • apps/web/app/api/lemon-squeezy/webhook/route.ts (1 hunks)
  • apps/web/app/api/user/stats/day/route.ts (1 hunks)
  • apps/web/app/manifest.json (1 hunks)
  • apps/web/components/TabSelect.tsx (0 hunks)
  • apps/web/components/assistant-chat/message-editor.tsx (1 hunks)
  • apps/web/components/assistant-chat/message.tsx (1 hunks)
  • apps/web/components/editor/SimpleRichTextEditor.css (2 hunks)
  • apps/web/package.json (0 hunks)
  • apps/web/postcss.config.js (1 hunks)
  • apps/web/sanity.cli.ts (1 hunks)
  • apps/web/styles/globals.css (1 hunks)
  • apps/web/utils/actions/admin.ts (1 hunks)
  • apps/web/utils/assess.ts (1 hunks)
  • apps/web/utils/error.ts (1 hunks)
  • apps/web/utils/redis/subscriber.ts (2 hunks)
  • apps/web/vitest.config.mts (1 hunks)
  • biome.json (1 hunks)
  • docker/Dockerfile.prod (0 hunks)
  • package.json (1 hunks)
  • packages/eslint-config/README.md (0 hunks)
  • packages/eslint-config/library.js (0 hunks)
  • packages/eslint-config/next.js (0 hunks)
  • packages/eslint-config/package.json (0 hunks)
  • packages/eslint-config/react-internal.js (0 hunks)
  • tsconfig.json (1 hunks)
  • turbo.json (1 hunks)
💤 Files with no reviewable changes (11)
  • apps/web/tests/ai/reply/draft-with-knowledge.test.ts
  • apps/web/components/TabSelect.tsx
  • packages/eslint-config/README.md
  • docker/Dockerfile.prod
  • apps/web/package.json
  • .eslintrc.js
  • packages/eslint-config/package.json
  • packages/eslint-config/react-internal.js
  • apps/web/.eslintrc.json
  • packages/eslint-config/next.js
  • packages/eslint-config/library.js
🧰 Additional context used
📓 Path-based instructions (8)
apps/web/app/**/*

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • apps/web/CLAUDE.md
apps/web/**/*.{ts,tsx}

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • apps/web/CLAUDE.md
**/*.{ts,tsx}

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • .cursor/rules/form-handling.mdc
turbo.json

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • .cursor/rules/environment-variables.mdc
.cursor/rules/*.mdc

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • .cursor/rules/cursor-rules.mdc
.cursor/rules/[a-z0-9\-]*.mdc

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • .cursor/rules/cursor-rules.mdc
apps/web/**/*.tsx

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • apps/web/CLAUDE.md
**/*.tsx

Instructions used from:

Sources:
📄 CodeRabbit Inference Engine

  • .cursor/rules/data-fetching.mdc
  • .cursor/rules/form-handling.mdc
🧠 Learnings (18)
📓 Common learnings
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use TypeScript with strict null checks
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
apps/web/sanity.cli.ts (4)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Path aliases: Use `@/` for imports from project root
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/prisma.mdc:0-0
Timestamp: 2025-06-23T12:26:53.882Z
Learning: In this project, Prisma should be imported using 'import prisma from "@/utils/prisma";' in TypeScript files.
turbo.json (4)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/environment-variables.mdc:0-0
Timestamp: 2025-07-03T12:02:45.107Z
Learning: Applies to turbo.json : Add all new environment variables to the `env` array under the `build` task in `turbo.json`
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/{.env.example,env.ts,turbo.json} : Add environment variables to `.env.example`, `env.ts`, and `turbo.json`
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/security-audit.mdc:0-0
Timestamp: 2025-06-23T12:27:05.686Z
Learning: Do not hardcode secrets directly in code for cron endpoints; secrets should be managed via environment variables (e.g., CRON_SECRET) and not as plain strings in the source code.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/security.mdc:0-0
Timestamp: 2025-06-23T12:27:17.978Z
Learning: Sensitive data (such as secrets and credentials) must be stored in environment variables, not in code or version control.
apps/web/postcss.config.js (3)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/utilities.mdc:0-0
Timestamp: 2025-06-23T12:27:35.927Z
Learning: Use lodash utilities for common operations involving arrays, objects, and strings to promote code consistency and reliability.
tsconfig.json (10)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use TypeScript with strict null checks
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Define validation schemas using Zod
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Apply the same validation in both client and server
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/llm.mdc:0-0
Timestamp: 2025-06-23T12:26:36.694Z
Learning: Use TypeScript types for all parameters and return values, and define clear interfaces for complex input and output structures to ensure type safety.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Use descriptive error messages
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/types/**/*.{ts,d.ts} : Centralize types in dedicated type files when shared
Learnt from: elie222
PR: elie222/inbox-zero#537
File: apps/web/app/api/user/stats/newsletters/route.ts:235-239
Timestamp: 2025-07-08T13:14:03.250Z
Learning: The user prefers proper TypeScript error type checking (using `error instanceof Error`) over type assertions with `as any` for better type safety and code quality.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/prisma.mdc:0-0
Timestamp: 2025-06-23T12:26:53.882Z
Learning: In this project, Prisma should be imported using 'import prisma from "@/utils/prisma";' in TypeScript files.
.cursor/rules/project-structure.mdc (13)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Cursor rule files must have a frontmatter section with description, globs, and alwaysApply fields
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to /*.mdc : Never place Cursor rule files in the project root
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Always place rule files in PROJECT_ROOT/.cursor/rules/
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Cursor rule files must use markdown formatting for main content, including step-by-step instructions, code examples, and guidelines
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to **/*.mdc : Never place Cursor rule files in subdirectories outside .cursor/rules
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Make Cursor rule file names descriptive of the rule's purpose
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/[a-z0-9\-]*.mdc : Use kebab-case for filenames of Cursor rule files
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Always use .mdc extension for Cursor rule files
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/index.mdc:0-0
Timestamp: 2025-06-23T12:26:22.732Z
Learning: Use dedicated markdown files for each major guideline or feature to keep documentation modular and maintainable.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/task-list.mdc:0-0
Timestamp: 2025-06-23T12:27:27.569Z
Learning: When managing project progress, use markdown files (such as 'TASKS.md' or feature-specific markdown files at the project root) to create structured task lists with clear sections for completed, in-progress, and future tasks, as well as implementation plans and relevant files.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/index.mdc:0-0
Timestamp: 2025-06-23T12:26:22.732Z
Learning: Organize code guidelines by category (Core, Frontend, Backend, AI, Testing, Features) to facilitate targeted learning and easier onboarding.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/index.mdc:0-0
Timestamp: 2025-06-23T12:26:22.732Z
Learning: Maintain a central index of all active coding rules and guidelines to ensure discoverability and consistency across the project.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/task-list.mdc:0-0
Timestamp: 2025-06-23T12:27:27.569Z
Learning: The 'Relevant Files' section in task list markdown files should be kept up to date with file paths, brief descriptions of each file's purpose, and status indicators (such as checkmarks for completed components).
apps/web/app/(app)/[emailAccountId]/assistant/group/ViewGroup.tsx (1)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.tsx : Validate form inputs before submission
apps/web/__tests__/ai-extract-from-email-history.test.ts (1)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/llm-test.mdc:0-0
Timestamp: 2025-06-23T12:26:27.693Z
Learning: When writing tests for LLM-related functionality in TypeScript (e.g., in 'apps/web/__tests__/*.test.ts'), always create helper functions for common test data to ensure consistency and reduce duplication.
.husky/pre-commit (3)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/installing-packages.mdc:0-0
Timestamp: 2025-06-23T12:26:24.473Z
Learning: Use 'pnpm' as the package manager for installing dependencies in the project.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
apps/web/vitest.config.mts (5)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/{.env.example,env.ts,turbo.json} : Add environment variables to `.env.example`, `env.ts`, and `turbo.json`
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/testing.mdc:0-0
Timestamp: 2025-06-23T12:27:30.570Z
Learning: When mocking Prisma in Vitest, import the Prisma mock from '@/utils/__mocks__/prisma', mock '@/utils/prisma', and clear all mocks in a beforeEach hook to ensure test isolation.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/prisma.mdc:0-0
Timestamp: 2025-06-23T12:26:53.882Z
Learning: In this project, Prisma should be imported using 'import prisma from "@/utils/prisma";' in TypeScript files.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/environment-variables.mdc:0-0
Timestamp: 2025-07-03T12:02:45.107Z
Learning: Applies to apps/web/env.ts : For client-side environment variables, prefix them with `NEXT_PUBLIC_` and add them to both the `client` and `experimental__runtimeEnv` sections in `apps/web/env.ts`
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/{.env.example,env.ts} : Client-side environment variables must be prefixed with `NEXT_PUBLIC_`
apps/web/components/editor/SimpleRichTextEditor.css (2)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
apps/web/utils/assess.ts (2)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/gmail-api.mdc:0-0
Timestamp: 2025-06-23T12:26:14.189Z
Learning: Always use wrapper functions from the utils folder (e.g., apps/web/utils/gmail/message.ts) to interact with provider APIs, ensuring maintainability and easier future provider support.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/gmail-api.mdc:0-0
Timestamp: 2025-06-23T12:26:14.189Z
Learning: Never call provider APIs (such as Gmail) directly from routes or components; always use abstraction layers provided by utility wrapper functions.
apps/web/components/assistant-chat/message-editor.tsx (5)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Prefer functional components with hooks
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Use descriptive error messages
Learnt from: elie222
PR: elie222/inbox-zero#485
File: apps/web/app/(landing)/login/page.tsx:41-43
Timestamp: 2025-06-05T09:49:12.168Z
Learning: In Next.js App Router, components that use the `useSearchParams` hook require a Suspense boundary to handle the asynchronous nature of search parameter access. The Suspense wrapper is necessary and should not be removed when a component uses useSearchParams.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/ui-components.mdc:0-0
Timestamp: 2025-06-23T12:27:33.499Z
Learning: For multi-line text input, use the `Input` component with `type="text"`, `autosizeTextarea`, and `rows` props to create an autosizing textarea, and handle validation and errors similarly to single-line inputs.
apps/web/utils/error.ts (6)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/security-audit.mdc:0-0
Timestamp: 2025-06-23T12:27:05.686Z
Learning: Error messages returned to clients should not reveal internal details or sensitive data; use generic error messages and SafeError for consistent and secure error responses.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Use descriptive error messages
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/security.mdc:0-0
Timestamp: 2025-06-23T12:27:17.978Z
Learning: Error responses should use generic messages and consistent formats (e.g., SafeError) to avoid leaking sensitive information or internal logic.
Learnt from: elie222
PR: elie222/inbox-zero#537
File: apps/web/app/api/user/stats/newsletters/route.ts:235-239
Timestamp: 2025-07-08T13:14:03.250Z
Learning: The user prefers proper TypeScript error type checking (using `error instanceof Error`) over type assertions with `as any` for better type safety and code quality.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use proper error handling with try/catch blocks
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/server-actions.mdc:0-0
Timestamp: 2025-06-23T12:27:23.938Z
Learning: SafeError should be used within server actions to handle expected errors in a centralized manner.
.cursor/rules/ultracite.mdc (20)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Make Cursor rule file names descriptive of the rule's purpose
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Cursor rule files must use markdown formatting for main content, including step-by-step instructions, code examples, and guidelines
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Cursor rule files must have a frontmatter section with description, globs, and alwaysApply fields
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Always use .mdc extension for Cursor rule files
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/[a-z0-9\-]*.mdc : Use kebab-case for filenames of Cursor rule files
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to .cursor/rules/*.mdc : Always place rule files in PROJECT_ROOT/.cursor/rules/
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to /*.mdc : Never place Cursor rule files in the project root
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/cursor-rules.mdc:0-0
Timestamp: 2025-07-03T12:02:24.598Z
Learning: Applies to **/*.mdc : Never place Cursor rule files in subdirectories outside .cursor/rules
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/index.mdc:0-0
Timestamp: 2025-06-23T12:26:22.732Z
Learning: Clearly document the purpose and scope of each rule file to help developers quickly understand where to find relevant guidance.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/index.mdc:0-0
Timestamp: 2025-06-23T12:26:22.732Z
Learning: Maintain a central index of all active coding rules and guidelines to ensure discoverability and consistency across the project.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use proper error handling with try/catch blocks
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/data-fetching.mdc:0-0
Timestamp: 2025-07-03T12:02:38.024Z
Learning: Applies to **/*.tsx : Use `result?.serverError` with `toastError` and `toastSuccess` for error handling; success toast is optional
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Use descriptive error messages
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/server-actions.mdc:0-0
Timestamp: 2025-06-23T12:27:23.938Z
Learning: In Next.js projects, server actions should be implemented using the next-safe-action library to ensure type safety, input validation, context management, and centralized error handling.
Learnt from: elie222
PR: elie222/inbox-zero#537
File: apps/web/app/api/user/stats/newsletters/route.ts:235-239
Timestamp: 2025-07-08T13:14:03.250Z
Learning: The user prefers proper TypeScript error type checking (using `error instanceof Error`) over type assertions with `as any` for better type safety and code quality.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/llm.mdc:0-0
Timestamp: 2025-06-23T12:26:36.694Z
Learning: Implement early returns for invalid inputs, use proper error types and logging, provide fallbacks for AI failures, and add retry logic for transient failures (e.g., using a 'withRetry' utility).
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use TypeScript with strict null checks
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/ui-components.mdc:0-0
Timestamp: 2025-06-23T12:27:33.499Z
Learning: When fetching data from an API in a Next.js React application, use the `swr` package for GET requests to the server. This provides built-in caching, revalidation, and error handling.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/llm-test.mdc:0-0
Timestamp: 2025-06-23T12:26:27.693Z
Learning: When writing tests for LLM-related functionality in TypeScript (e.g., in 'apps/web/__tests__/*.test.ts'), always create helper functions for common test data to ensure consistency and reduce duplication.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/llm.mdc:0-0
Timestamp: 2025-06-23T12:26:36.694Z
Learning: Use TypeScript types for all parameters and return values, and define clear interfaces for complex input and output structures to ensure type safety.
biome.json (8)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Define validation schemas using Zod
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/prisma.mdc:0-0
Timestamp: 2025-06-23T12:26:53.882Z
Learning: In this project, Prisma should be imported using 'import prisma from "@/utils/prisma";' in TypeScript files.
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Apply the same validation in both client and server
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/{.env.example,env.ts,turbo.json} : Add environment variables to `.env.example`, `env.ts`, and `turbo.json`
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Use TypeScript with strict null checks
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/types/**/*.{ts,d.ts} : Centralize types in dedicated type files when shared
package.json (5)
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/installing-packages.mdc:0-0
Timestamp: 2025-06-23T12:26:24.473Z
Learning: Use 'pnpm' as the package manager for installing dependencies in the project.
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/{.env.example,env.ts,turbo.json} : Add environment variables to `.env.example`, `env.ts`, and `turbo.json`
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/environment-variables.mdc:0-0
Timestamp: 2025-07-03T12:02:45.107Z
Learning: Applies to turbo.json : Add all new environment variables to the `env` array under the `build` task in `turbo.json`
.vscode/settings.json (3)
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.{ts,tsx} : Format code with Prettier
Learnt from: CR
PR: elie222/inbox-zero#0
File: apps/web/CLAUDE.md:0-0
Timestamp: 2025-07-03T12:02:16.137Z
Learning: Applies to apps/web/**/*.tsx : Follow tailwindcss patterns with prettier-plugin-tailwindcss
Learnt from: CR
PR: elie222/inbox-zero#0
File: .cursor/rules/form-handling.mdc:0-0
Timestamp: 2025-07-03T12:02:53.001Z
Learning: Applies to **/*.{ts,tsx} : Define validation schemas using Zod
🔇 Additional comments (20)
apps/web/app/manifest.json (1)

22-23: Good housekeeping: newline at EOF added

Adding a newline at the end of the file conforms to POSIX conventions and avoids diff-noise in future edits. No further action required.

apps/web/app/(marketing) (1)

1-1: Ignore – (marketing) is a Next.js route group, not a Git submodule
There is no .gitmodules entry or submodule at apps/web/app/(marketing). The parentheses denote a Next.js route grouping, so there’s no SHA to verify upstream.

Likely an incorrect or invalid review comment.

apps/web/styles/globals.css (1)

10-10: Whitespace cleanup acknowledged

Trailing-whitespace removal is harmless and aligns with the new formatter settings.

apps/web/postcss.config.js (1)

6-6: Semicolon is purely stylistic

module.exports = { … } doesn’t need a semicolon, but adding one is stylistically fine and consistent with Biome defaults.

apps/web/__tests__/ai-extract-from-email-history.test.ts (1)

80-82: 👍 Shorthand property improves readability

Using historicalMessages shorthand eliminates redundancy without changing behaviour.

turbo.json (1)

45-66: Whitespace trimmed – no functional impact

The env list remains unchanged; only stray spaces were removed. Looks good.

Also applies to: 48-48, 53-56, 59-62, 64-66

apps/web/app/api/google/webhook/process-history-item.test.ts (1)

84-84: Good modernization with ES6 shorthand property notation.

This change improves code conciseness while maintaining the same functionality.

apps/web/app/api/lemon-squeezy/webhook/route.ts (1)

223-223: Consistent application of ES6 shorthand property notation.

This change aligns with modern JavaScript conventions and improves code consistency across the codebase.

apps/web/app/api/user/stats/day/route.ts (1)

42-42: Cleaner TypeScript with strict null checking.

Removing the explicit undefined initialization is cleaner since TypeScript variables with union types including undefined are undefined by default. This aligns with the stricter TypeScript configuration.

apps/web/components/assistant-chat/message.tsx (1)

109-109: Good React best practice with unique key prop.

Adding the key prop using toolCallId is essential for React's reconciliation algorithm and prevents potential rendering issues in lists.

apps/web/utils/actions/admin.ts (1)

83-83: Consistent TypeScript improvement.

Removing the explicit undefined initialization is consistent with the stricter TypeScript configuration. The variable is properly typed and the pagination logic correctly handles the undefined case.

apps/web/app/(app)/[emailAccountId]/assistant/group/ViewGroup.tsx (1)

177-177: LGTM - Style improvement aligns with new formatting standards.

The removal of the void operator is a minor style improvement that doesn't affect functionality. The promise returned by handleSubmit is still handled appropriately even without explicitly discarding it.

apps/web/components/editor/SimpleRichTextEditor.css (2)

16-21: LGTM - Improved CSS readability.

The reformatting of these complex CSS selectors across multiple lines significantly improves readability while maintaining the exact same functionality.


30-34: LGTM - Consistent formatting improvement.

Similar readability improvement for the dark mode CSS selectors, maintaining consistency with the formatting applied above.

apps/web/vitest.config.mts (1)

2-13: LGTM - Formatting consistency improvements.

The changes from single to double quotes and other formatting adjustments improve code consistency without affecting the Vitest configuration functionality.

apps/web/utils/assess.ts (1)

13-13: LGTM - Cleaner function signature.

The consolidation of parameter destructuring and type annotation into a single inline declaration improves code conciseness without affecting functionality.

apps/web/utils/redis/subscriber.ts (1)

11-11: LGTM! Access modifier removal is a valid style improvement.

The removal of explicit public access modifiers from static methods aligns with TypeScript best practices, as static methods are public by default. This change maintains the same functionality while following the new linting standards.

Also applies to: 33-33

.vscode/settings.json (2)

17-19: Code actions configuration looks good.

The Biome code actions for fixing issues and organizing imports are properly configured with explicit activation, which ensures predictable behavior during development.


9-12: Dual-formatter configuration confirmed as intentional for migration

We’ve located a Prettier config at apps/web/prettier.config.js, which shows Prettier is still required for the web app (including Tailwind formatting), while Biome is being adopted as the formatter for JS/TS files in VS Code. This split aligns with the ongoing migration plan—no changes needed here.

.husky/pre-commit (1)

3-4: Good addition of Ultracite formatting to pre-commit workflow.

Adding npx ultracite format to the pre-commit hook aligns with the project's migration to Ultracite for code formatting. The execution order (lint-staged first, then formatting) ensures proper code quality checks before formatting.

Comment on lines +1 to +5
{
"compilerOptions": {
"strictNullChecks": true
}
} No newline at end of file
Copy link
Contributor

Choose a reason for hiding this comment

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

💡 Verification agent

🧩 Analysis chain

Excellent! Enabling strict null checks improves type safety.

This change aligns perfectly with the coding guidelines requiring strict null checks for TypeScript files. The strict null checking will help catch potential runtime null/undefined errors at compile time.

Verify if this minimal configuration is complete.

This tsconfig.json only contains strictNullChecks setting. Ensure this is intentional and that other necessary TypeScript configurations are handled elsewhere (e.g., workspace configs or extended configurations).


🏁 Script executed:

#!/bin/bash
# Check for other TypeScript configuration files in the project
fd -t f 'tsconfig.*\.json' .

Length of output: 281


🏁 Script executed:

#!/bin/bash
# Check for "extends" in all tsconfig.json to see inheritance patterns
rg '"extends"' -n --color never

Length of output: 481


Include a shared base config in root tsconfig.json

Your root tsconfig.json currently only enables strictNullChecks and doesn’t extend any common settings. To ensure a consistent TypeScript setup across the monorepo, please:

  • Add an "extends" field pointing to your shared base config (e.g. "packages/tsconfig/base.json") so you inherit all recommended compilerOptions (target, moduleResolution, strict modes, etc.).
  • If this file is meant ONLY to override strictNullChecks at the workspace level, add a comment explaining its role and ensure all other configs import it (or vice versa).

File to update:

  • tsconfig.json (repo root)
🤖 Prompt for AI Agents
In tsconfig.json at the root (lines 1 to 5), add an "extends" field referencing
the shared base config file, such as "packages/tsconfig/base.json", to inherit
common compilerOptions across the monorepo. If this root tsconfig.json is only
meant to override "strictNullChecks", add a comment explaining this purpose for
clarity. Ensure that other tsconfig files either extend this root config or the
base config consistently to maintain uniform TypeScript settings.

Comment on lines 1 to 5
---
description: Project structure and file organization guidelines
globs:
globs:
alwaysApply: false
---
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Fix malformed front-matter (globs has no value).

globs: must be a valid YAML value (usually a quoted glob or an array).
Without it, the file fails to parse and the rule is silently ignored.

 ---
 description: Project structure and file organization guidelines
-globs:
+globs:
+  - "apps/**"
+  - "packages/**"
 alwaysApply: false
 ---
📝 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.

Suggested change
---
description: Project structure and file organization guidelines
globs:
globs:
alwaysApply: false
---
---
description: Project structure and file organization guidelines
globs:
- "apps/**"
- "packages/**"
alwaysApply: false
---
🤖 Prompt for AI Agents
In .cursor/rules/project-structure.mdc at lines 1 to 5, the front-matter is
malformed because the `globs` key has no value, causing YAML parsing errors and
the rule to be ignored. Fix this by assigning a valid YAML value to `globs`,
such as an empty array `[]` or a quoted glob pattern string, ensuring the
front-matter is correctly formatted and the rule is applied.

Comment on lines 11 to 13
"format-and-lint": "biome check .",
"format-and-lint:fix": "biome check . --write"
},
Copy link
Contributor

Choose a reason for hiding this comment

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

🛠️ Refactor suggestion

Scripts still point to Biome only – Ultracite now does the heavy lifting.

format-and-lint* invoke biome but the project just migrated to Ultracite for both linting and formatting.
This will lead to two different code-style sources and inconsistent CI results.

-"format-and-lint": "biome check .",
-"format-and-lint:fix": "biome check . --write"
+"format-and-lint": "ultracite lint",
+"format-and-lint:fix": "ultracite format"
📝 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.

Suggested change
"format-and-lint": "biome check .",
"format-and-lint:fix": "biome check . --write"
},
"format-and-lint": "ultracite lint",
"format-and-lint:fix": "ultracite format"
},
🤖 Prompt for AI Agents
In package.json lines 11 to 13, the scripts "format-and-lint" and
"format-and-lint:fix" still use the Biome tool, but the project has migrated to
Ultracite for linting and formatting. Update these script commands to invoke
Ultracite instead of Biome to ensure consistent code style and CI results across
the project.

Comment on lines +1 to +4
---
alwaysApply: false
---

Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Mandatory front-matter fields missing (description, globs).

Cursor rule files must include description, globs, and alwaysApply.
Currently only alwaysApply is present, so the rule is ignored.

 ---
+description: Ultracite lint / format rules for JS & TS projects
+globs:
+  - "**/*.{js,jsx,ts,tsx}"
 alwaysApply: false
 ---
📝 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.

Suggested change
---
alwaysApply: false
---
---
description: Ultracite lint / format rules for JS & TS projects
globs:
- "**/*.{js,jsx,ts,tsx}"
alwaysApply: false
---
🤖 Prompt for AI Agents
In .cursor/rules/ultracite.mdc at lines 1 to 4, the front-matter is missing the
mandatory fields `description` and `globs`. Add these fields with appropriate
values describing the rule and specifying the file patterns it should apply to,
alongside the existing `alwaysApply` field, to ensure the rule is recognized and
applied.

@claude
Copy link

claude bot commented Jul 14, 2025

Claude finished @elie222's task —— View job


PR Review: ESLint to Biome Migration

Reviewing this major migration from ESLint to Biome. Here's my analysis progress:

  • Read repository setup and guidelines (CLAUDE.md)
  • Review Biome configuration (biome.json)
  • Analyze removed ESLint configurations
  • Check package.json changes and dependency updates
  • Review formatting changes across codebase
  • Examine new Cursor rules and documentation
  • Check pre-commit hook updates
  • Assess security and performance implications
  • Provide comprehensive feedback

Summary

This PR successfully migrates the inbox-zero codebase from ESLint to Biome, implementing the "Ultracite" configuration standard. The migration appears well-executed with comprehensive configuration and documentation.

✅ Strengths

  1. Complete Migration: Properly removes all ESLint configurations (.eslintrc.js, apps/web/.eslintrc.json, entire packages/eslint-config/ package)

  2. Comprehensive Biome Configuration: biome.json:115 extends "ultracite" with extensive rule customizations that appropriately disable overly strict rules while maintaining code quality

  3. Updated Tooling Integration:

    • Pre-commit hooks updated (.husky/pre-commit:4) to use npx ultracite format
    • VSCode settings (.vscode/settings.json:4,11,18) properly configured for Biome formatting
    • Package scripts (root package.json:11-12) include new format commands
  4. Excellent Documentation: The new .cursor/rules/ultracite.mdc provides comprehensive guidelines covering accessibility, React best practices, TypeScript conventions, and security

  5. Performance Benefits: Biome provides significantly faster linting/formatting than ESLint

⚠️ Areas for Attention

  1. Many Disabled Rules: The Biome configuration disables many recommended rules (54 total disabled rules). While this enables easier migration, consider gradually re-enabling rules that provide value:

    • correctness.noUnusedImports: "off" (biome.json:62) - unused imports should typically be cleaned up
    • correctness.noUnusedVariables: "off" (biome.json:61) - unused variables can indicate dead code
    • style.useFilenamingConvention: "off" (biome.json:12) - consistent file naming improves maintainability
  2. Linting Workflow: The turbo configuration (turbo.json:127) shows an empty lint task, but it's unclear how Biome linting is integrated into the build process

  3. Missing Error Handling: No apparent fallback if Biome formatting fails in pre-commit hooks

🔍 Security & Performance Analysis

Security: ✅ Clean migration with no security concerns

  • Biome is a well-maintained tool by the Babel team
  • Configuration doesn't expose sensitive data
  • No suspicious dependencies added

Performance: ✅ Significant improvements expected

  • Biome is ~100x faster than ESLint for similar operations
  • Reduced dependency tree (removed entire ESLint ecosystem)
  • Bundle size reduction from fewer dev dependencies

📝 Minor Suggestions

  1. Consider Re-enabling Select Rules:

    "correctness": {
      "noUnusedImports": "warn", // Instead of "off"
      "noUnusedVariables": "warn", // Instead of "off"
    }
  2. Add Biome to Turbo Pipeline: Update turbo.json to include Biome linting:

    "lint": {
      "dependsOn": ["^lint"],
      "outputs": []
    }
  3. Document Migration: Consider adding a brief migration note to explain the switch from ESLint to Biome for team members

🎯 Overall Assessment

Excellent migration that modernizes the tooling stack with significant performance benefits. The Ultracite configuration provides comprehensive code quality standards while remaining practical for a large codebase. The extensive documentation in .cursor/rules/ultracite.mdc is particularly valuable for maintaining consistency.

Recommendation: ✅ Approve with minor suggestions

The migration is well-executed and ready for production. The disabled rules can be addressed incrementally in future PRs as the team adapts to Biome's more opinionated defaults.


@elie222 elie222 merged commit 26c29b9 into main Jul 15, 2025
21 checks passed
@elie222 elie222 deleted the chore/ultracite branch December 18, 2025 23:00
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