没有不值得去解决的问题,也没有不值得去学习的技术!

How to Link One Field in an Association Table to Two Tables Simultaneously in Yii 2.0

Topic task: pa_plan_task

1. Column configuration: pa_config_column, as shown in Figure 1

Column configuration: pa_config_column
Figure 1

2. Column personnel configuration: pa_config_column_user, as shown in Figure 2

Column personnel configuration: pa_config_column_user
Figure 2

3. Topic: pa_plan, as shown in Figure 3

Topic: pa_plan
Figure 3

4. Topic task: pa_plan_task, as shown in Figure 4

Topic task: pa_plan_task
Figure 4

5. Task Management – My Tasks, query rules
(1) The tenant ID of the task is the tenant ID of the currently logged-in user;
(2) The column configuration is not deleted;
(3) The topic is not deleted;
(4) The topic task is not deleted;
(5) The execution user ID of the topic task (`pa_plan_task`.`exec_user_id`) is the currently logged-in user ID && the column personnel configuration is not deleted || the topic creation user ID (`pa_plan`.`create_user_id`) is the currently logged-in user ID && the column personnel configuration is not deleted || (the column personnel configuration tenant ID is the currently logged-in user tenant ID && the column personnel configuration role identifier includes the column owner identifier && && the column personnel configuration is not deleted);

6. For the current query rules, the requirement is that the main table is Topic task: pa_plan_task, which needs to join the table Topic: pa_plan; Topic task: pa_plan_task needs to join the table Column personnel configuration: pa_config_column_user, based on `pa_plan_task`.`exec_user_id`; Topic: pa_plan needs to join the table Column personnel configuration: pa_config_column_user, based on `pa_plan`.`create_user_id`

7. \common\logics\PlanTask.php, declare the relation

PHP

    public function getConfigColumn()
    {
        return $this->hasOne(ConfigColumn::className(), [ 'id' => 'config_column_id' ]);
    }

    public function getPlanById()
    {
        return $this->hasOne(Plan::className(), [ 'id' => 'plan_id' ]);
    }
    
    public function getConfigColumnUser()
    {
        return $this->hasOne(ConfigColumnUser::className(), [ 'config_column_id' => 'config_column_id', 'user_id' => 'exec_user_id' ]);
    }

8. \common\logics\Plan.php, declare the relation

PHP

    public function getConfigColumn()
    {
        return $this->hasOne(ConfigColumn::className(), [ 'id' => 'config_column_id' ]);
    }

    public function getConfigColumnUser()
    {
        return $this->hasOne(ConfigColumnUser::className(), [ 'config_column_id' => 'config_column_id', 'user_id' => 'create_user_id' ]);
    }

9. The final query code is as follows. If a single field in a joined table is simultaneously joined by two tables, you need to set an alias for the joined table

PHP

	$query = $modelClass::find()
		->joinWith('configColumn')
		->joinWith(['configColumnUser ccue'])
		->joinWith(['planById' => function($q) {
			$q->joinWith('configColumnUser ccuc');
		}])
		->where([
			'and',
			[$modelClass::tableName() . '.group_id' => $identity->group_id],
			[ConfigColumn::tableName() . '.is_deleted' => ConfigColumn::IS_DELETED_NO],
			[Plan::tableName() . '.is_deleted' => Plan::IS_DELETED_NO],
			[$modelClass::tableName() . '.is_deleted' => $modelClass::IS_DELETED_NO]
		])
		->andWhere([
			'or',
			[
				'and',
				[$modelClass::tableName() . '.exec_user_id' => $identity->id],
				['ccue.is_deleted' => ConfigColumnUser::IS_DELETED_NO]
			],
			[
				'and',
				[Plan::tableName() . '.create_user_id' => $identity->id],
				['ccuc.is_deleted' => ConfigColumnUser::IS_DELETED_NO]
			],
			[
				'in',
				Plan::tableName() . '.config_column_id',
				$configColumnIds
			]
		])
		->orderBy([$modelClass::tableName() . '.sort_order' => SORT_ASC, $modelClass::tableName() . '.id' => SORT_DESC]);

10. The final generated SQL statement is as follows:

SQL

SELECT `pa_plan_task`.* FROM `pa_plan_task` LEFT JOIN `pa_config_column` ON `pa_plan_task`.`config_column_id` = `pa_config_column`.`id` LEFT JOIN `pa_config_column_user` `ccue` ON `pa_plan_task`.`config_column_id` = `ccue`.`config_column_id` AND `pa_plan_task`.`exec_user_id` = `ccue`.`user_id` LEFT JOIN `pa_plan` ON `pa_plan_task`.`plan_id` = `pa_plan`.`id` LEFT JOIN `pa_config_column_user` `ccuc` ON `pa_plan`.`config_column_id` = `ccuc`.`config_column_id` AND `pa_plan`.`create_user_id` = `ccuc`.`user_id` WHERE (`pa_plan_task`.`group_id`='015ce30b116ce86058fa6ab4fea4ac63') AND (`pa_config_column`.`is_deleted`=0) AND (`pa_plan`.`is_deleted`=0) AND (`pa_plan_task`.`is_deleted`=0) AND (((`pa_plan_task`.`exec_user_id`='8') AND (`ccue`.`is_deleted`=0)) OR ((`pa_plan`.`create_user_id`='8') AND (`ccuc`.`is_deleted`=0)) OR (`pa_plan`.`config_column_id`=1)) ORDER BY `pa_plan_task`.`sort_order`, `pa_plan_task`.`id` DESC LIMIT 10

关于作者 · 持续学习与技术实践

我是一名拥有 15 年以上开发经验的技术从业者,自 2013 年起持续运营个人技术博客,记录工作与个人项目中遇到的真实问题,以及解决问题过程中的探索、实践和思考。

除了技术写作,我也在持续开发和维护自己的独立项目,探索新技术和新工具在实际场景中的应用。我始终相信,没有不值得去解决的问题,也没有不值得去学习的技术。

如果这篇文章对你有所帮助,欢迎浏览博客中的其他文章,也欢迎交流技术经验与想法。

关于我  ·  GitHub  ·  邮件联系