【问题标题】:How select objects from model in Yii depends on relational tableYii中如何从模型中选择对象取决于关系表
【发布时间】:2013-02-21 09:26:27
【问题描述】:

我是 Yii 新手,对 AR 关系感到困惑 例如,我有两个具有 MANY_MANY 关系的表

CREATE TABLE `banner` (
  `banner_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `banner_action` varchar(255) DEFAULT NULL,
  ...
  PRIMARY KEY (`banner_id`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8;

CREATE TABLE `position` (
  `position_id` tinyint(3) unsigned NOT NULL AUTO_INCREMENT,
  `position_name` varchar(64) NOT NULL,
  PRIMARY KEY (`position_id`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8;

CREATE TABLE `banner_position` (
  `banner_id` int(11) NOT NULL,
  `position_id` tinyint(4) NOT NULL,
  PRIMARY KEY (`banner_id`,`position_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

横幅可以位于一个或多个位置,例如,id 为 1 的横幅可以放置在位置 1 和 2,横幅 2 可以放置在位置 2 和 3 现在我想获取位置 2 的所有横幅,预计我现在得到两个横幅 我还想检查横幅字段,如果它为空或“测试”,则获取此横幅

在没有像这些 SQL 这样的 ORM id 的简单生活中

SELECT b.banner_id FROM banner b
INNER JOIN banner_position bp ON bp.banner_id = b.banner_id AND bp.position_id = 2
WHERE (b.banner_action = 'test' OR b.banner_action IS NULL)

在 Yii 中我无法理解如何成为

我写了banner_action的标准

$select = new CDbCriteria;
$select->addCondition(array('banner_action = "test" OR banner_action IS NULL'));

并使用模型得到结果

$banner = BannerModel::model()->find($select);

我现在如何添加位置条件,我应该使用 $model->with(???) 还是只将 JOIN 添加到条件中?

$select->join = 'INNER JOIN banner_position bp ON bp.position_id = 2 AND bp.banner_id = t.banner_id';

另外我在 JOIN 中使用关联名称 t,因为它默认用于 SQL 构建,这是正确的,还是我需要使用方法来获取正确的关联名称以防在某些情况下更改?

我也尝试过关系方式

public function relations()
{
    return array(
        'positions' => array(self::MANY_MANY, 'PositionModel',
            'banner_position(banner_id, position_id)')
    );
}

而且这个选择(我不知道如何添加诸如banner_action ='test'或banner_action之类的条件无论如何都是空的)

$banner = BannerModel::model()
                ->with('positions')
                ->find('positions.position_id = 2');

Yii 构建 SQL 看起来不像我预期的那样(我需要 INNER JOIN 并且我不需要 positions 表连接仅banner_positions(这是条件选择)) 并且似乎加入条件是获得我需要的简单和干净的 sql 的唯一方法 而且我还是得到了结果集中的模型......也许 Yii 没有办法处理条件关系?

SELECT `t`.`banner_id` AS `t0_c0`, `t`.`banner_type` AS `t0_c1`, `t`.`banner_content` AS `t0_c2`, `t`.`banner_target` AS `t0_c3`, `t`.`banner_controller` AS `t0_c4`, `t`.`banner_action` AS `t0_c5`, `t`.`banner_param_type` AS `t0_c6`, `t`.`banner_param_direction` AS `t0_c7`, `t`.`banner_param_kind` AS `t0_c8`, `positions`.`position_id` AS `t1_c0`, `positions`.`position_name` AS `t1_c1` FROM `banner` 
`t`  LEFT OUTER JOIN `banner_position` `positions_positions` ON (`t`.`banner_id`=`positions_positions`.`banner_id`) 
LEFT OUTER JOIN `position` `positions` ON (`positions`.`position_id`=`positions_positions`.`position_id`)  
WHERE (positions.position_id = 2)

【问题讨论】:

  • 你试过yii支持的MANY_MANY关系吗?
  • @dInGd0nG 我更改的问题添加了其他信息,请检查它

标签: php activerecord yii


【解决方案1】:

当您标记此问题活动记录时,您应该使用relational Active Records

您必须在模型中定义表之间的关系:

例如Banner

public function relations()
{
    return array(
        'positions'=>array(self::MANY_MANY, 'Position',
            'banner_position(banner_id, position_id)'),
    );
}

然后它将在您的Banner 模型中创建一个包含所有位置的数组。

【讨论】:

  • 我更改了问题来处理您的想法,如果您对它感兴趣,请查看新文本
猜你喜欢
  • 1970-01-01
  • 2010-11-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多