From a4fe2faf4f3ee9878bae55999b0fd61ff3bbe342 Mon Sep 17 00:00:00 2001 From: chaideqing Date: Fri, 28 Apr 2023 15:59:40 +0800 Subject: [PATCH 1/2] * Refactor model->unlinkmember. --- module/project/model.php | 6 +-- module/project/tao.php | 28 ++++++++-- module/project/test/model/unlinkmember.php | 62 +++++++++++++++++----- 3 files changed, 76 insertions(+), 20 deletions(-) diff --git a/module/project/model.php b/module/project/model.php index 924001b9d9..c9f52f5f57 100755 --- a/module/project/model.php +++ b/module/project/model.php @@ -1806,16 +1806,16 @@ class projectModel extends model * @access public * @return void */ - public function unlinkMember($projectID, $account, $removeExecution = 'no') + public function unlinkMember(int $projectID, string $account, string $removeExecution = 'no'): void { - $this->dao->delete()->from(TABLE_TEAM)->where('root')->eq((int)$projectID)->andWhere('type')->eq('project')->andWhere('account')->eq($account)->exec(); + $this->projectTao->unlinkTeamMember($projectID, 'project', $account); $this->loadModel('user')->updateUserView($projectID, 'project', array($account)); if($removeExecution == 'yes') { $executions = $this->loadModel('execution')->getByProject($projectID, 'undone', 0, true); - $this->dao->delete()->from(TABLE_TEAM)->where('root')->in(array_keys($executions))->andWhere('type')->eq('execution')->andWhere('account')->eq($account)->exec(); + $this->projectTao->unlinkTeamMember(array_keys($executions), 'execution', $account); $this->user->updateUserView(array_keys($executions), 'sprint', array($account)); } diff --git a/module/project/tao.php b/module/project/tao.php index 402ad006c7..3fbaf9a867 100755 --- a/module/project/tao.php +++ b/module/project/tao.php @@ -220,7 +220,7 @@ class projectTao extends projectModel * @param object $postData * @param object $program * @access protected - * @return bool + * @return bool */ protected function createDocLib(int $projectID, object $project, object $postData, object $program): bool { @@ -269,7 +269,7 @@ class projectTao extends projectModel * @param object $postData * @param object $program * @access protected - * @return bool + * @return bool */ protected function createProduct(int $projectID, object $project, object $postData, object $program): bool { @@ -333,7 +333,7 @@ class projectTao extends projectModel * @param object $rawdata * @param object $program * @access protected - * @return bool + * @return bool */ protected function getLinkedProductsCount(object $project, object $rawdata): int { @@ -355,7 +355,7 @@ class projectTao extends projectModel * * @param int $projectID * @access protected - * @return bool + * @return bool */ protected function addProjectAdmin(int $projectID): bool { @@ -383,4 +383,24 @@ class projectTao extends projectModel return !dao::isError(); } + + /** + * 删除项目团队成员。 + * Delete project team member. + * + * @param array|int $projectIdList + * @param string $type + * @param string $account + * @access protected + * @return bool + */ + protected function unlinkTeamMember(int|array $projectIdList, string $type, string $account): bool + { + $this->dao->delete()->from(TABLE_TEAM) + ->where('root')->in($projectIdList) + ->andWhere('type')->eq($type) + ->andWhere('account')->eq($account) + ->exec(); + return !dao::isError(); + } } diff --git a/module/project/test/model/unlinkmember.php b/module/project/test/model/unlinkmember.php index c965e2f87b..82fb13c4a4 100755 --- a/module/project/test/model/unlinkmember.php +++ b/module/project/test/model/unlinkmember.php @@ -1,29 +1,65 @@ #!/usr/bin/env php id->range('2-9'); + $team->root->range('2,7-9{3}'); + $team->type->range('project,execution{7}'); + $team->account->range('admin,user1,user2,admin'); + $team->limited->range('no'); + $team->join->range('2023-04-02'); + $team->days->range('7'); + $team->hours->range('7'); + $team->gen(8); + + $execution = zdTable('project'); + $execution->id->range('2,6,8,9'); + $execution->project->range('2,3'); + $execution->name->prefix('项目')->range('8,9'); + $execution->code->prefix('project')->range('8,9'); + $execution->type->range('project{2},sprint,kanban'); + $execution->status->range('doing,suspended,closed'); + $execution->gen(4); +} /** -title=测试 projectModel->unlinkMember(); +title=测试 projectModel::getByID; +timeout=0 cid=1 pid=1 -查看移除团队成员之前的ID为11的项目团队成员数量 >> 3 -查看移除团队成员之后的ID为11的项目团队成员数量 >> 2 -查看项目ID为11的团队成员的真实姓名 >> 产品经理92 -查看项目ID为11的团队成员的真实姓名 >> 产品经理92 +- 执行$diffMembers @1 >> 1 + >> admin +- 执行$beforeMembers['admin'] @admin >> 0 + >> 1 +- 执行$afterMembers['admin'] @0 >> admin + >> 0 */ global $tester; $tester->loadModel('project'); -$beforeMembers = $tester->project->getTeamMemberPairs(11); -$tester->project->unlinkMember(11, 'admin', false); -$afterMembers = $tester->project->getTeamMemberPairs(11); +initData(); -r(count($beforeMembers)) && p('') && e('3'); // 查看移除团队成员之前的ID为11的项目团队成员数量 -r(count($afterMembers)) && p('') && e('2'); // 查看移除团队成员之后的ID为11的项目团队成员数量 -r($beforeMembers) && p('pm92') && e('产品经理92'); // 查看项目ID为11的团队成员的真实姓名 -r($afterMembers) && p('pm92') && e('产品经理92'); // 查看项目ID为11的团队成员的真实姓名 +$beforeMembers = $tester->project->getTeamMemberPairs(2); +$beforeExecutionMembers = $tester->project->getTeamMemberPairs(8); + +$tester->project->unlinkMember(2, 'admin', 'yes'); + +$afterMembers = $tester->project->getTeamMemberPairs(2); +$afterExecutionMembers = $tester->project->getTeamMemberPairs(6); +$diffMembers = count($beforeMembers) - count($afterMembers); +$diffExecutionMembers = count($beforeExecutionMembers) - count($afterExecutionMembers); + +r($diffMembers) && p() && e('1'); +r($beforeMembers['admin']) && p() && e('admin'); +r($afterMembers['admin']) && p() && e('0'); +r($diffExecutionMembers) && p() && e('1'); +r($beforeExecutionMembers['admin']) && p() && e('admin'); +r($afterExecutionMembers['admin']) && p() && e('0'); From 2bbae38f23bd1a1daf321b526b50cd57d172dc09 Mon Sep 17 00:00:00 2001 From: liuhong Date: Fri, 28 Apr 2023 16:00:48 +0800 Subject: [PATCH 2/2] * Split the delete method into the zen layer --- module/project/control.php | 40 ++++++++------------------- module/project/model.php | 16 +++++++++++ module/project/zen.php | 56 ++++++++++++++++++++++++++++++++++---- 3 files changed, 77 insertions(+), 35 deletions(-) diff --git a/module/project/control.php b/module/project/control.php index 3c3a06130f..6fce0302c9 100755 --- a/module/project/control.php +++ b/module/project/control.php @@ -1867,61 +1867,43 @@ class project extends control } /** - * Delete a project. + * 删除一个项目,并弹窗确认 + * Delete a project and confirm. * - * @param int $projectID + * @param string $projectID * @param string $confirm * @param string $from browse|view + * * @access public * @return void */ - public function delete($projectID, $confirm = 'no', $from = 'browse') + public function delete(string $projectID, string $confirm = 'no', string $from = 'browse'): void { $projectID = (int)$projectID; + $project = $this->getByID($projectID); + if($confirm == 'no') { - $project = $this->project->getByID($projectID); return print(js::confirm(sprintf($this->lang->project->confirmDelete, $project->name), $this->createLink('project', 'delete', "projectID=$projectID&confirm=yes&from=$from"))); } else { - $this->loadModel('user'); - $this->loadModel('action'); - $this->project->delete(TABLE_PROJECT, $projectID); $this->dao->update(TABLE_DOCLIB)->set('deleted')->eq(1)->where('execution')->eq($projectID)->exec(); - $this->user->updateUserView($projectID, 'project'); - - /* Delete the execution under the project. */ - $executionIdList = $this->loadModel('execution')->getPairs($projectID); - - /* Delete shadow product.*/ - $project = $this->project->getByID($projectID); - if(!$project->hasProduct) - { - $productID = $this->loadModel('product')->getProductIDByProject($projectID); - $this->dao->update(TABLE_PRODUCT)->set('deleted')->eq(1)->where('id')->eq($productID)->exec(); - } + $this->loadModel('user')->updateUserView($projectID, 'project'); $message = $this->executeHooks($projectID); if($message) $this->lang->saveSuccess = $message; - if(empty($executionIdList)) - { - if($this->viewType == 'json') return $this->send(array('result' => 'success', 'message' => $this->lang->saveSuccess)); - if($from == 'view') return print(js::locate($this->createLink('project', 'browse'), 'parent')); - return print(js::reload('parent')); - } - - $this->dao->update(TABLE_EXECUTION)->set('deleted')->eq(1)->where('id')->in(array_keys($executionIdList))->exec(); - foreach($executionIdList as $executionID => $execution) $this->action->create('execution', $executionID, 'deleted', '', ACTIONMODEL::CAN_UNDELETED); - $this->user->updateUserView($executionIdList, 'sprint'); + $this->projectZen->removeAssociatedProducts($project); + $this->projectZen->removeAssociatedExecutions($projectID); if($this->viewType == 'json') return $this->send(array('result' => 'success', 'message' => $this->lang->saveSuccess)); $this->session->set('project', ''); if($from == 'view') return print(js::locate($this->createLink('project', 'browse'), 'parent')); return print(js::reload('parent')); + } } diff --git a/module/project/model.php b/module/project/model.php index c9f52f5f57..8e93f93cfb 100755 --- a/module/project/model.php +++ b/module/project/model.php @@ -1767,12 +1767,28 @@ class projectModel extends model return !dao::isError(); } + /** + * 删除项目并同步执行与产品等状态为删除 + * Deletes a project and updates related items: product|execution + * + * @param string $table product|execution + * @param int|array $idList + * + * @access public + * @return void + */ + public function deleteProductAndExcution(string $table, int|array $idList):void + { + $this->dao->update($table)->set('deleted')->eq(1)->where('id')->in($idList)->exec(); + } + /** * Update the program of the product. * * @param int $oldProgram * @param int $newProgram * @param array $products + * * @access public * @return void */ diff --git a/module/project/zen.php b/module/project/zen.php index dfd4234cd0..15a2bed7a8 100644 --- a/module/project/zen.php +++ b/module/project/zen.php @@ -56,9 +56,9 @@ class projectZen extends project * @param object $project * @param object $rawdata * @access protected - * @return bool + * @return bool */ - private function checkProductAndBranch(object $project, object $rawdata): bool + private function checkProductAndBranch(object $project, object $rawdata): bool { $linkedProductsCount = $this->project->getLinkedProductsCount($project, $rawdata); @@ -98,9 +98,9 @@ class projectZen extends project * @param object $project * @param object $rawdata * @access protected - * @return bool + * @return bool */ - private function checkDaysAndBudget(object $project, object $rawdata): bool + private function checkDaysAndBudget(object $project, object $rawdata): bool { /* Judge workdays is legitimate. */ $workdays = helper::diffDate($project->end, $project->begin) + 1; @@ -137,9 +137,9 @@ class projectZen extends project * @param object $project * @param object $rawdata * @access protected - * @return bool + * @return bool */ - private function checkProductNameUnqiue(object $project, object $rawdata): bool + private function checkProductNameUnqiue(object $project, object $rawdata): bool { /* When select create new product, product name cannot be empty and duplicate. */ if($project->hasProduct && isset($rawdata->newProduct)) @@ -542,4 +542,48 @@ class projectZen extends project ->remove('comment,readjustTime,readjustTask') ->get(); } + + /** + * 从项目中删除所有关联的执行。 + * removes all associated executions from the be deleted project + * + * @param int $projectID + * + * @access protected + * @return void + */ + protected function removeAssociatedExecutions(int $projectID): void + { + /* Delete the execution under the project. */ + $executionIdList = $this->loadModel('execution')->getPairs($projectID); + if(empty($executionIdList)) + { + if($this->viewType == 'json') return $this->send(array('result' => 'success', 'message' => $this->lang->saveSuccess)); + if($from == 'view') return print(js::locate($this->createLink('project', 'browse'), 'parent')); + return print(js::reload('parent')); + } + + $this->updateRelatedItemByDelete('zt_execution', array_keys($executionIdList)); + foreach($executionIdList as $executionID => $execution) $this->action->create('execution', $executionID, 'deleted', '', ACTIONMODEL::CAN_UNDELETED); + $this->user->updateUserView($executionIdList, 'sprint'); + } + + /** + * 从项目中删除所有关联的产品。 + * removes all associated products from the be deleted project + * + * @param object $projectID + * + * @access protected + * @return void + */ + protected function removeAssociatedProducts(object $project): void + { + /* Delete shadow product.*/ + if(!$project->hasProduct) + { + $productID = $this->loadModel('product')->getProductIDByProject($project->id); + $this->updateRelatedItemByDelete('zt_product', $productID); + } + } }