# What changed in express

> 17 changes in express 4 to 5 from its official release notes, upgrade guides and advisories: 3 breaking, 1 deprecations, 4 security. Each one cited. Sources checked 2026-10-18. HTML: https://unstale.sh/npm/express/

To see which of these apply to a repository, run `npx @unstale/cli init` in it.

## express 5

### Breaking changes

- Invalid limit values now throw during parser initialization instead of being ignored, preventing request body size enforcement from being silently disabled. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- Valid HTTP-token file names are no longer quoted in the Content-Disposition header; applications asserting exact header bytes may need to update expectations. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)

### Security

- Upgraded to fix CVE-2026-90711. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- Upgraded to fix arrayLimit bypasses in comma parsing and a denial of service via an attacker-controlled isBuffer. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- body-parser was upgraded to 2.2.1 to address CVE-2025-13466. (5.2.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.2.0)
- A security fix addresses CVE-2024-51999. (4.22.0, 5.2.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.2.0), [release notes](https://github.com/expressjs/express/releases/tag/4.22.0)

### Deprecations

- Deprecation warnings are now emitted for redirect arguments that are undefined. (5.2.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.2.0)

### Behavior and default changes

- Now logs the full error object instead of only its stack trace, retaining nested details such as Error.cause and library-specific properties. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- Freshness validation now includes QUERY requests, allowing matching conditional validators to produce 304 responses. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- HTML-format redirect responses now include a doctype, title, and body for better browser compatibility. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)

### Fixes and other changes

- Passing null as options now handles the locals object correctly and behaves like omitting options or passing an empty object. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- Only adds Content-Length when Transfer-Encoding is absent, preventing conflicting response headers; ETag generation is unaffected by Transfer-Encoding. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- When adding a charset, existing Content-Type parameters are preserved, and a Content-Type that fails to parse no longer throws. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- Avoids duplicate Content-Type header processing when sending string responses without an explicit Content-Type header. (5.3.0) — [release notes](https://github.com/expressjs/express/releases/tag/v5.3.0)
- The breaking change to the extended query parser introduced in 5.2.0 was fully reverted. (4.22.1, 5.2.1) — [release notes](https://github.com/expressjs/express/releases/tag/v5.2.1), [release notes](https://github.com/expressjs/express/releases/tag/v4.22.1)

## express 4

### Breaking changes

- Method functions called without a path now error. (4.22.0) — [release notes](https://github.com/expressjs/express/releases/tag/4.22.0)

### Behavior and default changes

- Repeated-key arrays can contain more than 20 items, and indexed notation now allows up to 1000 items, unifying array-cap behavior across notations. (4.22.2) — [release notes](https://github.com/expressjs/express/releases/tag/v4.22.2)
