迁移站点后file_put_contents写入异常,重复';'致语法错误
排查与解决思路
先排除代码层面的并发问题
你当前的代码没有加文件锁,哪怕调用频率不高,偶尔出现并发写入时,file_put_contents 默认的覆盖模式可能会因为进程竞争导致内容叠加——比如两个进程同时写入,后一个进程的结尾分号和前一个的内容拼接,就会出现 ';'; 这种情况。
先给写入操作加排他锁试试,修改代码:
$ip = '127.0.0.1'; $content = '<?php return '.var_export($ip, true).';'; file_put_contents('/path/some/where/log.txt', $content, LOCK_EX);
LOCK_EX 会确保同一时间只有一个进程能写入这个文件,避免竞争导致的内容错乱。
校验写入结果,定位问题根源
如果加锁后还是出现异常,就需要验证磁盘写入的一致性。可以在写入后立刻读取文件内容,和预期值对比,一旦不一致就记录错误:
$ip = '127.0.0.1'; $expected = '<?php return '.var_export($ip, true).';'; $filePath = '/path/some/where/log.txt'; file_put_contents($filePath, $expected, LOCK_EX); $actual = file_get_contents($filePath); if ($actual !== $expected) { error_log("IP日志写入异常:预期内容 `$expected`,实际内容 `$actual`"); // 可以尝试重新写入1-2次 }
如果日志里频繁出现这种不匹配,基本可以确定是磁盘或文件系统的问题。
磁盘与文件系统排查步骤
- 查看系统IO日志:检查
/var/log/messages、dmesg输出,看有没有磁盘IO错误、坏道、挂载异常之类的日志信息,比如IO error、bad sector关键词。 - 检测磁盘健康:用
smartctl工具检查磁盘SMART数据,确认是否有坏扇区或硬件故障:
(替换成你的磁盘设备名,比如smartctl -a /dev/your-disk-device/dev/sda) - 文件系统检查:卸载目标分区后,用
fsck检查文件系统完整性:
注意:执行前要确保没有进程在使用该分区,避免数据丢失。umount /your/mount/point fsck /dev/your-disk-partition - 批量写入测试:写个简单的shell脚本,循环写入固定内容到测试文件,然后校验内容是否一致,持续跑一段时间看是否会出现异常:
跑几个小时后看错误日志,如果有异常,磁盘问题的可能性就很大了。#!/bin/bash TEST_FILE="/tmp/test_write.txt" EXPECTED="<?php return '127.0.0.1';" while true; do echo "$EXPECTED" > "$TEST_FILE" ACTUAL=$(cat "$TEST_FILE") if [ "$ACTUAL" != "$EXPECTED" ]; then echo "$(date) 写入异常:预期 '$EXPECTED',实际 '$ACTUAL'" >> /tmp/write_error.log fi sleep 1 done
内容的提问来源于stack exchange,提问作者John Smith
相关产品推荐
相关产品推荐

