phpList 3.6.17 常用 CLI 命令详解
详解 phpList 3.6.17 命令行工具机制、参数解析规则与 17 个命令页,逐命令附实测回显(发送/队列/退信/导入导出/拉黑/维护),并给出 cron 无人值守编排与参数解析踩坑实录。
phpList 3.6.17 常用 CLI 命令详解
目标:详解 phpList 3.6.17 命令行工具的调用机制、参数解析规则与 17 个命令页的全量清单,逐命令给出实测语法与真实回显,覆盖发送、队列、退信、导入导出、拉黑、系统维护与 cron 无人值守编排,并沉淀本次实测踩到的参数解析坑位。
一、环境信息
- phpList 版本:3.6.17(官方最新稳定版);CLI 入口为发布包自带的
bin/phplist包装脚本,实际调用php admin/index.php -c config.php <参数> - 实测环境:Ubuntu 22.04 + PHP 8.1 + MariaDB 10.6,源码包手工安装(安装与包装脚本部署见《Ubuntu 22.04 安装 phpList 3.6.17 指南》6.2 节)
- 实测库内数据:3 个列表(
test未激活、newsletter、demo-list),订阅者若干(含已拉黑样本),发送走本机 1025 端口调试 SMTP 捕获器 - 版本自检(实测回显):
phplist --version
phpList - phpList version 3.6.17 (c) 2000-2026 phpList Ltd, https://www.phplist.com
二、工具机制与参数解析
2.1 调用链与包装脚本
命令行本质是把 Web 管理后台的 17 个功能页(admin 目录下的 PHP 页面)以页面名直接执行:php admin/index.php -p<页面名> -c config.php。推荐自建全局包装脚本 /usr/local/bin/phplist:
cat > /usr/local/bin/phplist <<'EOF'
#!/bin/bash
/usr/bin/php /var/www/lists/admin/index.php $* -c /var/www/lists/config/config.php
EOF
chmod +x /usr/local/bin/phplist
⚠️ 实测坑位 1:
$*(用户参数)必须写在-c之前。phpList 会把key=value形式的参数注入请求上下文,若-c在前,command=reconcileusers这类参数会被吞掉,进而报出「Cannot find config file」这类误导性错误。
2.2 参数解析规则
实测总结四条规则:
- 页面选择用
-p<页面名>连写形式(如-pprocessqueue),-p与页面名之间不能有空格; - 其余参数为单字符连写形式:
-s、-l、-f、-e、-u等,与值之间是否留空格不影响解析(phpList 按字符切片); key=value形式的参数(供 runcommand 等页面使用)必须写在所有-X参数之前,否则被-p解析器吞掉(负面实录见 3.10 节);- 裸跑
phplist(不带任何参数)输出用法与 17 个命令页清单:
phpList - Usage: /var/www/lists/admin/index.php -p page [other parameters]
phpList - Available options:
initialise
dbcheck
send
processqueue
processbounces
import
upgrade
convertstats
reindex
blacklistemail
systemstats
converttoutf8
initlanguages
cron
updatetlds
export
runcommand
2.3 运行安全
config.php 中的 $commandline_users 白名单决定哪些系统用户可运行(空数组=不限制,详见《phpList 3.6.17 配置参数详解》4.5 节);服务器上建议以运行 cron 的专用账号执行,且 TEST=0 确认后再跑真实队列。
2.4 命令页总览
| 命令页 | 用途 | 关键参数 |
|---|---|---|
| initialise | 初始化数据库结构与管理员 | Web 向导参数(见 3.3 节警告) |
| dbcheck | 数据库结构自检 | 无 |
| send | 创建发送活动(进入队列) | -s 主题、-l 列表、-f 发件人、正文从标准输入读入 |
| processqueue | 处理发送队列 | 可配 -c 之外的批量参数走数据库配置 |
| processbounces | 拉取并处理退信 | 无(邮箱配置来自 config) |
| import | 批量导入订阅者 | -f CSV 文件路径、-l 列表 ID |
| export | 导出订阅者 CSV | -l 列表 ID |
| blacklistemail | 将邮箱加入黑名单 | -e 邮箱地址 |
| upgrade | 数据库结构升级 | 无 |
| convertstats | 统计表结构迁移(老版本升级用) | 无 |
| reindex | 重建数据库索引 | 无 |
| converttoutf8 | 数据库整体转 UTF-8 | 无 |
| initlanguages | 初始化/刷新多语言包 | 无 |
| cron | cron 入口页(按配置跑队列+退信) | 无 |
| updatetlds | 更新顶级域名列表(邮箱校验用) | 无 |
| systemstats | 记录系统状态统计 | 无 |
| runcommand | 运行 reconciliation 等后台动作 | 前置 command= 与 option= |
三、命令详解与实测回显
3.1 dbcheck:数据库结构自检
phplist -pdbcheck
实测回显:
phpList - phpList version 3.6.17 (c) 2000-2026 phpList Ltd, https://www.phplist.com
phpList - PASS
升级或迁移后先跑一次,PASS 即结构完好;结构异常时会输出缺失/多余表清单。
3.2 upgrade:数据库升级
phplist -pupgrade
实测回显(已是当前版本时幂等无害):
phpList - phpList version 3.6.17 (c) 2000-2026 phpList Ltd, https://www.phplist.com
Your database version: 3.6.17
Your database is already the correct version, there is no need to upgrade
升级流程:替换代码后跑本命令,phpList 按库内 version 值自动补齐缺失表与字段。
3.3 initialise:初始化数据库
命令行可重复执行初始化页,但已初始化的库会报 Database error 1050 ... Table ... already exists 建表错误,且页面提供「Force Initialisation (will erase all data!)」强制重置选项——会清空全部数据,生产环境严禁误触(实录见《Ubuntu 22.04 安装 phpList 3.6.17 指南》5.1 节)。首次安装建议直接走 Web 向导,CLI 版本用于脚本化全自动安装场景。
3.4 send:创建发送活动
printf "CLI demo body for D1 captures.\n" > /root/demo-body.txt
phplist -psend -s CLI-D2 -l demo-list -f admin@example.com < /root/demo-body.txt
实测回显:
Message with subject CLI-D2 was sent to "demo-list"
参数说明:-s 活动主题;-l 目标列表;-f 发件人地址;活动正文从标准输入读入。send 只把活动写入队列,不直接投递,需要随后执行 processqueue。
⚠️ 实测坑位 2:phpList 按空格重新分词解析参数,参数值中若再出现
-x形式的词会被错误归属(如主题写成-s "From via -f flag",实际主题只取到From via,flag被-f吞掉)。主题避免内嵌短横线词,最稳妥。
3.5 processqueue:处理发送队列
phplist -pprocessqueue
实测回显(4 个订阅者成功投递):
phpList - Found them: 4 to process [0.0007680000] (157)
phpList - sent 1 ETA Mon 26 Oct 11:05 sending 59901 msg/hrphpList - sent 2 ETA Mon 26 Oct 11:05 sending 67155 msg/hrphpList - sent 3 ETA Mon 26 Oct 11:05 sending 70422 msg/hrphpList - sent 4 ETA Mon 26 Oct 11:05 sending 72151 msg/hrphpList - Processed 4 out of 4 subscribers [0.1945120000] (265)
phpList - 4 messages sent in 0.20 seconds (71045 msgs/hr) [0.0002380000] (282)
日志要点:Found them: N 为本批待发订阅者数;sent N ETA ... 显示预估完成时间与瞬时速率;行尾 messages sent in X seconds (N msgs/hr) 是汇总。SMTP 捕获器实际收到 4 封,From 头 "admin@example.com" <admin@example.com> 正确。
发送失败时的日志形态(failed_sent、Warning: script never reached stage 5)与根因定位(查 phplist_eventlog)见《Ubuntu 22.04 安装 phpList 3.6.17 指南》第七节排障实录。
3.6 processbounces:处理退信
phplist -pprocessbounces
实测回显(默认配置指向本机 POP3、无服务):
phpList - Cannot create POP3 connection to {localhost:110/pop3/notls}INBOX: Connection failed to localhost,110: Connection refused
phpList - Download failed, exiting
该报错说明退信邮箱三要素($bounce_mailbox_host/user/password,见《phpList 3.6.17 配置参数详解》4.4 节)未配置或服务不可达。配置真实 POP3 邮箱后,本命令完成「拉取退信 → 模式匹配 → 按阈值自动停发」流水线;mbox 协议则读取本地 mbox 文件。
3.7 import:批量导入订阅者
printf "email\nimport3@example.com\nimport4@example.com\n" > /root/import-users.csv
phplist -pimport -f /root/import-users.csv -l 3
实测回显:
2 emails succesfully imported to the database and added to 1 lists.
2 emails subscribed to the lists
Subscriber data was updated for 2 subscribers
0 subscribers were matched by foreign key, 2 by email
All done
⚠️ 实测坑位 3:
-f是 CSV 文件路径(首行为表头,Error: Cannot find file to import (hint: use -f);-l只认列表数字 ID,传列表名时导入成功但「added to 0 lists」(ID 可在后台 Lists 页或phplist_list表查询)。
3.8 export:导出订阅者
phplist -pexport -l 3
实测回显:
phpList - Export subscribers
phpList - 0 out of 3phpList - File available as "/tmp/phpList subscribers on demo-list from 2026-10-26 to 2026-10-26 (2026-Oct-26).csv"
导出文件落在系统临时目录(实测 633 字节,含表头与订阅者行,已拉黑用户亦在列并带标记)。定期备份订阅者名单可将其纳入 cron 并转存归档目录。
3.9 blacklistemail:邮箱拉黑
phplist -pblacklistemail -e import1@example.com
实测回显:
phpList - OK
⚠️ 实测坑位 4:邮箱地址必须用
-e传递。直接跟在页面名后面(-pblacklistemail import1@example.com)会报:Error: blacklistemail import1@example.com does not process commandline
拉黑后的订阅者全局停发(所有列表),且后台用户列表带 blacklisted 标记;恢复需在后台操作。
3.10 runcommand:后台维护动作入口
phplist command=reconcileusers option=deleteinvalidemail -pruncommand
实测回显(库内无无效地址,删除 0 条为正常结果):
phpList - Command result :Deleting subscribers with an invalid email address0 Subscribers deleted
⚠️ 实测坑位 5:
command=/option=必须放在-pruncommand之前(规则见 2.2 节第 3 条)。写成phplist -pruncommand command=reconcileusers会报:Error: runcommand command=reconcileusers does not process commandline
reconcileusers 常用 option:deleteinvalidemail(删除无效地址)、markblacklisted(按退信记录拉黑)、findusers(按条件查找);动作脚本无状态输出时结果会显示 FAILED(如 command=test 的示例动作本身不回传状态,不代表库操作失败)。
3.11 updatetlds:更新顶级域名列表
phplist -pupdatetlds
实测回显:
phpList - Now we have 1286 top level domains
更新库内 TLD 集合(配合 EMAIL_ADDRESS_VALIDATION_LEVEL 做邮箱域名校验)。建议纳入月度 cron。
3.12 initlanguages:初始化多语言包
phplist -pinitlanguages
实测回显(节选):
phpList - uk
phpList - Up to date
phpList - tr
phpList - Up to date
已最新时逐语言显示 Up to date;新装/升级后会联网拉取语言包。镜像部署在启动时自动执行本命令。
3.13 cron:无人值守总入口
phplist -pcron
实测回显(无待办任务时):
phpList - Nothing to do
cron 页按配置依次执行队列处理与退信处理,是官方推荐的定时任务入口;前提是把 MANUALLY_PROCESS_QUEUE/MANUALLY_PROCESS_BOUNCES 设为 0(见下节)。
3.14 维护三件套:convertstats / reindex / converttoutf8
phplist -pconvertstats
实测回显(统计表已是新版时):
0 entries still to convert
Optimizing table to recover space.
Finished.
phplist -preindex
实测回显(节选):
phpList - processingattribute
phpList - Adding index nameindex (name) to attribute
phpList - Adding index idnameindex (id,name) to attribute
...(逐表重建索引)
phplist -pconverttoutf8
实测回显(已转换时幂等):
phpList - The DB was already converted to UTF-8 on 2026-10-26 10:00
三者均为升级/迁移后的一次性维护动作,重复执行安全。
四、cron 无人值守编排
4.1 前置配置
将 config.php 中两项手动开关关闭(参数语义见《phpList 3.6.17 配置参数详解》4.3/4.4 节):
define('MANUALLY_PROCESS_QUEUE', 0); // 队列只由命令行驱动
define('MANUALLY_PROCESS_BOUNCES', 0); // 退信只由命令行驱动
4.2 crontab 示例
*/10 * * * * /usr/local/bin/phplist -pprocessqueue >/dev/null 2>&1
*/30 * * * * /usr/local/bin/phplist -pprocessbounces >/dev/null 2>&1
0 3 * * 1 /usr/local/bin/phplist -pupdatetlds >/dev/null 2>&1
每日/每周可再挂 phplist -pcron 兜底。批量节奏由 MAILQUEUE_BATCH_SIZE/PERIOD 控制,单次运行超时可设 MAX_PROCESSQUEUE_TIME 断点续跑(下一轮 cron 自动接续)。
4.3 幂等与重试
- 队列对
failed_sent的订阅者自动重试(见 B1 排障实录:补配置后重跑队列即恢复投递); processqueue/processbounces可安全地高频重复执行,无任务时快速返回;- 系统每周会自动发送统计周报类系统邮件,属正常行为。
五、注意事项与常见问题
Q1:命令报 does not process commandline?
两种成因:参数值没有用规定的单字符参数传递(如 -e 之于 blacklistemail),或 key=value 参数写在了 -p 后面(如 runcommand)。修正形式见 3.9/3.10 节负面实录。
Q2:Cannot find config file?
包装脚本参数顺序问题:$* 必须在 -c 之前(见 2.1 节)。
Q3:import 提示找不到文件 / 没加入列表?
-f 传 CSV 文件绝对路径;-l 传列表数字 ID 而非名称(见 3.7 节坑位 3)。
Q4:命令输出开头都有一行版本横幅?
正常行为:CLI 页面统一先输出 phpList - phpList version 3.6.17 ... 标识行,脚本解析时跳过首行即可。
Q5:队列速率显示 msgs/hr 数千是否虚高?
msgs/hr 由本轮实测速率外推(实测 4 封 0.20 秒 → 71045 msgs/hr),样本越小数值越夸张,仅作参考;真实吞吐以批量配置与 SMTP 服务器实际承受为准。
Q6:Web 界面和 CLI 的参数为何有些不同名?
CLI 参数只服务于对应功能页的命令行分支(如 send 页的 -s/-l/-f),与后台表单字段不是一一映射;本系列《phpList 3.6.17 配置参数详解》覆盖的数据库/代码层参数决定功能行为,CLI 参数决定单次调用输入。