简介
Hyperf 的数据库查询构造器为创建和运行数据库查询提供了一个方便的接口。它可用于执行应用程序中大部分数据库操作,且可在所有支持的数据库系统上运行。
Hyperf 的查询构造器使用 PDO 参数绑定来保护您的应用程序免受 SQL 注入攻击。因此没有必要清理作为绑定传递的字符串。
这里只提供一部分常用的教程,具体教程可以到 Laravel 官网查看。 Laravel Query Builder
获取结果
use Hyperf\DbConnection\Db;
$users = Db::select('SELECT * FROM user;');
$users = Db::table('user')->get();
$users = Db::table('user')->select('name', 'gender as user_gender')->get();
Copy to clipboardErrorCopied
Db::select()
方法会返回一个 array,而 get
方法会返回 Hyperf\Collection\Collection
。其中元素是 stdClass
,所以可以通过以下代码返回各个元素的数据
<?php
foreach ($users as $user) {
echo $user->name;
}
Copy to clipboardErrorCopied
将结果转为数组格式
在某些场景下,您可能会希望查询出来的结果内采用 数组(Array)
而不是 stdClass
对象结构时,而 Eloquent
又去除了通过配置的形式配置默认的 FetchMode
,那么此时可以通过监听器来监听 Hyperf\Database\Events\StatementPrepared
事件来变更该配置:
<?php
declare(strict_types=1);
namespace App\Listener;
use Hyperf\Database\Events\StatementPrepared;
use Hyperf\Event\Annotation\Listener;
use Hyperf\Event\Contract\ListenerInterface;
use PDO;
#[Listener]
class FetchModeListener implements ListenerInterface
{
public function listen(): array
{
return [
StatementPrepared::class,
];
}
public function process(object $event)
{
if ($event instanceof StatementPrepared) {
$event->statement->setFetchMode(PDO::FETCH_ASSOC);
}
}
}
Copy to clipboardErrorCopied
获取一行的值
如果想获取一行的值, 则可以使用 first
方法
<?php
use Hyperf\DbConnection\Db;
$row = Db::table('user')->first(); // sql 会自动加上 limit 1
var_dump($row);
Copy to clipboardErrorCopied
获取单个值
如果想获取单个值, 则可以使用 value
方法
<?php
use Hyperf\DbConnection\Db;
$id = Db::table('user')->value('id');
var_dump($id);
Copy to clipboardErrorCopied
获取一列的值
如果你想获取包含单列值的集合,则可以使用 pluck
方法。在下面的例子中,我们将获取角色表中标题的集合:
<?php
use Hyperf\DbConnection\Db;
$names = Db::table('user')->pluck('name');
foreach ($names as $name) {
echo $name;
}
Copy to clipboardErrorCopied
你还可以在返回的集合中指定字段的自定义键值:
<?php
use Hyperf\DbConnection\Db;
$roles = Db::table('roles')->pluck('title', 'name');
foreach ($roles as $name => $title) {
echo $title;
}
Copy to clipboardErrorCopied
分块结果
如果你需要处理上千条数据库记录,你可以考虑使用 chunk
方法。该方法一次获取结果集的一小块,并将其传递给 闭包
函数进行处理。该方法在 Command
编写数千条处理数据的时候非常有用。例如,我们可以将全部 user 表数据切割成一次处理 100 条记录的一小块:
<?php
use Hyperf\DbConnection\Db;
Db::table('user')->orderBy('id')->chunk(100, function ($users) {
foreach ($users as $user) {
//
}
});
Copy to clipboardErrorCopied
你可以通过在 闭包 中返回 false
来终止继续获取分块结果:
use Hyperf\DbConnection\Db;
Db::table('user')->orderBy('id')->chunk(100, function ($users) {
return false;
});
Copy to clipboardErrorCopied
如果要在分块结果时更新数据库记录,则块结果可能会和预计的返回结果不一致。 因此,在分块更新记录时,最好使用 chunkById 方法。 此方法将根据记录的主键自动对结果进行分页:
use Hyperf\DbConnection\Db;
Db::table('user')->where('gender', 1)->chunkById(100, function ($users) {
foreach ($users as $user) {
Db::table('user')
->where('id', $user->id)
->update(['update_time' => time()]);
}
});
Copy to clipboardErrorCopied
在块的回调里面更新或删除记录时,对主键或外键的任何更改都可能影响块查询。 这可能会导致记录没有包含在分块结果中。
聚合查询
框架还提供了聚合类方法,例如 count
, max
, min
, avg
, sum
。
use Hyperf\DbConnection\Db;
$count = Db::table('user')->count();
Copy to clipboardErrorCopied
判断记录是否存在
除了通过 count
方法可以确定查询条件的结果是否存在之外,还可以使用 exists
和 doesntExist
方法:
return Db::table(