根本原因是typescript语言服务未接管文件:右下角显示javascript react、缺tsconfig.json、jsx文件后缀为.js、include未覆盖源码目录或jsx配置缺失,导致ts无法解析jsx及推导props类型。

VSCode 不补全 React 属性,根本原因不是插件没装,而是 TypeScript 类型服务没真正接管当前文件。 即使你写了 useState、useEffect,只要 TS 语言服务没激活,onClick、className、组件 props 等属性名就不会出现在补全列表里——它连“这是个 JSX 元素”都不知道。
为什么 div 能补全但 onClick 不行?
这是两种不同机制:div 补全是 Emmet 或原生 HTML 模式触发的,而 onClick 这类属性依赖 TypeScript 的类型定义推导。JSX 标签本身被识别为 JSX.IntrinsicElements,它的属性列表来自 react 包里的 index.d.ts;组件 props 则来自你写的 interface Props 或函数签名。没有 TS 服务,这些定义就等于不存在。
- 右下角状态栏显示的是
JavaScript React(不是TypeScript React)→ 文件被当 JS 处理,无类型信息 - 项目根目录缺失
tsconfig.json(哪怕空文件也没写)→ VS Code 启动的是“无类型 JS 语言服务” - 文件是
.js后缀但写了 JSX → 编辑器无法安全推导类型,自动降级为纯 JS 模式 -
tsconfig.json中"include"没覆盖组件目录(如"src/**/*"),TS Server 根本不扫描你的文件
tsconfig.json 必须存在的最小配置
哪怕你用的是纯 JavaScript 项目,也得有 tsconfig.json 来启用类型检查。否则 React.FC、JSX.IntrinsicElements 这些关键定义不会加载。
{
"compilerOptions": {
"allowJs": true,
"checkJs": true,
"jsx": "react-jsx",
"moduleResolution": "node",
"skipLibCheck": true,
"strict": false
},
"include": ["src/**/*"]
}
-
"jsx": "react-jsx"是必须项,否则 TS 不会解析 JSX 语法并注入类型 -
"checkJs": true让 JS 文件也走类型检查流程(配合// @ts-check注释) - 删掉
"noEmit": true或其他阻断类型服务启动的选项,它们会让 TS Server 直接退出
自定义组件 props 不补全?检查导出和导入路径
你写了 export interface ButtonProps { size?: 'sm' | 'lg' },但 <button size=" 按 Ctrl+Space 没反应——问题大概率出在“导出未被 TS Server 看见”。
- 组件文件后缀不是
.tsx(比如用了.js)→ TS 不读取该文件中的类型声明 - 自定义 Hook 或组件从
@/components/Button导入,但tsconfig.json里没配" paths> → 类型路径解析失败,补全和跳转都失效 <li>导出写成 <code>const Button = () => {}+export default Button,但没加类型注解 → TS 推不出props结构;应改用export const Button: React.FC<buttonprops> = () => {}</buttonprops> - 第三方库(如
@headlessui/react)没安装@types/xxx,且库自身不带.d.ts→ 补全退化为 any
容易被忽略的硬性前提
所有补全功能都建立在一个事实之上:VS Code 当前正在运行 TypeScript 语言服务,并且它已成功加载了你的项目配置和依赖类型。任何一步断开——比如 Developer: Restart Language Server 按完没反应、node_modules 里缺 react 的类型文件、或 package.json 中 "type": "module" 与旧版 TS 配置冲突——都会让属性补全彻底静默,且不报错、不提示。











