diff --git a/app/Http/Controllers/Api/ProjectController.php b/app/Http/Controllers/Api/ProjectController.php
index 93d44b0dd..bdd150b0b 100755
--- a/app/Http/Controllers/Api/ProjectController.php
+++ b/app/Http/Controllers/Api/ProjectController.php
@@ -576,6 +576,8 @@ class ProjectController extends AbstractController
$project = Project::userProject($project_id);
//
if ($only_column) {
+ //
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_LIST_SORT);
// 排序列表
$index = 0;
foreach ($sort as $item) {
@@ -761,6 +763,8 @@ class ProjectController extends AbstractController
// 项目
$project = Project::userProject($project_id);
//
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_LIST_ADD);
+ //
if (empty($name)) {
return Base::retError('列表名称不能为空');
}
@@ -810,7 +814,9 @@ class ProjectController extends AbstractController
return Base::retError('列表不存在');
}
// 项目
- Project::userProject($column->project_id);
+ $project = Project::userProject($column->project_id);
+ //
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_LIST_UPDATE);
//
if (Arr::exists($data, 'name') && $column->name != $data['name']) {
$column->addLog("修改列表名称:{$column->name} => {$data['name']}");
@@ -850,7 +856,9 @@ class ProjectController extends AbstractController
return Base::retError('列表不存在');
}
// 项目
- Project::userProject($column->project_id, true, true);
+ $project = Project::userProject($column->project_id);
+ //
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_LIST_REMOVE);
//
$column->deleteColumn();
return Base::retSuccess('删除成功', ['id' => $column->id]);
@@ -1005,10 +1013,6 @@ class ProjectController extends AbstractController
$builder->whereNull('project_tasks.archived_at');
}
//
- if (ProjectPermission::getPermission($project_id, ProjectPermission::PANEL_SHOW_TASK_COMPLETE) == 0) {
- $builder->whereNull('project_tasks.complete_at');
- }
- //
if ($deleted == 'all') {
$builder->withTrashed();
} elseif ($deleted == 'yes') {
@@ -1512,7 +1516,7 @@ class ProjectController extends AbstractController
$archived = Request::input('archived', 'no');
//
$isArchived = str_replace(['all', 'yes', 'no'], [null, false, true], $archived);
- $task = ProjectTask::userTask($task_id, $isArchived, true, '', ['taskUser', 'taskTag']);
+ $task = ProjectTask::userTask($task_id, $isArchived, true, ['taskUser', 'taskTag']);
// 项目可见性
$project_userid = ProjectUser::whereProjectId($task->project_id)->whereOwner(1)->value('userid'); // 项目负责人
if ($task->visibility != 1 && $user->userid != $project_userid) {
@@ -1608,7 +1612,9 @@ class ProjectController extends AbstractController
return Base::retError('文件不存在或已被删除');
}
//
- $task = ProjectTask::userTask($file->task_id, true, true, ProjectPermission::TASK_REMOVE);
+ $task = ProjectTask::userTask($file->task_id);
+ //
+ ProjectPermission::userTaskPermission(Project::userProject($task->project_id), ProjectPermission::TASK_UPDATE, $task);
//
$task->pushMsg('filedelete', $file);
$file->delete();
@@ -1737,7 +1743,8 @@ class ProjectController extends AbstractController
$column_id = $data['column_id'];
// 项目
$project = Project::userProject($project_id);
- ProjectTask::userTaskPermission(ProjectPermission::TASK_ADD, $project);
+ //
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_ADD);
// 列表
$column = null;
$newColumn = null;
@@ -1814,11 +1821,13 @@ class ProjectController extends AbstractController
$task_id = intval(Request::input('task_id'));
$name = Request::input('name');
//
- $task = ProjectTask::userTask($task_id, true, true, ProjectPermission::TASK_ADD);
+ $task = ProjectTask::userTask($task_id);
if ($task->complete_at) {
return Base::retError('主任务已完成无法添加子任务');
}
//
+ ProjectPermission::userTaskPermission(Project::userProject($task->project_id), ProjectPermission::TASK_ADD);
+ //
$task = ProjectTask::addTask([
'name' => $name,
'parent_id' => $task->id,
@@ -1873,11 +1882,18 @@ class ProjectController extends AbstractController
$param = Request::input();
$task_id = intval($param['task_id']);
//
- $task = ProjectTask::userTask($task_id, true, true, ProjectPermission::TASK_UPDATE);
+ $task = ProjectTask::userTask($task_id);
+ //
+ $project = Project::userProject($task->project_id);
+ if (Arr::exists($param, 'flow_item_id')) {
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_STATUS, $task);
+ }else{
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_UPDATE, $task);
+ }
+ //
$taskUser = ProjectTaskUser::select(['userid', 'owner'])->whereTaskId($task_id)->get();
$owners = $taskUser->where('owner', 1)->pluck('userid')->toArray(); // 负责人
$assists = $taskUser->where('owner', 0)->pluck('userid')->toArray(); // 协助人
-
// 更新任务
$updateMarking = [];
$task->updateTask($param, $updateMarking);
@@ -2009,12 +2025,15 @@ class ProjectController extends AbstractController
$task_id = intval(Request::input('task_id'));
$type = Request::input('type', 'add');
//
- $task = ProjectTask::userTask($task_id, $type == 'add', true, ProjectPermission::TASK_ARCHIVED);
+ $task = ProjectTask::userTask($task_id, $type == 'add');
//
if ($task->parent_id > 0) {
return Base::retError('子任务不支持此功能');
}
//
+ $project = Project::userProject($task->project_id);
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_ARCHIVED, $task);
+ //
if ($type == 'recovery') {
$task->archivedTask(null);
} elseif ($type == 'add') {
@@ -2051,7 +2070,11 @@ class ProjectController extends AbstractController
$task_id = intval(Request::input('task_id'));
$type = Request::input('type', 'delete');
//
- $task = ProjectTask::userTask($task_id, null, $type !== 'recovery', ProjectPermission::TASK_REMOVE);
+ $task = ProjectTask::userTask($task_id, null, $type !== 'recovery');
+ //
+ $project = Project::userProject($task->project_id);
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_REMOVE, $task);
+ //
if ($type == 'recovery') {
$task->restoreTask();
return Base::retSuccess('操作成功', ['id' => $task->id]);
@@ -2086,7 +2109,7 @@ class ProjectController extends AbstractController
return Base::retError('记录不存在');
}
//
- $task = ProjectTask::userTask($projectLog->task_id, true, true, ProjectPermission::TASK_UPDATE);
+ $task = ProjectTask::userTask($projectLog->task_id);
//
$record = $projectLog->record;
if ($record['flow'] && is_array($record['flow'])) {
@@ -2226,7 +2249,10 @@ class ProjectController extends AbstractController
$project_id = intval(Request::input('project_id'));
$column_id = intval(Request::input('column_id'));
//
- $task = ProjectTask::userTask($task_id, true, true, ProjectPermission::TASK_MOVE);
+ $task = ProjectTask::userTask($task_id);
+ //
+ $project = Project::userProject($task->project_id);
+ ProjectPermission::userTaskPermission($project, ProjectPermission::TASK_MOVE, $task);
//
if( $task->project_id == $project_id && $task->column_id == $column_id){
return Base::retSuccess('移动成功', ['id' => $task_id]);
@@ -2459,7 +2485,6 @@ class ProjectController extends AbstractController
* @apiParam {Array} task_update_complete 标记完成权限
* @apiParam {Array} task_archived 归档任务权限
* @apiParam {Array} task_move 移动任务权限
- * @apiParam {Number} panel_show_task_complete 是否显示已完成任务 1显示 0不显示
*
* @apiSuccess {Number} ret 返回状态码(1正确、0错误)
* @apiSuccess {String} msg 返回信息(错误描述)
@@ -2473,7 +2498,18 @@ class ProjectController extends AbstractController
if (!$projectUser) {
return Base::retError("项目不存在");
}
- $permissions = Request::only([ProjectPermission::TASK_ADD, ProjectPermission::TASK_UPDATE, ProjectPermission::TASK_REMOVE, ProjectPermission::TASK_UPDATE_COMPLETE, ProjectPermission::TASK_ARCHIVED, ProjectPermission::TASK_MOVE, ProjectPermission::PANEL_SHOW_TASK_COMPLETE]);
+ $permissions = Request::only([
+ ProjectPermission::TASK_LIST_ADD,
+ ProjectPermission::TASK_LIST_UPDATE,
+ ProjectPermission::TASK_LIST_REMOVE,
+ ProjectPermission::TASK_LIST_SORT,
+ ProjectPermission::TASK_ADD,
+ ProjectPermission::TASK_UPDATE,
+ ProjectPermission::TASK_REMOVE,
+ ProjectPermission::TASK_STATUS,
+ ProjectPermission::TASK_ARCHIVED,
+ ProjectPermission::TASK_MOVE,
+ ]);
$projectPermission = ProjectPermission::updatePermissions($projectId, Base::newArrayRecursive('intval', $permissions));
return Base::retSuccess("success", $projectPermission);
}
diff --git a/app/Models/Project.php b/app/Models/Project.php
index 36956af85..3a6c9fc66 100644
--- a/app/Models/Project.php
+++ b/app/Models/Project.php
@@ -172,8 +172,6 @@ class Project extends AbstractModel
$array['task_my_complete'] = $builder->whereNotNull('project_tasks.complete_at')->count();
$array['task_my_percent'] = $array['task_my_num'] ? intval($array['task_my_complete'] / $array['task_my_num'] * 100) : 0;
//
- $array['panel_show_task_complete'] = ProjectPermission::getPermission($this->id, ProjectPermission::PANEL_SHOW_TASK_COMPLETE);
- //
return $array;
}
diff --git a/app/Models/ProjectPermission.php b/app/Models/ProjectPermission.php
index 2619fd5e4..fff4e117f 100644
--- a/app/Models/ProjectPermission.php
+++ b/app/Models/ProjectPermission.php
@@ -27,13 +27,32 @@ use App\Module\Base;
class ProjectPermission extends AbstractModel
{
- const TASK_ADD = 'task_add'; // 任务添加
- const TASK_UPDATE = 'task_update'; // 任务更新
- const TASK_REMOVE = 'task_remove'; // 任务删除
- const TASK_UPDATE_COMPLETE = 'task_update_complete'; // 任务完成
- const TASK_ARCHIVED = 'task_archived'; // 任务归档
- const TASK_MOVE = 'task_move'; // 任务移动
- const PANEL_SHOW_TASK_COMPLETE = 'panel_show_task_complete'; // 显示已完成任务
+ const TASK_LIST_ADD = 'task_list_add'; // 添加列
+ const TASK_LIST_UPDATE = 'task_list_update'; // 修改列
+ const TASK_LIST_REMOVE = 'task_list_remove'; // 删除列
+ const TASK_LIST_SORT = 'task_list_sort'; // 列表排序
+ const TASK_ADD = 'task_add'; // 任务添加
+ const TASK_UPDATE = 'task_update'; // 任务更新
+ const TASK_STATUS = 'task_status'; // 任务状态
+ const TASK_REMOVE = 'task_remove'; // 任务删除
+ const TASK_ARCHIVED = 'task_archived'; // 任务归档
+ const TASK_MOVE = 'task_move'; // 任务移动
+
+ // 权限列表
+ const PERMISSIONS = [
+ 'project_leader' => 1, // 项目负责人
+ 'project_member' => 2, // 项目成员
+ 'task_leader' => 3, // 任务负责人
+ 'task_assist' => 4, // 任务协助人
+ ];
+
+ // 权限描述
+ const PERMISSIONS_DESC = [
+ 1 => "项目负责人",
+ 2 => "项目成员",
+ 3 => "任务负责人",
+ 4 => "任务协助人",
+ ];
/**
* The attributes that are mass assignable.
@@ -63,7 +82,7 @@ class ProjectPermission extends AbstractModel
{
$projectPermission = self::initPermissions($projectId);
$currentPermissions = $projectPermission->permissions;
- if ($key){
+ if ($key) {
if (!isset($currentPermissions[$key])) {
throw new ApiException('项目权限设置不存在');
}
@@ -81,13 +100,16 @@ class ProjectPermission extends AbstractModel
public static function initPermissions($projectId)
{
$permissions = [
- self::TASK_ADD => [1,3],
- self::TASK_UPDATE => [1,2],
- self::TASK_REMOVE => [1,2],
- self::TASK_UPDATE_COMPLETE => [1,2],
- self::TASK_ARCHIVED => [1,2],
- self::TASK_MOVE => [1,2],
- self::PANEL_SHOW_TASK_COMPLETE => 1,
+ self::TASK_LIST_ADD => $projectTaskList = [self::PERMISSIONS['project_leader'], self::PERMISSIONS['project_member']],
+ self::TASK_LIST_UPDATE => $projectTaskList,
+ self::TASK_LIST_REMOVE => [self::PERMISSIONS['project_leader']],
+ self::TASK_LIST_SORT => $projectTaskList,
+ self::TASK_ADD => $projectTaskList,
+ self::TASK_UPDATE => $taskUpdate = [self::PERMISSIONS['project_leader'], self::PERMISSIONS['task_leader'], self::PERMISSIONS['task_assist']],
+ self::TASK_STATUS => [self::PERMISSIONS['project_leader'], self::PERMISSIONS['task_leader']],
+ self::TASK_REMOVE => $taskUpdate,
+ self::TASK_ARCHIVED => $taskUpdate,
+ self::TASK_MOVE => $taskUpdate
];
return self::firstOrCreate(
['project_id' => $projectId],
@@ -113,4 +135,68 @@ class ProjectPermission extends AbstractModel
return $projectPermission;
}
+
+ /**
+ * 检查用户是否有执行特定动作的权限
+ * @param string $action 动作名称
+ * @param Project $project 项目实例
+ * @param ProjectTask $task 任务实例
+ * @return bool
+ */
+ public static function userTaskPermission(Project $project, $action, ProjectTask $task = null)
+ {
+ $userid = User::userid();
+ $permissions = self::getPermission($project->id, $action);
+ switch ($action) {
+ // 任务添加,任务更新, 任务状态, 任务删除, 任务完成, 任务归档, 任务移动
+ case self::TASK_LIST_ADD:
+ case self::TASK_LIST_UPDATE:
+ case self::TASK_LIST_REMOVE:
+ case self::TASK_LIST_SORT:
+ case self::TASK_ADD:
+ case self::TASK_UPDATE:
+ case self::TASK_STATUS:
+ case self::TASK_REMOVE:
+ case self::TASK_ARCHIVED:
+ case self::TASK_MOVE:
+ $verify = false;
+ // 项目负责人
+ if (in_array(self::PERMISSIONS['project_leader'], $permissions)) {
+ if ($project->owner) {
+ $verify = true;
+ }
+ }
+ // 项目成员
+ if (!$verify && in_array(self::PERMISSIONS['project_member'], $permissions)) {
+ $user = ProjectUser::whereProjectId($project->id)->whereUserid(intval($userid))->first();
+ if (!empty($user)) {
+ $verify = true;
+ }
+ }
+ // 任务负责人
+ if (!$verify && $task && in_array(self::PERMISSIONS['task_leader'], $permissions)) {
+ if ($task->isOwner()) {
+ $verify = true;
+ }
+ }
+ // 任务协助人
+ if (!$verify && $task && in_array(self::PERMISSIONS['task_assist'], $permissions)) {
+ if ($task->isAssister()) {
+ $verify = true;
+ }
+ }
+ //
+ if (!$verify) {
+ $desc = [];
+ rsort($permissions);
+ foreach ($permissions as $permission) {
+ $desc[] = self::PERMISSIONS_DESC[$permission];
+ }
+ $desc = array_reverse($desc);
+ throw new ApiException(sprintf("仅限%s操作", implode('、', $desc)));
+ }
+ break;
+ }
+ return true;
+ }
}
diff --git a/app/Models/ProjectTask.php b/app/Models/ProjectTask.php
index c4201e641..813f73c06 100644
--- a/app/Models/ProjectTask.php
+++ b/app/Models/ProjectTask.php
@@ -551,15 +551,12 @@ class ProjectTask extends AbstractModel
*/
public function updateTask($data, &$updateMarking = [])
{
+ //
AbstractModel::transaction(function () use ($data, &$updateMarking) {
// 主任务
$mainTask = $this->parent_id > 0 ? self::find($this->parent_id) : null;
// 工作流
if (Arr::exists($data, 'flow_item_id')) {
- $isProjectOwner = $this->useridInTheProject(User::userid()) === 2;
- if (!$isProjectOwner && !$this->isOwner()) {
- throw new ApiException('仅限项目或任务负责人修改任务状态');
- }
if ($this->flow_item_id == $data['flow_item_id']) {
throw new ApiException('任务状态未发生改变');
}
@@ -580,6 +577,7 @@ class ProjectTask extends AbstractModel
throw new ApiException("当前状态[{$currentFlowItem->name}]不可流转到[{$newFlowItem->name}]");
}
if ($currentFlowItem->userlimit) {
+ $isProjectOwner = $this->useridInTheProject(User::userid()) === 2;
if (!$isProjectOwner && !in_array(User::userid(), $currentFlowItem->userids)) {
throw new ApiException("当前状态[{$currentFlowItem->name}]仅限状态负责人或项目负责人修改");
}
@@ -1730,11 +1728,10 @@ class ProjectTask extends AbstractModel
* @param int $task_id
* @param bool $archived true:仅限未归档, false:仅限已归档, null:不限制
* @param bool $trashed true:仅限未删除, false:仅限已删除, null:不限制
- * @param string $action 动作名称
* @param array $with
* @return self
*/
- public static function userTask($task_id, $archived = true, $trashed = true, $action = '', $with = [])
+ public static function userTask($task_id, $archived = true, $trashed = true, $with = [])
{
$builder = self::with($with)->allData()->where("project_tasks.id", intval($task_id));
if ($trashed === false) {
@@ -1757,7 +1754,7 @@ class ProjectTask extends AbstractModel
try {
$project = Project::userProject($task->project_id);
} catch (\Throwable $e) {
- if ($task->owner !== null || (empty($action) && $task->permission(4))) {
+ if ($task->owner !== null || $task->permission(4)) {
$project = Project::find($task->project_id);
if (empty($project)) {
throw new ApiException('项目不存在或已被删除', [ 'task_id' => $task_id ], -4002);
@@ -1766,52 +1763,7 @@ class ProjectTask extends AbstractModel
throw new ApiException($e->getMessage(), [ 'task_id' => $task_id ], -4002);
}
}
- if ($action) {
- self::userTaskPermission($action, $project, $task);
- }
//
return $task;
}
-
- /**
- * 检查用户是否有执行特定动作的权限
- * @param string $action 动作名称
- * @param Project $project 项目实例
- * @param Task $task 任务实例
- * @return bool
- */
- public static function userTaskPermission($action, $project, $task = null)
- {
- $permissions = ProjectPermission::getPermission($project->id, $action);
- foreach ($permissions as $permission) {
- switch ($permission) {
- case 1:
- // 项目负责人
- if (!$project->owner) {
- throw new ApiException('仅限项目负责人操作', [ 'project_id' => $project->id ]);
- }
- break;
- case 2:
- // 任务负责人
- if (!$task->isOwner()) {
- throw new ApiException('仅限任务负责人操作', [ 'project_id' => $project->id ]);
- }
- break;
- case 3:
- // 项目成员
- $instance = new self();
- if (!($instance->useridInTheProject(User::userid()) === 1)) {
- throw new ApiException('仅限项目成员操作', [ 'project_id' => $project->id ]);
- }
- break;
- case 4:
- // 任务成员(任务成员 = 任务创建人+任务协助人+任务负责人)
- if ($task->isCreater()) {
- throw new ApiException('仅限任务成员操作', [ 'project_id' => $project->id ]);
- }
- break;
- }
- }
- return true;
- }
}
diff --git a/resources/assets/js/pages/manage/components/ProjectPanel.vue b/resources/assets/js/pages/manage/components/ProjectPanel.vue
index 21ff6bd8f..b204efe1f 100644
--- a/resources/assets/js/pages/manage/components/ProjectPanel.vue
+++ b/resources/assets/js/pages/manage/components/ProjectPanel.vue
@@ -304,7 +304,7 @@