You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复Laravel代码中用户可控路径构造的安全漏洞?

修复Laravel中用户可控路径构造的安全漏洞

存在安全风险的原代码

public function exportRule(Request $request)
{
    $checkRequest = DB::table('table')->where('id', $request->id)->count();
    if (!$checkRequest) {
        return "unable to find requested id";
    }
    $requestId = $request->id;
    $filename = "rules-" . date("mdyhis") . ".xlsx";
    $dir = $this->exportUrl . $requestId;
    if (is_dir($dir)) {
        foreach (scandir($dir) as $file) {
            if ("." === $file || ".." === $file) {
                continue;
            }
            if (is_dir("$dir/$file")) {
                rmdir_recursive("$dir/$file");
            } else {
                unlink("$dir/$file");
            }
        }
        rmdir($dir);
    }
    Excel::store(
        new RulesExport(["request_id" => $requestId]),
        "$requestId/$filename",
        ExcelExcel::XLSX
    );
    $encypfile = hash_file(
        "sha256",
        $this->exportUrl . $requestId . "/$filename"
    );
    Storage::put("public/export/$requestId/$encypfile.txt", $encypfile);
    return Excel::download(
        new RulesExport(["request_id" => $requestId]),
        $filename,
        ExcelExcel::XLSX
    );
}

漏洞分析

这段代码的核心风险是用户可控的$request->id直接被用于构造文件系统路径,攻击者可构造含../等目录遍历字符的请求,实现对服务器任意文件的删除或访问:

  • 用户传入恶意id值(如../../../../etc/passwd)
  • 该值直接赋值给$requestId,并被拼接进$dir、存储路径、哈希计算路径等多个位置
  • 后续的scandir、unlink、rmdir等文件系统操作会使用这些恶意路径,引发目录遍历攻击,可能删除服务器重要文件或访问敏感数据

修复后的代码

use Illuminate\Support\Facades\Storage;

public function exportRule(Request $request)
{
    // 1. 验证输入合法性,确保id为整数且存在于数据库
    $validated = $request->validate([
        'id' => 'required|integer|exists:table,id'
    ]);

    // 2. 从数据库获取可信的记录ID,避免直接使用用户输入值
    $record = DB::table('table')->find($validated['id']);
    $requestId = $record->id;

    $filename = "rules-" . date("mdyhis") . ".xlsx";
    $disk = Storage::disk('public');
    $exportBasePath = "export/$requestId";

    // 3. 用Storage门面安全清理目录,替代手动文件系统操作
    if ($disk->exists($exportBasePath)) {
        $disk->deleteDirectory($exportBasePath);
    }

    // 4. 安全存储Excel文件,依赖Storage处理路径
    Excel::store(
        new RulesExport(["request_id" => $requestId]),
        "$exportBasePath/$filename",
        ExcelExcel::XLSX
    );

    // 5. 通过Storage获取合法文件路径,避免手动拼接
    $filePath = $disk->path("$exportBasePath/$filename");
    $encypfile = hash_file("sha256", $filePath);

    // 6. 安全存储哈希文件
    $disk->put("$exportBasePath/$encypfile.txt", $encypfile);

    return Excel::download(
        new RulesExport(["request_id" => $requestId]),
        $filename,
        ExcelExcel::XLSX
    );
}

修复关键点说明

  • 输入验证过滤:用Laravel验证规则required|integer|exists:table,id,直接拦截非法字符和不存在的ID
  • 使用可信ID值:从数据库查询获取记录ID,而非直接用用户输入值,彻底阻断恶意值注入路径
  • 依赖Storage门面:所有文件操作通过Laravel Storage处理,它会自动处理路径安全,防止目录遍历
  • 简化目录清理:用deleteDirectory替代手动遍历删除,既简洁又避免路径拼接风险
  • 安全获取路径:通过disk->path()获取绝对路径,替代手动拼接字符串,消除路径注入可能

内容的提问来源于stack exchange,提问作者abhishek kashyap

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 13:05:34