Laravel JSON API: 如何从数据库中创建自定义的虚拟资源(用于聚合值)?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Laravel JSON API: 如何从数据库中创建自定义的虚拟资源(用于聚合值)?相关的知识,希望对你有一定的参考价值。
自从几天前我想知道如何添加一个 "虚拟 "资源到我的Laravel JSON API中 ("cloudcreativity/laravel-json-api": "~2.0"
). 来解释一下。
假设我在数据库表中有一个定时器记录和一个Eloquent模型,JSON API包使用它自动将其转换为资源,显示在 /api/v1/timerecords
. 通过添加一个适配器、一个Schema和一些小的配置,这在开箱即用的情况下效果非常好。例如定时器记录。
id | customer_id | user_id | ts_start | ts_end | hours | amount_xy | ...
1 | 123 | 5 | 2020-0...| 2020...| 4.5 | 95.2 | ...
2 | 987 | 5 | 2020-0...| 2020...| 2.75 | 32.8 | ...
但现在我想有一个API端点: /api/v1/timeaggregates
的计算值,如 COUNT(id) AS num_records, SUM(hours) AS sum_hours, AVG(amount_xy) AS avg_xy
,其中,这些记录可以通过各种参数(或过滤器留在API术语?)进行汇总,如。
- "CUSTOMER=123的DATE-ROM和DATE-TO之间的聚合值"
- "CUSTOMER=123的总值"
- "CUSTOMER=123和USER=5的合计值"
当然,这个资源必须是只读的(GET),因为它是 "虚拟 "的。但我甚至无法接近任何工作。而且搜索整个网络也没有任何结果,这让我更加奇怪,因为我发现这样的功能对于一个API来说是一个很常见的任务,不是吗?到目前为止,我已经尝试了什么。
- 尝试创建一个...
EloquentCollection
. 问题是,我无法在某个地方使用这个Collection,因为只有一个通用的JsonApiController。 - 尝试使用一个虚拟模型(jenssegerslaravel-model-----。),但JSON API希望收到Eloquent模型的
- 从其他框架中我知道Repository模式,我会在那里实现这样的聚合函数,但Laravel似乎没有实现这种模式,即使我自己做,又该在哪里调用Repository函数?
- ......无数次的尝试
也许我在这里错过了一些重要的东西,或者问题可能是使用CloudCreativity包,它不支持这样的事情(再次,这将使我怀疑,因为该包似乎非常专业,有很好的文档)。
我appreachiate如果你们有人能给我一个提示。謝謝你們
我创造了一个丑陋的工作方法。如果有更简洁的解决方案,请随时指导我^^。
首先,我创建了一个 "虚拟 "模型,这并不是真正的虚拟,因为我使用了一个现有的 "定时器记录 "表。
class Timeaggregate extends Model {
protected $table = 'timerecords';
}
在资源适配器中,我覆盖了 "时间记录 "表 queryAll()
方法来计算汇总值。
protected function queryAll($query, EncodingParametersInterface $parameters) {
$this->with($query, $parameters);
$this->applyFilters($query, collect($parameters->getFilteringParameters()));
$query->selectRaw('COUNT(id) as count_records')
->selectRaw('SUM(hours) AS sum_hours');
return $query->first();
}
比起资源模式的getAttributes()方法,我可以简单地将计算出的字段添加到响应中,例如: $resource->sum_hours
.
另一个解决方案可能是创建一个非eloquent资源,并手动执行数据库查询以填充所需的属性。但是我还没有测试过,因为我发现我的需求和一个真实存在的资源关系非常密切,所以在我看来,它应该还是一个Eloquent资源。
以上是关于Laravel JSON API: 如何从数据库中创建自定义的虚拟资源(用于聚合值)?的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 Guzzle 和 Laravel 从 JSON 响应中提取单个数组值
将 JSON 数据从 API 转换为数组并在 Laravel 和 Guzzle HTTP Client 中分别显示?
如何将 JSON 对象从 React Native 发送到 Laravel 服务器?