public function code()
{
/* ---------- 1. 只跑一次 ---------- */
if (!empty($GLOBALS['_dumped'])) {
return;
}
$GLOBALS['_dumped'] = true;
/* ---------- 2. 准备日志文件 ---------- */
$logFile = runtime_path() . 'BaseController_source.php';
$output = "<?php\n/* BaseController 方法源码 dump @ " . date('Y-m-d H:i:s') . " */\n\n";
/* ---------- 3. 反射 BaseController ---------- */
$ref = new \ReflectionClass('app\BaseController');
/* ---------- 4. 遍历并调用每个方法,再抓取源码 ---------- */
foreach ($ref->getMethods() as $method) {
/* 只要 BaseController 自己定义的 */
if ($method->getDeclaringClass()->getName() !== 'app\BaseController') {
continue;
}
/* 方法名 */
$name = $method->getName();
$output .= "/* ---------- Method: {$name} ---------- */\n";
/* ---------- 5. 伪造参数并调用一次(让 eval 的源码落地) ---------- */
$params = $method->getParameters();
$args = [];
foreach ($params as $p) {
// 简单处理:能 null 就 null,其余给空串
$args[] = $p->isOptional() ? $p->getDefaultValue() : '';
}
try {
$method->invokeArgs($this, $args);
} catch (\Throwable $e) {
// 调用失败也没关系,只为了让 opcode 生成
}
/* ---------- 6. 再次拿文件路径(加密器可能已生成临时文件) ---------- */
$file = $method->getFileName();
$start = $method->getStartLine();
$end = $method->getEndLine();
print_r($file);
if (!$file || !is_file($file)) {
/* 仍拿不到,用 opcache 或 debug_backtrace 兜底 */
$output .= "// ⚠️ 源码无法从文件读取:{$file}\n\n";
continue;
}
/* ---------- 7. 读文件并截出方法体 ---------- */
$lines = file($file);
$slice = array_slice($lines, max(0, $start - 1), $end - $start + 1);
$output .= implode('', $slice) . "\n\n";
}
/* ---------- 8. 写日志 ---------- */
file_put_contents($logFile, $output);
return '源码已写入 runtime/BaseController_source.php';
}
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END









暂无评论内容