Yii2 关系基于属性值而不是键
Yii2 relation based on attribute values instead of keys
我在 db (mysql) 中有 2 个 table,并且这两个之间没有通过键或 ID 的经典关系。我可以定义关系的唯一方法是通过属性值。例如。 table wheel 和 car 和某些车轮仅因尺寸而匹配某些汽车。是否可以在DB级别定义,yii2中and/or,如果是,如何定义?
在关系中我可以添加一个 onCondition(),但是你 必须 定义一个属性 (???)
:
public function getWheels() {
return $this->hasMany(\app\models\Wheel::className(), ['???' => '???'])->onCondition(['<', 'wheelsize', $this->wheelsize]);
}
我可以使用一个伪造的属性并在所有记录中将其设置为 1,但对我来说这似乎有点奇怪。
我在网上找不到任何关于此的内容,或者我只是搜索了错误的方法,或者我正在尝试一些完全错误的做法。你能给我指明正确的方向吗?
我不认为你可以通过关系实现这一点。
但是有一种方法可以解决这个限制。
<?php
namespace app\models;
class Car extend \yii\db\ActiveRecord
{
/**
* @var \app\models\Wheel
*/
private $_wheels;
/**
* @return \app\models\Wheel[]
*/
public function getWheels()
{
if (!$this->_wheels) {
$this->_wheels = Wheel::find()
->where(['<', 'wheelsize', $this->wheelsize])
//->andWhere() customize your where here
->all();
}
return $this->_wheels;
}
}
然后您可以像关系一样访问 wheels
属性。
<?php
$car = Car::find(1);
$car->wheels;
注意此方式不支持Eager Loading
假设您可以将空数组设置为 link,但出于安全原因(我认为)条件“0 = 1”会自动添加到select.
我多次遇到你自己的问题,我能找到的最佳解决方案是显式使用 ActiveQuery(类似于 hasOne 和 hasMany 的情况):
public function getWheels() {
return new ActiveQuery(\app\models\Wheel::className(), [
'where' => 'my condition' // <--- inserte here your condition as string or array
'multiple' => true // true=hasMany, false=hasOne
// you can also add other configuration params (select, on condition, order by, ...
]);
}
这样就可以得到数组和ActiveQuery来添加其他条件:
var_dump($model->wheels); // array of wheels objects
var_dump($model->getWheels()); // yii\db\ActiveQuery object
$model->getWheels()->andWhere(...); // customize active query
我在 db (mysql) 中有 2 个 table,并且这两个之间没有通过键或 ID 的经典关系。我可以定义关系的唯一方法是通过属性值。例如。 table wheel 和 car 和某些车轮仅因尺寸而匹配某些汽车。是否可以在DB级别定义,yii2中and/or,如果是,如何定义?
在关系中我可以添加一个 onCondition(),但是你 必须 定义一个属性 (???)
:
public function getWheels() {
return $this->hasMany(\app\models\Wheel::className(), ['???' => '???'])->onCondition(['<', 'wheelsize', $this->wheelsize]);
}
我可以使用一个伪造的属性并在所有记录中将其设置为 1,但对我来说这似乎有点奇怪。
我在网上找不到任何关于此的内容,或者我只是搜索了错误的方法,或者我正在尝试一些完全错误的做法。你能给我指明正确的方向吗?
我不认为你可以通过关系实现这一点。 但是有一种方法可以解决这个限制。
<?php
namespace app\models;
class Car extend \yii\db\ActiveRecord
{
/**
* @var \app\models\Wheel
*/
private $_wheels;
/**
* @return \app\models\Wheel[]
*/
public function getWheels()
{
if (!$this->_wheels) {
$this->_wheels = Wheel::find()
->where(['<', 'wheelsize', $this->wheelsize])
//->andWhere() customize your where here
->all();
}
return $this->_wheels;
}
}
然后您可以像关系一样访问 wheels
属性。
<?php
$car = Car::find(1);
$car->wheels;
注意此方式不支持Eager Loading
假设您可以将空数组设置为 link,但出于安全原因(我认为)条件“0 = 1”会自动添加到select.
我多次遇到你自己的问题,我能找到的最佳解决方案是显式使用 ActiveQuery(类似于 hasOne 和 hasMany 的情况):
public function getWheels() {
return new ActiveQuery(\app\models\Wheel::className(), [
'where' => 'my condition' // <--- inserte here your condition as string or array
'multiple' => true // true=hasMany, false=hasOne
// you can also add other configuration params (select, on condition, order by, ...
]);
}
这样就可以得到数组和ActiveQuery来添加其他条件:
var_dump($model->wheels); // array of wheels objects
var_dump($model->getWheels()); // yii\db\ActiveQuery object
$model->getWheels()->andWhere(...); // customize active query