使用DB :: raw表达式的带有POINT/POLYGON等的Laravel模型 [英] Laravel model with POINT/POLYGON etc. using DB::raw expressions
问题描述
我有一些使用地理空间字段的模型,例如POINT
,POLYGON
或MULTIPOLYGON
.我想告诉我的模型以一种特殊的方式处理这些属性,以使我获得所需的模型属性集.
I have some models that use geospatial fields like POINT
, POLYGON
or MULTIPOLYGON
. I would like to tell my model to process these attributes in a special way, for me to get the desired model attributes set.
示例:
每个常规Model::find()
或其他Eloquent方法都应在存储数据库值之前或之后应用一些自定义代码.
Example:
Every regular Model::find()
or other Eloquent method should apply some custom code before storing or after retrieving a database value.
$area->surface
是MySQL中的POLYGON
字段,但是在我的模型类中,我想将$area->surfare
作为点数组处理.
$area->surface
is a POLYGON
field in MySQL, but in my model class I would like to handle $area->surfare
as an array of points.
在SELECT
上,我想1)使用原始表达式获取值以获取该值的文本表示形式,2)通过一些自定义PHP代码将WKT字符串转换为数组.
On SELECT
I would therefore like to 1) fetch the value using a raw expression to get a text representation of the value, and 2) go through some custom PHP code to convert the WKT string into an array.
在INSERT/UPDATE
上,我想获取属性值(一个数组),然后1)将其转换为WKT字符串,然后2)使用存储该值的DB raw语句将其写入数据库.
On INSERT/UPDATE
I would like to take the attribute value (an array) and 1) convert it into a WKT string, whereafter 2) it's written to the databse using a DB raw statement that stores the value.
我想将此设置为基于字段的方式,而不是为每个字段设置特殊的获取/设置功能,而不是在控制器中设置-因为我有很多地理空间字段.
I'd like to set this on a field-basis, not as special get/set functions for each field, and not in the controllers - because I have many geosptial fields.
在Laravel中有实现此目标的方法吗?
(同一问题的一个更抽象的版本,是我如何创建用于处理实际SQL查询的属性值的代码,而不仅仅是通过增减器和访问器进行基于值的操作)
更新:
深入研究Laravel Doc和API,我发现也许Eloquent::newQuery()
方法是我需要操纵的?不论SELECT
,INSERT
或UPDATE
,该查询都将用于任何查询吗?
UPDATE:
Looking deeper into the Laravel Doc and API, I found that maybe the Eloquent::newQuery()
method is what I need to manipulate? Would that be used for any query regardless if SELECT
, INSERT
or UPDATE
?
推荐答案
我们现在通过扩展以下功能来对所有模型进行通用解决:
We have now solved this generically for all models by extending our base model with the following functionaly:
- 我们定义了一个保存几何数据的属性数组.
- 如果我们希望将其自动加载为文本,则决定是否基于模型.
- 我们更改了默认查询生成器,以从数据库中选择几何属性作为文本.
以下是我们现在使用的基本模型的摘录:
Here is an excerpt from the base model we now use:
/**
* The attributes that hold geometrical data.
*
* @var array
*/
protected $geometry = array();
/**
* Select geometrical attributes as text from database.
*
* @var bool
*/
protected $geometryAsText = false;
/**
* Get a new query builder for the model's table.
* Manipulate in case we need to convert geometrical fields to text.
*
* @param bool $excludeDeleted
* @return \Illuminate\Database\Eloquent\Builder
*/
public function newQuery($excludeDeleted = true)
{
if (!empty($this->geometry) && $this->geometryAsText === true)
{
$raw = '';
foreach ($this->geometry as $column)
{
$raw .= 'AsText(`' . $this->table . '`.`' . $column . '`) as `' . $column . '`, ';
}
$raw = substr($raw, 0, -2);
return parent::newQuery($excludeDeleted)->addSelect('*', DB::raw($raw));
}
return parent::newQuery($excludeDeleted);
}
这篇关于使用DB :: raw表达式的带有POINT/POLYGON等的Laravel模型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!