环境变量

环境变量是 Viswoole 配置系统的第一层数据源,由 Viswoole\Core\Env 管理:加载项目根目录的 .env 文件,提供统一的读写访问。本篇是 .env 格式与读取规则的完整参考。

.env 文件位置

.env 固定位于项目根目录(BASE_PATH/.env)。通常随项目骨架提供一份 .example.env 模板,复制后修改:

bash
cp .example.env .env

不要提交到版本控制

.env 通常包含数据库密码等敏感信息,务必加入 .gitignore;版本库中只保留模板文件。

文件格式

.env 采用逐行 KEY=VALUE 格式。框架使用逐行解析而非 parse_ini_file——注释中的 ~(; 等特殊字符会导致 INI 解析报错并使整份文件静默失效,因此 .env 不做 INI 校验,也不支持 [SECTION] 分节行(分节行会被忽略)。

ini
# 整行注释(# 或 ; 开头均可)
; 这也是注释

# 基本键值对
APP_DEBUG=true

# 兼容 bash 风格的 export 前缀
export DEFAULT_TIMEZONE=Asia/Shanghai

# 双引号:支持 \n \r \t \" \\ 转义
WELCOME_TEXT="Hello\nWorld"

# 单引号:内容原样保留,不处理转义
REGEX_PATTERN='^\d+
# 未加引号的值:从首个 " #"(空格+#)处截断行内注释 PAGE_SIZE=20 # 每页条数

格式规则明细

规则说明
注释行行首为 #;(允许前导空白)视为注释,跳过
行内注释未加引号的值中,遇到 #(空格 + #)截断其后的内容;# 前无空白不会截断,因此 URL=http://a.com#frag 安全
export 前缀兼容 bash 风格 export KEY=VALUE,前缀自动去除
键名= 左侧为键名,去除首尾空白,为空则整行忽略
= 右侧去除首尾空白;无 = 的行忽略
单引号内容原样保留,不处理转义,引号本身去除
双引号支持 \n\r\t\"\\ 转义,引号本身去除
空值KEY= 解析为空字符串

读取方式

env() 助手函数

php
// 基本读取(推荐在 config/ 配置文件中使用)
$debug = env('app_debug');

// 带默认值:变量不存在(或值为 null)时返回默认值
$host = env('DATABASE_HOST', '127.0.0.1');

// 不传键名时返回全部已加载的环境变量数组
$all = env();

env() 内部等价于 App::factory()->get('env')->get($key, $default)

Env 门面(Facade)

php
use Viswoole\Core\Facade\Env;

Env::get('app_debug');              // 读取
Env::get('DATABASE_HOST', '127.0.0.1'); // 带默认值
Env::has('REDIS_PASSWORD');         // 是否存在(值为 null 视为不存在)
Env::set('feature.enabled', true);  // 编程式写入(仅当前进程有效)

数组式访问

Env 实现了 ArrayAccess,可通过容器实例以数组语法读写:

php
$env = app('env');

$value = $env['APP_DEBUG'];   // 读取,等价 Env::get('APP_DEBUG')
$env['APP_NAME'] = 'demo';    // 写入,等价 Env::set('APP_NAME', 'demo')

不支持 unset

对环境变量执行 unset($env['KEY']) 会直接抛出异常(not support: unset),环境变量一经定义不可通过数组语法删除。

键名规范

内部处理规则

读取与写入时,键名统一做以下转换:

因此以下写法等价,最终都读写存储键 APP_DEBUG

php
env('app.debug');   // 推荐
env('APP_DEBUG');
env('App.Debug');

与配置键的约定

框架自带配置文件中 env() 调用的键名存在两种风格(如 app_debug 小写、DATABASE_HOST 大写),由于读取时统一转大写,两种风格可混用。业务自定义变量建议统一使用大写下划线命名,并与 config/ 中对应 env() 调用保持一致,否则不会被框架读取。

编程式批量设置

Env::set() 传入数组时可批量设置,数组键转大写;值为嵌套数组时会展开为 父键_子键 连接格式:

php
use Viswoole\Core\Facade\Env;

// 等价于定义 DATABASE_HOST 与 DATABASE_PORT
Env::set([
    'DATABASE' => [
        'HOST' => 'localhost',
        'PORT' => 3306,
    ],
]);

Env::get('DATABASE_HOST');   // 'localhost'
Env::get('DATABASE_PORT');   // 3306

布尔值自动转换

以下小写字符串会被自动转换为布尔值:

字符串转换结果
'true'true
'on'true
'false'false
'off'false
其他字符串保持原样
php
env('A') === true;    // .env 中定义 A=true
env('B') === false;   // .env 中定义 B=off

// 注意:转换仅对上面四种小写字面量生效
env('C');             // .env 中定义 C=ON,返回字符串 'ON',而非 true
env('D');             // .env 中定义 D=9501,返回字符串 '9501'

类型敏感

自动转换是大小写敏感的,TRUEOn 等写法不会被转换。需要确保布尔语义时,.env 中请使用小写 true/false/on/off

读取优先级

同一变量可能来自多个位置,Env::get() 按以下顺序取值:

text
.env 文件 > $_ENV(进程环境数组) > getenv()(系统环境变量) > 默认值

详细过程:

  1. Env 初始化时先载入 $_ENV,再解析 .env 文件覆盖同名键——因此 .env 优先于系统环境变量
  2. 内部数据未命中时,回退调用 getenv() 查询系统级环境变量,命中后缓存进内部数据;
  3. 仍未命中返回调用方给定的默认值。
bash
# 系统环境中设置(如 docker run -e APP_DEBUG=false)
export APP_DEBUG=false
ini
# .env 中同时定义
APP_DEBUG=true
php
env('APP_DEBUG');   // → true,.env 文件优先于系统环境变量

容器部署注意

由于 .env 优先级最高,容器化部署时若依赖 docker run -e / Kubernetes env 注入变量,需确保项目根目录不存在同名定义的 .env 文件,否则注入值会被覆盖。

常用配置项速查

以下键名与 config/ 目录对应配置文件中的 env() 调用一致,可直接在 .env 中设置:

键名默认值说明
app_debugtrue调试模式,生产环境必须设为 false
default_timezoneAsia/Shanghai默认时区
default_start_serverhttp默认启动的服务名
cache.storefile默认缓存存储名
DATABASE_DEFAULTdefault默认数据库通道名
DATABASE_HOST127.0.0.1数据库主机
DATABASE_PORT3306数据库端口
DATABASE_NAME''数据库名
DATABASE_USERroot数据库用户
DATABASE_PASSWORD123456数据库密码

完整键位以 config/ 目录下各配置文件中的 env() 调用为准。

下一步