Skip to content

[BUG] @types/react is not declared as a peer dependency, breaking types under strict linkers #3801

Description

@tifandotme

2. Describe the bug

motion and framer-motion declare react and react-dom as optional peer dependencies, but not @types/react. Their type files import React:

import * as React from "react"

Under a strict, non-hoisted node_modules, those type files cannot resolve React's types. Every motion component's props degrade and TypeScript reports:

error TS2607: JSX element class does not support attributes because it does not have a 'props' property

3. IMPORTANT: Provide a CodeSandbox reproduction of the bug

Not possible here, and I want to be upfront about that rather than link something that does not show the problem. CodeSandbox installs with a hoisted node_modules, which is exactly the layout that hides this bug. It only appears under a strict linker: Bun isolated, pnpm, or Yarn PnP.

The local reproduction is four files:

// package.json
{
  "devDependencies": {
    "motion": "13.1.1",
    "react": "^19",
    "react-dom": "^19",
    "@types/react": "^19",
    "typescript": "^5"
  }
}
# bunfig.toml
[install]
linker = "isolated"
// tsconfig.json
{ "compilerOptions": { "jsx": "react-jsx", "strict": true, "noEmit": true, "moduleResolution": "bundler", "module": "esnext" } }
// a.tsx
import { motion } from "motion/react"
export const A = () => <motion.div className="x" />

4. Steps to reproduce

  1. bun install
  2. npx tsc -p .

5. Expected behavior

Types resolve and the file compiles.

7. Environment details

macOS 26.5, Bun 1.4.0, React 19.2, TypeScript 5.9. Also reproduces with pnpm.


Why it happens

A strict linker symlinks each package into a store. Node and TypeScript resolve a symlink to its real path before walking parent directories, so a package sees only what it declares. react is declared and resolves; @types/react is not, so it does not.

skipLibCheck suppresses the errors inside motion's own .d.ts files, but not the broken types they hand to consumers.

Suggested fix

Add @types/react alongside the existing optional peers in packages/motion and packages/framer-motion:

"peerDependencies": {
  "@types/react": "*"
},
"peerDependenciesMeta": {
  "@types/react": { "optional": true }
}

Same pattern @radix-ui/* and posthog-js@1.422.5 already ship. Happy to open the PR.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions