ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Claude Code配置三剑客:settings.json、CLAUDE.md与memory职责边界与实战

Claude Code配置三剑客:settings.json、CLAUDE.md与memory职责边界与实战 1. 三个配置文件到底谁管什么先把职责边界划清楚很多人第一次接触 Claude Code 的配置体系时最容易犯的错就是把settings.json、CLAUDE.md和 memory 当成三个差不多的东西随便往哪个里面塞内容。结果就是明明写了规则Claude 就是不遵守明明配了权限命令还是被拦明明记了偏好下次对话又忘了。问题的根源不在于配置写错了而在于放错了地方。我先把这三者的本质区别用一句话讲透settings.json管的是工具和环境——它决定 Claude Code 这个程序本身怎么运行能碰哪些文件、能跑哪些命令、用哪个模型、走哪个 API 端点。它是给程序看的。CLAUDE.md管的是项目规矩——它告诉 Claude 在这个代码库里应该怎么写代码、遵循什么风格、避开哪些坑。它是给当前项目上下文看的。memory 管的是跨会话记忆——它记录你个人的偏好、习惯、长期有效的事实让 Claude 在不同会话、不同项目之间都能记得你。它是给你这个人看的。这三者的作用域是层层放大的settings.json是机器级/项目级CLAUDE.md是项目级memory 是用户级。理解了这个层级关系后面所有的配置决策都会变得顺理成章。1.1 为什么不能混着放一个真实的翻车案例我见过一个很典型的场景。有位朋友想让 Claude 在每次生成代码时都用 2 空格缩进他把这条规则写进了settings.json的某个自定义字段里然后发现完全不起作用。原因很简单——settings.json的 schema 是固定的你塞进去的未知字段会被直接忽略Claude 根本读不到。正确的做法是缩进风格属于项目代码规范应该写进CLAUDE.md。而如果你希望所有项目都用 2 空格缩进那应该写进 memory因为它是你的个人偏好跨项目生效。再举一个例子。有人想限制 Claude 不能执行rm -rf这类危险命令他写进了CLAUDE.md说请不要执行删除命令。这其实是个软约束——Claude 大部分时候会遵守但它本质上只是上下文里的一句话不是硬性拦截。真正要硬性拦截得在settings.json的permissions里配置deny规则。这就是软规矩和硬权限的区别。记住一个判断口诀能拦住程序的写 settings.json能指导写代码的写 CLAUDE.md能跨项目记住你的写 memory。1.2 三者的加载顺序与优先级Claude Code 启动时的加载逻辑大致是这样的先读用户级的settings.json通常在~/.claude/settings.json再读项目级的settings.json项目根目录下的.claude/settings.json项目级会覆盖用户级的同名配置。然后加载 memory 文件最后把当前项目的CLAUDE.md注入到系统提示里。这个顺序很重要因为它决定了冲突时谁说了算。比如你在用户级 settings 里设了默认模型是 A项目级设了模型是 B那在这个项目里就用 B。而CLAUDE.md和 memory 之间不存在覆盖关系它们是叠加注入的内容都会出现在上下文里。如果两者有矛盾Claude 通常会倾向于更具体、更靠近当前任务的那一条但这个行为并不绝对可靠所以尽量不要让 memory 和 CLAUDE.md 出现直接冲突。配置类型典型路径作用域生效方式适合放什么settings.json用户级~/.claude/settings.json所有项目程序读取硬性生效默认模型、API 端点、全局权限settings.json项目级项目/.claude/settings.json当前项目覆盖用户级项目专属权限、环境变量CLAUDE.md项目/CLAUDE.md当前项目注入上下文代码规范、架构说明、禁忌事项memory~/.claude/下的记忆文件所有项目注入上下文个人偏好、沟通习惯、长期事实这张表建议你直接截图存下来配置的时候对着看能省掉大量试错时间。2. settings.json 的字段拆解哪些能改哪些改了会出事settings.json是三者里最硬的一个因为它直接控制程序行为。但也正因为如此它的 schema 最严格写错字段名或者写错类型轻则被忽略重则导致 Claude Code 启动异常。我下面按功能模块拆开讲每个字段都说明它解决什么问题、怎么配、有什么坑。2.1 模型与端点配置本地模型接入的关键最常被改的就是模型相关配置。默认情况下 Claude Code 走官方端点但很多人希望接入本地模型或者其他兼容端点这时候就要动env字段。典型写法是这样{ env: { ANTHROPIC_BASE_URL: http://localhost:1234, ANTHROPIC_API_KEY: your-key-here, ANTHROPIC_MODEL: your-model-name } }这里有几个实操细节值得说。第一ANTHROPIC_BASE_URL指向的端点必须兼容 Anthropic 的消息格式不是随便一个 OpenAI 兼容端点就能直接用很多本地推理框架需要额外的适配层。第二ANTHROPIC_API_KEY如果本地服务不校验随便填一个非空字符串即可但不能留空否则客户端可能直接报错。第三模型名称要和你本地实际加载的模型标识完全一致大小写都别错。提示改完env之后一定要重启 Claude Code环境变量是在进程启动时读取的热改不生效。我踩过的一个坑是把ANTHROPIC_BASE_URL写成了带路径的形式比如http://localhost:1234/v1结果请求全部 404。后来才发现客户端会自己在后面拼/v1/messages所以 base url 只需要写到域名和端口就够了。这个细节官方文档里没明说但实测就是这样。2.2 权限系统allow / deny / ask 三档怎么用权限配置是settings.json里最有价值的部分也是最能体现硬约束的地方。它分三档allow白名单列出的操作直接放行不再询问。deny黑名单列出的操作直接拒绝Claude 连尝试的机会都没有。ask灰名单列出的操作每次都要你手动确认。配置格式大致如下{ permissions: { allow: [ Bash(npm run test:*), Bash(git status), Read(//src/**) ], deny: [ Bash(rm -rf:*), Bash(curl:*), Read(./.env) ], ask: [ Bash(git push:*) ] } }这里的匹配语法是工具名(参数模式)支持通配符。几个经验点第一deny的优先级最高一个操作只要命中 deny无论 allow 里怎么写都会被拒。所以别把同一个模式同时写进 allow 和 deny那样只会以 deny 为准。第二Read(./.env)这类敏感文件一定要放进 deny防止 Claude 在探索代码库时不小心把你的密钥读进上下文。这是安全底线。第三Bash(git push:*)放 ask 是个好习惯。push 是少数几个一旦执行就难以撤销的操作让它每次确认一下能避免很多手滑。第四通配符:*表示这个命令后面跟任意参数。如果你只写Bash(git)那只有裸的git命令会匹配git status不会命中。这个细节很多人搞错。2.3 环境变量与工具开关除了模型和权限settings.json还能控制一些行为开关。比如是否启用自动更新、是否收集遥测、默认的编辑器行为等。这些字段相对冷门但有几个值得关注和终端执行相关的开关决定 Claude 能否直接跑命令还是必须先征求同意。和文件监听相关的配置影响它感知项目变化的速度。和输出格式相关的设置影响日志详细程度排查问题时很有用。我的建议是不要一次性把所有字段都配上。先跑起来遇到具体需求再针对性添加。配置越多出问题的面越大而且很多字段的默认值其实已经调得不错了。2.4 项目级 settings 的覆盖陷阱项目级.claude/settings.json会覆盖用户级但覆盖是按字段而不是按整个文件。也就是说如果项目级只写了permissions那用户级的env依然生效。这个机制很合理但有个坑数组类型的字段比如allow列表通常是整体替换而不是合并。你在用户级 allow 里放了一堆常用命令项目级又写了一个 allow结果用户级那些全没了。解决办法是要么在项目级把需要的都写全要么干脆把通用规则都放用户级项目级只写项目特有的。我个人的习惯是用户级放通用白名单项目级只放 deny 和项目专属的 allow这样冲突最少。3. CLAUDE.md 的写法让 Claude 真正读懂你的项目如果说settings.json是给程序看的说明书那CLAUDE.md就是给 Claude 看的项目入职手册。它的质量直接决定了 Claude 在你项目里的表现——写得好的CLAUDE.md能让 Claude 像一个熟悉项目的老员工写得差的就只是个会写代码的陌生人。3.1 该写什么从项目地图到行为准则CLAUDE.md的内容可以分成几个层次我按重要性排序第一层是项目地图。用几句话讲清楚这个项目是干什么的、目录结构怎么组织、核心模块在哪。这能帮 Claude 快速定位代码而不是盲目地全库搜索。比如## 项目结构 - src/api/ 所有 HTTP 接口使用 Fastify 框架 - src/core/ 业务逻辑不依赖任何框架 - src/db/ 数据库访问层使用 Prisma - tests/ 测试文件与 src 目录结构镜像对应第二层是技术栈和约定。用了什么语言、什么框架、什么版本、什么包管理器。这些信息能避免 Claude 给出过时的写法。比如你用的是 React 18 的函数组件就明确写出来别让它给你生成 class 组件。第三层是行为准则。这是最有价值的部分包括代码风格缩进、命名、注释语言、提交规范、测试要求、禁止事项。比如所有新功能必须带单元测试不要修改generated/目录下的文件提交信息用中文。第四层是常见任务的执行方式。比如跑测试用npm test构建用npm run build本地启动用npm run dev。把这些命令写清楚Claude 就不会瞎猜。3.2 不该写什么三个常见的过度配置很多人写CLAUDE.md容易走两个极端要么太简略要么太啰嗦。我重点说说太啰嗦的三种典型第一种是把整个 README 复制过来。README 是给人看的里面有大量安装步骤、背景介绍、贡献指南这些对 Claude 写代码没帮助反而占用宝贵的上下文窗口。CLAUDE.md应该只保留和写代码直接相关的信息。第二种是把详细的 API 文档贴进去。接口文档动辄几千行全塞进去会让上下文爆炸。正确做法是告诉 Claude接口定义在docs/api.md需要时去读而不是把内容直接内联。第三种是写一堆正确的废话。比如请写出高质量的代码注意代码可读性遵循最佳实践。这些话没有任何可操作性Claude 看了等于没看。要写就写具体的比如函数不超过 50 行避免嵌套超过 3 层所有异步操作必须处理错误。一个判断标准如果一条规则你自己都没法判断有没有被遵守那它就不该写进 CLAUDE.md。3.3 分层组织用标题和列表提升可读性CLAUDE.md是 Markdown 文件善用标题层级能让 Claude 更容易抓重点。我的建议是控制在两级标题以内每个标题下用列表而不是长段落。原因很简单列表的每一条都是独立的指令Claude 解析起来更清晰长段落里的信息容易被淹没。一个实用的结构模板是这样的# 项目说明 一段话讲清楚项目是什么 # 技术栈 - 语言TypeScript 5.x - 框架Next.js 14App Router - 样式Tailwind CSS - 测试Vitest # 目录约定 - app/ 路由和页面 - components/ 可复用组件 - lib/ 工具函数 # 编码规范 - 使用函数组件和 Hooks不用 class - 组件文件名用 PascalCase - 工具函数用 camelCase - 所有导出必须有 JSDoc 注释 # 常用命令 - 开发npm run dev - 测试npm test - 构建npm run build # 禁止事项 - 不要修改 app/generated/ 下的文件 - 不要引入新的依赖除非明确要求 - 不要提交 .env 文件这个模板大概 40 行覆盖了核心信息又不至于臃肿。你可以根据项目复杂度增减但尽量控制在 100 行以内超过这个量级就要考虑拆分或者精简了。3.4 让 CLAUDE.md 真正生效的三个技巧写完CLAUDE.md不代表就完事了还得确保它被正确加载和遵守。三个实操技巧技巧一放在项目根目录。Claude Code 默认会从当前工作目录向上查找CLAUDE.md放在根目录最稳妥。如果你在子目录里工作它也能找到上层的但根目录是约定俗成的位置。技巧二用祈使句而不是陈述句。使用 2 空格缩进比本项目使用 2 空格缩进更有效因为前者是明确的指令。技巧三定期回顾和更新。项目在演进CLAUDE.md也要跟着改。我一般每个迭代结束会花五分钟扫一遍把过时的规则删掉把新踩的坑补进去。这个习惯能让CLAUDE.md一直保持活的状态。4. memory 机制跨会话记住你的个人偏好memory 是三者里最容易被忽视、但长期收益最高的一个。settings.json和CLAUDE.md都是项目绑定的换个项目就失效而 memory 是跟着你这个人走的无论你在哪个项目、哪个会话它都能让 Claude 记得你的习惯。4.1 memory 和 CLAUDE.md 的本质区别很多人会问既然CLAUDE.md也能写偏好为什么还要 memory关键在于作用域和持久性。CLAUDE.md是项目文件会跟着代码库走。如果你把个人偏好写进去同事拉下代码也会看到这显然不合适。而且换个项目这些偏好就没了。memory 是存在你本地的用户级配置不进入代码库跨项目生效。它适合放那些只关于你、和具体项目无关的信息。比如你习惯用中文交流希望 Claude 也用中文回复你喜欢简洁的回答不要长篇大论的解释你偏好函数式编程风格你常用的技术栈和版本你希望 Claude 在改动代码前先说明计划这些内容放进 memory一次配置处处生效。4.2 什么内容值得进 memory三个筛选标准memory 不是越多越好塞太多会让每次对话的上下文都变重而且过时的记忆反而会误导 Claude。我用三个标准来筛选标准一长期有效。这条信息半年后还成立吗如果只是当前项目的临时需求那不该进 memory。比如这个月我在学 Rust就不适合但我主要用 TypeScript 和 Python就适合。标准二跨项目通用。这条信息在换项目后还有意义吗如果只在特定项目成立那应该写进CLAUDE.md。比如我们团队用 GitLab是跨项目的这个项目用 Jest是项目级的。标准三可操作。这条信息能指导 Claude 的具体行为吗我喜欢优雅的代码太虚函数优先于类才具体。按这三个标准筛下来真正该进 memory 的内容其实不多通常十几条就够了。少而精比多而杂有效得多。4.3 memory 的更新与维护别让它变成垃圾场memory 最大的风险是只增不减。用久了之后里面堆满了各种过时的偏好Claude 每次都要读一遍既浪费上下文又可能产生冲突。我的维护习惯是每月清理一次。翻一遍所有记忆条目问自己这条现在还成立吗。不成立的直接删模糊的改具体。冲突及时合并。如果发现两条记忆互相矛盾比如一条说用分号另一条说不用分号立刻合并成一条明确的规则。重要信息前置。memory 的读取也是有顺序的越靠前的内容越容易被重视。把最核心的偏好放在最前面。一个实用技巧给每条 memory 加一个添加日期的备注。这样清理的时候一眼就能看出哪些是陈年老账哪些是最近才加的。4.4 memory 与 CLAUDE.md 的协同分工而非重复理想状态下memory 和CLAUDE.md应该是互补的而不是重复的。我的分工原则是memory 放我是谁我的技术背景、沟通偏好、通用工作习惯。CLAUDE.md 放这个项目是什么项目结构、技术栈、编码规范、禁忌事项。举个例子。假设你是个偏好函数式编程、喜欢简洁回复的开发者同时在一个用 React 的项目里工作。那么memory 里写偏好函数式风格避免可变状态回复简洁不需要过多解释。CLAUDE.md里写本项目用 React 18 TypeScript组件用函数式写法状态管理用 Zustand。这样 Claude 在任何项目里都知道你的个人风格进入这个项目后又知道具体的技术约束。两者叠加效果最好。如果发现某条规则在两个地方都写了那说明它可能放错了位置。要么它是个人偏好该只在 memory要么它是项目规范该只在CLAUDE.md。重复不会加强效果只会增加维护成本。5. 三套配置的联动实战从零搭一个顺手的开发环境讲了这么多理论最后用一个完整的场景把三者串起来。假设你要在一个新的 TypeScript 项目里配置 Claude Code让它既安全又高效还符合你的个人习惯。5.1 第一步先配 settings.json 打好安全底座先创建用户级的~/.claude/settings.json把通用的安全规则和偏好设好{ permissions: { deny: [ Read(./.env), Read(./.env.*), Read(./secrets/**), Bash(rm -rf:*), Bash(curl:*), Bash(wget:*) ], ask: [ Bash(git push:*), Bash(git reset --hard:*) ], allow: [ Bash(git status), Bash(git diff:*), Bash(git log:*), Bash(npm run test:*), Bash(npm run lint:*) ] } }这一层的核心目的是兜底。敏感文件读不了危险命令跑不了常用只读命令免确认。配完之后无论你在哪个项目基本的安全边界都有了。然后在项目里创建.claude/settings.json只加项目特有的{ permissions: { allow: [ Bash(npm run dev), Bash(npm run build), Bash(npx prisma:*) ] } }注意这里没有再写 deny因为用户级的 deny 已经生效了项目级不需要重复。5.2 第二步写 CLAUDE.md 给项目建立上下文在项目根目录创建CLAUDE.md按前面讲的四层结构来写。重点是把项目特有的信息写清楚通用的个人偏好留给 memory。# 项目说明 一个基于 Next.js 14 的内容管理后台支持多租户。 # 技术栈 - TypeScript 5.3严格模式 - Next.js 14 App Router - Prisma PostgreSQL - Tailwind CSS shadcn/ui - Vitest 做单元测试 # 目录约定 - app/ 路由和页面组件 - components/ui/ 基础 UI 组件来自 shadcn - components/features/ 业务组件 - lib/ 工具函数和配置 - prisma/ 数据库 schema 和迁移 # 编码规范 - 组件用函数式不用 class - 服务端组件优先需要交互才加 use client - 所有数据库操作走 Prisma不写原生 SQL - 错误处理用 Result 类型不抛异常 - 提交信息用中文格式类型(范围): 描述 # 常用命令 - 开发npm run dev - 测试npm test - 迁移npx prisma migrate dev - 生成客户端npx prisma generate # 禁止事项 - 不要修改 components/ui/ 下的文件那是 shadcn 生成的 - 不要直接操作数据库一律通过 Prisma - 不要在客户端组件里引入服务端代码这份CLAUDE.md大概 35 行信息密度很高Claude 读完就能对项目有清晰认知。5.3 第三步用 memory 固化个人习惯最后在 memory 里加上你的个人偏好。这些内容不进入代码库只影响你自己的使用体验用中文回复技术术语保留英文回答简洁先给结论再给理由改动代码前先说明计划等我确认偏好函数式风格避免可变状态和副作用代码注释用中文变量名用英文遇到不确定的地方主动提问不要瞎猜这几条配好之后你在任何项目里用 Claude Code它都会按这个风格和你协作。不用每次重新交代省心很多。5.4 联动效果与常见冲突排查三套配置都到位后一个典型的交互流程是这样的Claude 启动时读取用户级 settings 建立安全边界读取项目级 settings 加载项目权限注入 memory 了解你的偏好注入CLAUDE.md了解项目上下文。然后你让它改一个功能它会先说明计划memory 生效用函数式风格写代码memory 生效遵循项目的目录约定CLAUDE.md生效跑测试时自动放行settings 生效但 push 前会问你settings 生效。如果发现某条规则没生效按这个顺序排查现象可能原因排查方法权限规则不生效字段名拼错或路径不对检查 JSON 语法确认路径是相对项目根项目规范没遵守CLAUDE.md 没被加载确认文件在项目根目录重启会话个人偏好丢失memory 没保存或冲突检查 memory 内容看是否有矛盾条目配置改了没反应需要重启进程关闭并重新启动 Claude Code排查的核心思路是先确认配置有没有被读到再确认有没有被覆盖最后确认内容本身对不对。大部分问题都出在第一步——文件放错位置或者 JSON 写错了。6. 几个容易踩的坑和长期维护建议最后分享几个我在长期使用中总结的坑都是文档里不太会提但实际很常见的。坑一JSON 里写注释。settings.json是严格的 JSON不支持注释。很多人习惯性加//说明结果整个文件解析失败所有配置静默失效。要写说明就单独放个 README别往 JSON 里塞。坑二路径写绝对路径。CLAUDE.md和项目级 settings 里的路径尽量用相对路径绝对路径换台机器就失效了。特别是团队协作时绝对路径会直接坑到同事。坑三memory 里写项目信息。我见过有人在 memory 里写当前项目用 Vue结果换个 React 项目后 Claude 还在推荐 Vue 写法。项目信息一定要放CLAUDE.mdmemory 只放跨项目的个人偏好。坑四deny 写太宽。有人为了安全把Bash(git:*)整个 deny 了结果 Claude 连git status都跑不了每次都要手动确认。deny 要精准只拦真正危险的操作。坑五CLAUDE.md 长期不更新。项目重构了、换框架了、改规范了CLAUDE.md还原封不动Claude 就会按过时的规则干活。建议把更新CLAUDE.md纳入代码评审清单改架构的时候顺手改一下。关于长期维护我的建议是建立一个简单的节奏每周花十分钟回顾 memory每月花半小时整理 CLAUDE.md每次大重构后检查 settings 的权限是否还合适。这个投入不大但能让你的 Claude Code 一直保持在一个顺手的状态。配置这东西一次配好不难难的是持续维护。把它当成项目的一部分来对待收益会远超预期。
返回列表