DEV Community

Cover image for Getting Started with eslint-plugin-express-security
Ofri Peretz
Ofri Peretz

Posted on

Getting Started with eslint-plugin-express-security

9 Express security rules. CORS, cookies, rate limiting, Helmet.

This plugin is for Node.js teams building web applications with Express.js.

Quick Install

npm install --save-dev eslint-plugin-express-security
Enter fullscreen mode Exit fullscreen mode

Flat Config

// eslint.config.js
import expressSecurity from 'eslint-plugin-express-security';

export default [expressSecurity.configs.recommended];
Enter fullscreen mode Exit fullscreen mode

Rule Overview

Rule CWE What it catches
require-helmet CWE-693 Missing security headers
no-cors-credentials-wildcard CWE-346 CORS * + credentials
no-permissive-cors CWE-942 Overly permissive CORS
no-insecure-cookie-options CWE-614 Missing cookie flags
require-csrf-protection CWE-352 No CSRF protection
require-rate-limiting CWE-307 No rate limiting
require-express-body-parser-limits CWE-400 Unlimited body size
no-express-unsafe-regex-route CWE-1333 ReDoS in routes
no-graphql-introspection-production CWE-200 Schema exposed

Run ESLint

npx eslint .
Enter fullscreen mode Exit fullscreen mode

You'll see output like:

src/app.ts
  15:1  error  πŸ”’ CWE-693 | Missing Helmet middleware
               Fix: Add app.use(helmet()) before routes

src/routes/api.ts
  8:1   error  πŸ”’ CWE-346 | CORS with credentials and wildcard origin
               Fix: Specify explicit origin when using credentials

src/middleware/auth.ts
  22:3  error  πŸ”’ CWE-614 | Cookie missing secure/httpOnly flags
               Fix: Add { secure: true, httpOnly: true, sameSite: 'strict' }
Enter fullscreen mode Exit fullscreen mode

Quick Wins

Security Headers

// ❌ Missing security headers
const app = express();
app.use(cors());

// βœ… Safe: Helmet adds security headers
import helmet from 'helmet';
const app = express();
app.use(helmet());
app.use(cors({ origin: 'https://app.example.com' }));
Enter fullscreen mode Exit fullscreen mode

Cookie Security

// ❌ Insecure cookie
res.cookie('session', token);

// βœ… Safe: All security flags
res.cookie('session', token, {
  httpOnly: true,
  secure: true,
  sameSite: 'strict',
  maxAge: 3600000,
});
Enter fullscreen mode Exit fullscreen mode

Custom Configuration

// eslint.config.js
import expressSecurity from 'eslint-plugin-express-security';

export default [
  expressSecurity.configs.recommended,
  {
    rules: {
      // Override severity
      'express-security/require-rate-limiting': 'warn',

      // Configure with options
      'express-security/require-express-body-parser-limits': [
        'error',
        {
          maxBodySize: '1mb',
        },
      ],
    },
  },
];
Enter fullscreen mode Exit fullscreen mode

Strongly-Typed Options (TypeScript)

// eslint.config.ts
import expressSecurity, {
  type RuleOptions,
} from 'eslint-plugin-express-security';

const corsOptions: RuleOptions['no-permissive-cors'] = {
  allowedOrigins: ['https://app.example.com'],
};

export default [
  expressSecurity.configs.recommended,
  {
    rules: {
      'express-security/no-permissive-cors': ['error', corsOptions],
    },
  },
];
Enter fullscreen mode Exit fullscreen mode

Quick Reference

# Install
npm install --save-dev eslint-plugin-express-security

# Config (eslint.config.js)
import expressSecurity from 'eslint-plugin-express-security';
export default [expressSecurity.configs.recommended];

# Run
npx eslint .
Enter fullscreen mode Exit fullscreen mode

πŸ“¦ npm: eslint-plugin-express-security
πŸ“– Full Rule List

⭐ Star on GitHub


πŸš€ Running Express? Try the linter!

GitHub | LinkedIn | Dev.to

Top comments (0)