默认语言由配置项、语言包路径、加载时机三者共同决定;default_lang必须设为小写连字符格式并写在config/app.php中,lang_switch_on需开启,语言包须置于app/lang/zh-cn/common.php且内容为return ['hello' => '你好'];,lang::setlang()须在任何lang()调用前于全局中间件执行。

默认语言不是“设了就生效”,而是由配置项、语言包路径、加载时机三者共同决定的;漏掉任一环,lang('hello') 都会原样返回 hello。
default_lang 配置必须写在 config/app.php 里
ThinkPHP 6 不再读取 config/lang.php 或 config.php(TP5/TP3 风格),所有核心多语言开关都集中在 config/app.php。只改 DEFAULT_LANG 常量或旧版配置文件完全无效。
-
'default_lang' => 'zh-cn'是唯一生效的默认语言配置项,必须是小写连字符格式 -
'lang_switch_on' => true必须开启,否则整个多语言机制不启动 -
'lang_list' => ['zh-cn', 'en-us']虽非强制,但建议显式声明,避免Lang::setLang()传入非法值时静默失败
语言包文件必须放在 app/lang/zh-cn/ 下,且叫 common.php
ThinkPHP 默认只加载 app/lang/{lang}/common.php,不是 app/lang/zh-cn.php,也不是 app/lang/zh_CN/common.php。命名错一个字符,就不会加载——而且不报错,lang() 直接回退到键名。
- 目录结构严格为:
app/lang/zh-cn/common.php、app/lang/en-us/common.php - 文件内必须用
return ['hello' => '你好'];,不能包裹在嵌套数组里,不能是 JSON - Linux 服务器上
zh-CN≠zh-cn,大小写敏感,别用 IDE 自动首字母大写
Lang::setLang() 必须在任何 lang() 调用前执行
很多人在控制器 __construct() 里调用 Lang::setLang('en-us'),结果页面还是中文——因为中间件已加载完默认语言包,后续设置只是“换了个没用的 locale”,翻译缓存不会刷新。
- 正确位置是全局中间件,如
app/middleware.php中注册think\middleware\LoadLangPack::class - 若需动态切换(比如用户点按钮),应在中间件中读取 session 或 input,并在
$next($request)前完成Lang::setLang($lang) - 切勿在模型验证规则里依赖未初始化的语言包,
['name', 'require', lang('name_required')]会因加载时机问题返回原 key
lang() 返回原 key 时,90% 是语言包根本没加载
这不是函数失效,而是路径、命名、配置三者中至少一个没对上。调试时不要只盯 lang() 调用处,先确认 app/lang/zh-cn/common.php 是否被 include 过(可临时加 file_put_contents('/tmp/load.log', "zh-cn loaded\n", FILE_APPEND) 验证)。
- 开启调试模式后,缺失 key 会记日志,但线上环境默认静默,容易误判
-
Lang::get('missing')和lang('missing')行为一致:返回'missing',不是null或抛异常 - 模块化项目中,优先级是「模块 lang/ → 应用 lang/ → 框架 lang/」,别把语言包放错层级
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











