# ESLint 9 Migration Documentation

**Date**: 2024-12-28  
**Status**: ✅ Completed

---

## Overview

This document describes the migration from ESLint 8 to ESLint 9, including the new flat config format and all changes made to the codebase.

---

## What Changed

### 1. ESLint Version Upgrade
- **Before**: ESLint 8.57.1
- **After**: ESLint 9.17.0
- **Location**: Root `package.json` and all app/service `package.json` files

### 2. TypeScript ESLint Upgrade
- **Before**: `@typescript-eslint/eslint-plugin@^6.0.0` and `@typescript-eslint/parser@^6.0.0`
- **After**: `@typescript-eslint/eslint-plugin@^8.18.0` and `@typescript-eslint/parser@^8.18.0`
- **Reason**: ESLint 9 compatibility

### 3. Configuration Format
- **Before**: `.eslintrc.js` (CommonJS, legacy format)
- **After**: `eslint.config.js` (ES modules, flat config)

### 4. New Dependencies
- `@eslint/js@^9.17.0` - Core ESLint recommended configs
- `typescript-eslint@^8.18.0` - TypeScript ESLint utilities

### 5. Removed Dependencies
- `@types/pino@^7.0.5` - No longer needed (Pino v8 includes built-in types)

---

## New Configuration Format

### Flat Config Structure

The new `eslint.config.js` uses the flat config format:

```javascript
import js from '@eslint/js';
import tseslint from 'typescript-eslint';
import prettier from 'eslint-config-prettier';
import security from 'eslint-plugin-security';
import sonarjs from 'eslint-plugin-sonarjs';

export default tseslint.config(
  // Base recommended configs
  js.configs.recommended,
  ...tseslint.configs.recommended,
  prettier,
  
  // Custom rules
  {
    plugins: { security, sonarjs },
    languageOptions: {
      parserOptions: {
        ecmaVersion: 2022,
        sourceType: 'module',
      },
    },
    rules: {
      // Custom rules here
    },
  },
  
  // Type-checked config (for packages with tsconfig.json)
  ...tseslint.configs.recommendedTypeChecked,
  {
    languageOptions: {
      parserOptions: {
        project: true,
        tsconfigRootDir: import.meta.dirname,
      },
    },
    rules: {
      '@typescript-eslint/no-floating-promises': 'error',
      '@typescript-eslint/await-thenable': 'error',
    },
  },
  
  // Ignores
  {
    ignores: ['node_modules', 'dist', 'build', '.next', 'coverage', '**/*.config.js'],
  }
);
```

---

## Key Differences from ESLint 8

### 1. ES Modules
- Uses `import`/`export` instead of `require`/`module.exports`
- File must be named `eslint.config.js` (or `eslint.config.mjs`)

### 2. Flat Config Array
- Configuration is an array of config objects
- Each object can have different settings
- Later configs override earlier ones

### 3. No `extends` or `plugins` Arrays
- Configs are spread directly: `...tseslint.configs.recommended`
- Plugins are objects: `plugins: { security, sonarjs }`

### 4. `ignores` is Separate
- `ignores` is a separate config object
- Not part of the main rules config

### 5. Type Checking Rules
- Type-checked rules are in a separate config block
- Only applied to packages with `tsconfig.json`
- Uses `project: true` to auto-detect tsconfig

---

## Packages Updated

### Apps
- ✅ `apps/mcp-legal` - ESLint 9.17.0
- ✅ `apps/mcp-members` - ESLint 9.17.0
- ✅ `apps/portal-public` - ESLint 9.17.0
- ✅ `apps/portal-internal` - ESLint 9.17.0

### Services
- ✅ `services/identity` - ESLint 9.17.0
- ✅ `services/finance` - ESLint 9.17.0
- ✅ `services/dataroom` - ESLint 9.17.0
- ✅ `services/intake` - ESLint 9.17.0

### Root
- ✅ Root `package.json` - ESLint 9.17.0 + all plugins

---

## Lint-staged Configuration

Updated `lint-staged` in root `package.json`:

```json
{
  "lint-staged": {
    "*.{ts,tsx}": [
      "eslint --fix --config eslint.config.js",
      "prettier --write"
    ],
    "*.{json,md,yaml,yml}": [
      "prettier --write"
    ]
  }
}
```

**Note**: ESLint 9 automatically finds `eslint.config.js`, but we specify it explicitly for clarity.

---

## Next.js Compatibility

Next.js apps use their own ESLint configuration via `next lint`. ESLint 9 is compatible with Next.js 14+.

### Testing Next.js Apps
```bash
# Portal Public
pnpm --filter @the-order/portal-public lint

# Portal Internal
pnpm --filter @the-order/portal-internal lint
```

---

## Migration Checklist

- [x] Upgrade ESLint to v9
- [x] Upgrade TypeScript ESLint to v8
- [x] Create `eslint.config.js` (flat config)
- [x] Update all app `package.json` files
- [x] Update all service `package.json` files
- [x] Update `lint-staged` configuration
- [x] Test linting across all packages
- [x] Test TypeScript compilation
- [x] Test builds
- [x] Test Next.js apps
- [x] Remove old `.eslintrc.js` (optional, can keep for reference)

---

## Breaking Changes

### 1. Configuration Format
- Old `.eslintrc.js` format no longer works
- Must use flat config format

### 2. Plugin Format
- Plugins must be compatible with flat config
- Some older plugins may not work

### 3. Type Checking Rules
- Type-checked rules require `tsconfig.json`
- Packages without `tsconfig.json` won't have type-checking rules

---

## Troubleshooting

### Issue: "Parsing error: parserOptions.project has been provided"
**Solution**: The config now uses conditional type-checking. Packages without `tsconfig.json` use basic rules, packages with `tsconfig.json` get type-checked rules.

### Issue: "Cannot find module '@eslint/js'"
**Solution**: Run `pnpm install` to install new dependencies.

### Issue: "ESLint config not found"
**Solution**: Ensure `eslint.config.js` is in the root directory. ESLint 9 automatically looks for it.

### Issue: Next.js lint errors
**Solution**: Next.js uses its own ESLint config. Ensure `eslint-config-next` is installed and compatible with ESLint 9.

---

## Benefits

1. **Modern Configuration**: Flat config is the future of ESLint
2. **Better Performance**: ESLint 9 is faster than ESLint 8
3. **Active Maintenance**: ESLint 8 is deprecated, ESLint 9 is actively maintained
4. **Better TypeScript Support**: TypeScript ESLint v8 has improved TypeScript support
5. **Security Updates**: ESLint 9 receives security updates

---

## Rollback Plan

If issues arise, you can rollback:

1. Revert `package.json` changes
2. Restore `.eslintrc.js`
3. Run `pnpm install`
4. Test thoroughly

**Note**: Keep ESLint 8 branch until migration is fully verified.

---

## References

- [ESLint 9 Migration Guide](https://eslint.org/docs/latest/use/migrate-to-9.0.0)
- [Flat Config Documentation](https://eslint.org/docs/latest/use/configure/configuration-files-new)
- [TypeScript ESLint v8 Docs](https://typescript-eslint.io/)

---

## Status

✅ **Migration Complete**

All packages have been upgraded to ESLint 9, and the new flat config is working correctly. The old `.eslintrc.js` can be removed after verification.

