laravel 如何优化PDF转换从数据库中获取数据

z2acfund  于 2023-04-07  发布在  其他
关注(0)|答案(3)|浏览(144)

我有一个问题,从数据库加载数据,系统给予我一个错误

Maximum Execution time off 60 seconds exceeded

我意识到我需要优化我的代码来缩短加载数据的时间,我几乎有10K的数据在表中。
这是我的代码

public function export(Request $request){
    $fotoOutcomes= new FotoOutcomeCollection(FotoOutcome::with('user','outcomeCategory','paymentMethod')->select('name','cost','date','pcs')->get());  
    $pdf = PDF::loadView('FotoOutcomeExport/FotoOutcomeExport', compact('fotoOutcomes'));
    return $pdf->download('Foto-Outcome.pdf');

}

请帮助我优化这段代码,我不知道我应该做些什么来优化这段代码。提前谢谢你

UPDATE这是我的视图代码

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>

</head>
<body>
<div className="overflow-x-auto">
    <table className="table table-zebra w-full">
        <thead>
            <tr>
                <th>No</th>
                <th>Name</th>
                <th>Date</th>
                <th>Pcs</th>
                <th>Cost</th>
            </tr>
        </thead>
        <tbody>
            @php $i=1 @endphp
            @foreach ($fotoOutcomes as $fotoOutcome)
            
            <tr>
                <th>{{$i}}</th>
                <td>{{$fotoOutcome->name}}</td>
                <td>{{$fotoOutcome->date}}</td>
                <td>{{$fotoOutcome->pcs}}</td>
                <td>{{$fotoOutcome->cost}}</td>
            </tr>
            @php $i++; @endphp
            @endforeach
        </tbody>
    </table>
</div>
xmakbtuz

xmakbtuz1#

如果你有10K的项目,你在那个查询中需要水合一吨模型。这需要时间和内存。可能最有效的方法是使用DB查询,而不是完全水合模型。假设你的表是foto_outcomes

$fotoOutcomes = \DB::table('foto_outcomes')->get();

但是,这仍然是从该表中提取所有信息。您可以通过不选择*,只应用您需要的字段来进一步减少查询时间:

$fotoOutcomes = \DB::table('foto_outcomes')->select('name', 'date', 'pcs', 'cost')->get();

我看到你在原始查询中包含了三个关系。如果有必要,你必须将它们添加到上面的查询中。你也可以为这些关系添加一个select语句,以保存对这些关系的调用*。但是,如果这些项在原始foto_outcomes表中,你可以跳过它们,使用上面的查询来大大提高效率。

vuktfyat

vuktfyat2#

请显示您生成PDF的视图,当我尝试使用一些Laravel助手函数时,我也遇到了同样的问题(在我的情况下,我尝试使用asset()函数)。
尝试使用loop变量而不是$i变量

<tr>
 <th>{{$loop->index}}</th>
 <td>{{$fotoOutcome->name}}</td>
 <td>{{$fotoOutcome->date}}</td>
 <td>{{$fotoOutcome->pcs}}</td>
 <td>{{$fotoOutcome->cost}}</td>
</tr>

或者,您可以使用少量数据进行测试,如果失败,则错误在视图中

public function export(Request $request){
    $fotoOutcomes= new FotoOutcomeCollection(FotoOutcome::with('user','outcomeCategory','paymentMethod')->select('name','cost','date','pcs')->take(10)->get());  
    $pdf = PDF::loadView('FotoOutcomeExport/FotoOutcomeExport', compact('fotoOutcomes'));
    return $pdf->download('Foto-Outcome.pdf');

}
ca1c2owp

ca1c2owp3#

您可以使用分页来加载少量数据,而不是一次加载所有数据。

public function export(Request $request){
    $pageSize = 100; // set the number of records to load per page
    $fotoOutcomes = FotoOutcome::with('user', 'outcomeCategory', 'paymentMethod')
        ->select('name', 'cost', 'date', 'pcs')
        ->paginate($pageSize); // use pagination to load data in smaller chunks
    $fotoOutcomes = new FotoOutcomeCollection($fotoOutcomes);
    $pdf = PDF::loadView('FotoOutcomeExport/FotoOutcomeExport', compact('fotoOutcomes'));
    return $pdf->download('Foto-Outcome.pdf');
}

你可以在视图代码中这样改变for循环。

@foreach ($fotoOutcomes as $fotoOutcome)
<tr>
    <th>{{ $fotoOutcomes->firstItem() + $loop->index }}</th>
    <td>{{ $fotoOutcome->name }}</td>
    <td>{{ $fotoOutcome->date }}</td>
    <td>{{ $fotoOutcome->pcs }}</td>
    <td>{{ $fotoOutcome->cost }}</td>
</tr>
@endforeach

相关问题