package.json 逐字段读一遍package.json, field by field
拿两个真实 assessment 的 package.json,一个字段一个字段地读懂。Take the package.json of both real exam projects and read them one field at a time.
这一页有什么On this page6
- 认得 name / version / private / type / main / scripts 各是干什么的Recognise what name, version, private, type, main and scripts each control
- 知道 "type": "module" 会怎样改变 import 的写法Know how "type": "module" changes the way you write import
- 能从一个陌生的 package.json 判断出这个项目怎么跑、用什么测试Work out from an unfamiliar package.json how the project runs and which test tool it uses
- 知道配置也可以内嵌在 package.json 里(subgraph 的 jest 配置就是)Know that configuration can also sit inside package.json, as the jest config of the subgraph does
考场上没人会告诉你「这个项目怎么跑」。package.json 就是答案本身。看懂它,等于拿到了考场地图。In an exam nobody tells you how to run the project. package.json is the answer itself. Read it and you have the map of the exam.
react-notes-app/package.jsonReact 考试The React exam
react-notes-app/package.jsongraphql-federation-practice/node-subgraph/package.jsonFederation 考试的 Node 部分The Node half of the Federation exam
graphql-federation-practice/node-subgraph/package.json先读 React 考试的这一份Start with the one from the React exam
整个文件只有 7 个顶层字段。逐个看。The whole file has only 7 top-level fields. Go through them one by one.
下面这份是原样从项目里拿出来的,一个字都没改:
The file below was copied verbatim out of the project. Not one character changed:
react-notes-app/package.json字段逐条解释Every field, one by one
| 字段 | 这份文件里的值 | 它在管什么 |
|---|---|---|
name | "react-notes-app" | 包名。发布到 npm 时是唯一标识;不发布的话只是个名字。 |
private | true | 「这个包不许被发布到 npm」。手滑跑了 npm publish 会被拦下来。练习/考试项目基本都会写它。 |
version | "1.0.0" | 本项目自己的版本号。不发布的话没什么实际作用,但字段得在。 |
type | "module" | 关键字段。告诉 Node「本项目的 .js 文件按 ES Module 解析」,于是能用 import / export,不能用 require。 |
scripts | dev / build / q2 | 可以用 npm run <名字> 跑的快捷命令。下一节专门讲。 |
dependencies | react、react-dom | 产品运行时需要的包。 |
devDependencies | 11 个 | 开发、构建、测试用的包。 |
只看这 7 个字段,你已经能推出一堆事实:这是个用 Vite 打包的React 18 + TypeScript 项目,测试用Vitest + Testing Library,DOM 环境靠jsdom 模拟,另外还有一个用 tsx 直接跑 TypeScript 的独立小题(q2)。
| Field | Value in this file | What it controls |
|---|---|---|
name | "react-notes-app" | The package name. A unique identity if you publish to npm; just a name if you do not. |
private | true | “This package must not be published to npm.” A slip of the finger running npm publish gets blocked. Practice and exam projects almost always set it. |
version | "1.0.0" | This project’s own version number. It does nothing much if you never publish, but the field has to be there. |
type | "module" | The field that matters. It tells Node “parse this project’s .js files as ES Modules”, so import / export work and require does not. |
scripts | dev / build / q2 | Shortcut commands you can run with npm run <name>. The next lesson is all about these. |
dependencies | react, react-dom | Packages the product needs at runtime. |
devDependencies | 11 of them | Packages for developing, building and testing. |
From those 6 fields alone you can already work out a pile of facts: this is a React 18 + TypeScript project bundled by Vite, tested with Vitest + Testing Library, with the DOM faked by jsdom, plus one standalone side question (q2) that runs TypeScript directly through tsx.
再读 Federation 考试那一份Now the one from the Federation exam
同样的读法,但多了两个新东西:main 和内嵌配置。Read it the same way. Two things are new here: main, and configuration kept inside the file.
这一份多出 main(包的入口文件)、description, 以及最要紧的一处:jest 的配置直接内嵌在 package.json 里, 没有单独的 jest.config.js。
这一点很容易踩坑 —— 你在项目里翻半天找不到测试配置文件, 以为项目没配好,其实它就在 package.json 的最后几行。 很多工具(jest、eslint、prettier、babel)都支持这种内嵌写法。
This one adds main (the package entry file) and description, plus the part most worth staring at: the jest config is embedded straight into package.json. There is no separate jest.config.js.
That trips people up — you dig through the project for a test config file, find nothing, decide the project was never set up properly, and it was sitting in the last few lines of package.json the whole time. Plenty of tools (jest, eslint, prettier, babel) accept this embedded form.
graphql-federation-practice/node-subgraph/package.json拿到陌生 package.json 的三步读法Three steps for reading a package.json you have never seen
- 先看 scripts。这决定了你能跑什么命令。 有
dev就说明能起开发服务器,有test就说明能跑测试,没有test就得自己想办法(下一节讲)。 - 再看 dependencies。看见
react就知道是前端; 看见@apollo/server+@apollo/subgraph就知道是 GraphQL 联邦的一个 subgraph;看见dataloader就知道这题大概会考批量加载。 - 最后看 type 和内嵌配置。
"type": "module"决定 import 的写法, 内嵌的 jest/eslint 配置决定测试怎么被发现。
第 2 步尤其重要:依赖清单本身就在泄题。subgraph 的 dependencies 里明摆着一个 dataloader, 而 starter 代码里正好有个 TODO 写着「用 DataLoader 防 N+1」—— 这不是巧合。
- Read scripts first. It decides which commands you can run. A
deventry means there is a dev server; atestentry means you can run tests; notestentry means you have to work something out yourself (next lesson). - Then read dependencies. Spot
reactand you know it is frontend; spot@apollo/server+@apollo/subgraphand you know it is one subgraph of a GraphQL federation; spotdataloaderand you can bet batch loading is on the test. - Read type and the embedded config last.
"type": "module"decides how imports get written, and an embedded jest/eslint config decides how tests get found.
Step 2 matters most: the dependency list leaks the questions. The subgraph has dataloader sitting right there in dependencies, and the starter code happens to carry a TODO saying “use DataLoader to avoid N+1” — that is no coincidence.
动手做Get your hands on it
填空只是过渡。真正掌握的标准,是在没有答案的时候从头写出来 —— 所以做完 L2 之后一定要往 L3、L4 走。Filling blanks is a stepping stone. The real bar is writing it from nothing, so once L2 is comfortable, push on to L3 and L4.
下面是 node-subgraph/package.json 的骨架,挖掉了三个决定项目行为的值。 照真实文件补回来。
Below is the skeleton of node-subgraph/package.json with three values removed. Each one decides how the project behaves. Put them back the way the real file has them.
换一道题也能用Works on other problems too
考试不会原题重考。真正能带走的是「看到这种信号 → 伸手去拿这个解法」。The exam will not reuse the same question. What you take away is the reflex: see this signal, reach for that solution.
- package.json 的 scripts 决定你能跑什么命令,是拿到项目第一个要读的字段。The scripts in package.json decide which commands you can run. It is the first field to read.
- "type": "module" 决定源码用 ESM 还是 CommonJS,直接影响 import 能不能写。"type": "module" decides whether the source uses ESM or CommonJS, so it decides whether you can write import.
- private: true 只是防止误发布,与能不能跑无关。private: true only stops the package from being published by mistake. It has nothing to do with running it.
- 配置可以内嵌:subgraph 的 jest 配置就在 package.json 里,不在单独文件。Configuration can live inside package.json. The jest config of the subgraph is there, not in a separate file.
- dependencies 里出现 dataloader 这种特征包,基本等于告诉你考点在哪。A telling package such as dataloader in dependencies almost always shows you what the exam will test.