* @package group * @version $Id: model.php 4976 2013-07-02 08:15:31Z wyd621@gmail.com $ * @link https://www.zentao.net */ class groupModel extends model { /** * 创建一个分组。 * Create a group. * * @access public * @return bool * @param object $group */ public function create($group) { if(isset($group->limited)) { unset($group->limited); $group->role = 'limited'; } if(!isset($group->vision)) $group->vision = $this->config->vision; $this->lang->error->unique = $this->lang->group->repeat; $this->dao->insert(TABLE_GROUP)->data($group) ->check('name', 'unique', "vision = '{$this->config->vision}' and project='{$group->project}'") ->exec(); if(dao::isError()) return false; $groupID = $this->dao->lastInsertId(); $data = new stdclass(); $data->group = $groupID; $data->module = 'index'; $data->method = 'index'; $this->dao->replace(TABLE_GROUPPRIV)->data($data)->exec(); return $groupID; } /** * 更新权限分组。 * Update a group. * * @param int $groupID * @param object $group * @access public * @return void */ public function update($groupID, $group) { $this->lang->error->unique = $this->lang->group->repeat; $this->dao->update(TABLE_GROUP)->data($group) ->where('id')->eq($groupID) ->exec(); return !dao::isError(); } /** * 复制一个分组。 * Copy a group. * * @param int $groupID * @param object $group * @param array $options * @access public * @return int|false */ public function copy($groupID, $group, $options) { $this->lang->error->unique = $this->lang->group->repeat; $this->dao->insert(TABLE_GROUP)->data($group) ->check('name', 'unique', "vision = '{$this->config->vision}' and project = '{$group->project}'") ->exec(); if(dao::isError()) return false; $newGroupID = $this->dao->lastInsertID(); if(empty($options)) return $newGroupID; if(in_array('copyPriv', $options)) $this->copyPriv($groupID, $newGroupID); if(in_array('copyUser', $options)) $this->copyUser($groupID, $newGroupID); return $newGroupID; } /** * 复制分组的权限。 * Copy privileges. * * @param int $fromGroup * @param int $toGroup * @access public * @return void * @param int $fromGroupID * @param int $toGroupID */ public function copyPriv($fromGroupID, $toGroupID) { $privs = $this->dao->select('*')->from(TABLE_GROUPPRIV)->where('`group`')->eq($fromGroupID)->fetchAll(); foreach($privs as $key => $priv) { $privs[$key]->group = $toGroupID; } $this->insertPrivs($privs); } /** * 复制分组的成员。 * Copy user. * * @param int $fromGroup * @param int $toGroup * @access public * @return void */ public function copyUser($fromGroupID, $toGroupID) { $users = $this->dao->select('*')->from(TABLE_USERGROUP)->where('`group`')->eq($fromGroupID)->fetchAll(); foreach($users as $user) { $user->group = $toGroupID; $this->dao->insert(TABLE_USERGROUP)->data($user, 'id')->exec(); } } /** * 获取分组列表。 * Get group lists. * * @param int $projectID * @access public * @return array */ public function getList($projectID = 0) { return $this->dao->select('*')->from(TABLE_GROUP) ->where('project')->eq($projectID) ->beginIF($this->config->vision)->andWhere('vision')->eq($this->config->vision)->fi() ->orderBy('id') ->fetchAll(); } /** * 获取分组。 * Get group pairs. * * @param int $projectID * @access public * @return array */ public function getPairs($projectID = 0) { return $this->dao->select('id, name')->from(TABLE_GROUP) ->where('project')->eq($projectID) ->andWhere('vision')->eq($this->config->vision) ->orderBy('id')->fetchPairs(); } /** * 获取一个分组。 * Get group by id. * * @param int $groupID * @access public * @return object */ public function getByID($groupID) { $group = $this->dao->findById($groupID)->from(TABLE_GROUP)->fetch(); if(!$group) return null; if($group->acl) $group->acl = json_decode($group->acl, true); if(!isset($group->acl) || !is_array($group->acl)) $group->acl = array(); return $group; } /** * 获取用户的所有分组。 * Get group by account. * * @param string $account * @param bool $allVision * @access public * @return array */ public function getByAccount($account, $allVision = false) { return $this->dao->select('t2.*')->from(TABLE_USERGROUP)->alias('t1') ->leftJoin(TABLE_GROUP)->alias('t2') ->on('t1.`group` = t2.id') ->where('t1.account')->eq($account) ->andWhere('t2.project')->eq(0) ->beginIF(!$allVision)->andWhere('t2.vision')->eq($this->config->vision)->fi() ->fetchAll('id'); } /** * 获取多个分组包含的所有用户。 * Get the accounts in the groups. * * @param array $groupIdList * @access public * @return array */ public function getGroupAccounts($groupIdList = array()) { $groupIdList = array_filter($groupIdList); if(empty($groupIdList)) return array(); return $this->dao->select('account')->from(TABLE_USERGROUP)->where('`group`')->in($groupIdList)->fetchPairs('account'); } /** * 获取一个分组的权限列表。 * Get privileges of a groups. * * @param int $groupID * @access public * @return array */ public function getPrivs($groupID) { $privs = array(); $stmt = $this->dao->select('module, method')->from(TABLE_GROUPPRIV)->where('`group`')->eq($groupID)->orderBy('module')->query(); while($priv = $stmt->fetch()) $privs[$priv->module][$priv->method] = $priv->method; return $privs; } /** * 获取一个分组下的用户Pairs。 * Get user pairs of a group. * * @param int $groupID * @access public * @return array */ public function getUserPairs($groupID) { return $this->dao->select('t2.account, t2.realname') ->from(TABLE_USERGROUP)->alias('t1') ->leftJoin(TABLE_USER)->alias('t2')->on('t1.account = t2.account') ->where('`group`')->eq((int)$groupID) ->beginIF($this->config->vision)->andWhere("CONCAT(',', visions, ',')")->like("%,{$this->config->vision},%")->fi() ->andWhere('t2.deleted')->eq(0) ->orderBy('t2.account') ->fetchPairs(); } /** * 获取系统内权限分组的成员信息。 * Get all group members. * * @access public * @return array */ public function getAllGroupMembers() { /* Get normal group members. */ $memberGroup = $this->dao->select('t1.`group` as `group`, t2.account, t2.realname') ->from(TABLE_USERGROUP)->alias('t1') ->leftJoin(TABLE_USER)->alias('t2')->on('t1.account = t2.account') ->where('t2.deleted')->eq(0) ->beginIF($this->config->vision)->andWhere("CONCAT(',', visions, ',')")->like("%,{$this->config->vision},%")->fi() ->orderBy('t2.account') ->fetchAll(); $groupMembers = array(); foreach($memberGroup as $member) { if(!isset($groupMembers[$member->group])) $groupMembers[$member->group] = array(); $groupMembers[$member->group][$member->account] = $member->realname; } /* Get project admin memebers. */ $projectAdmins = $this->dao->select('t1.account, t2.realname')->from(TABLE_PROJECTADMIN)->alias('t1')->leftJoin(TABLE_USER)->alias('t2')->on('t1.account = t2.account')->fetchPairs(); $adminGroupID = $this->dao->select('id')->from(TABLE_GROUP)->where('role')->eq('projectAdmin')->fetch('id'); $groupMembers[$adminGroupID] = $projectAdmins; return $groupMembers; } /** * 为项目管理员分组展示项目集、项目、产品、执行。 * Get object for manage admin group. * * @access public * @return void */ public function getObjectForAdminGroup() { $objects = $this->dao->select('id, name, path, type, project, grade, parent')->from(TABLE_PROJECT) ->where('vision')->eq($this->config->vision) ->andWhere('type')->ne('program') ->andWhere('deleted')->eq(0) ->fetchAll('id'); $projects = array(); $executions = array(); foreach($objects as $object) { $type = $object->type; $path = explode(',', trim($object->path, ',')); $topID = $path[0]; if($type == 'project') { if($topID != $object->id) $object->name = isset($objects[$topID]) ? $objects[$topID]->name . '/' . $object->name : $object->name; $projects[$object->id] = $object->name; } else { if($object->grade == 2) { unset($objects[$object->parent]); unset($executions[$object->parent]); } $object->name = isset($objects[$object->project]) ? $objects[$object->project]->name . '/' . $object->name : $object->name; $executions[$object->id] = $object->name; } } $programs = $this->getProgramsForAdminGroup(); $products = $this->getProductsForAdminGroup($programs); return array($programs, $projects, $products, $executions); } /** * 为项目管理员分组展示项目集。 * Get programs for admin group. * * @access protected * @return array */ protected function getProgramsForAdminGroup() { $isAdmin = $this->app->user->admin; /* Get the list of program sets under administrator permission. */ if(!$this->app->user->admin) $this->app->user->admin = true; $programs = $this->loadModel('program')->getParentPairs('', '', false); if(!$isAdmin) $this->app->user->admin = false; return $programs; } /** * 为项目管理员分组展示产品列表。 * Get products for admin group. * * @param array $programs * @access protected * @return array */ protected function getProductsForAdminGroup($programs) { $products = array(); $productList = $this->dao->select('id, name, program')->from(TABLE_PRODUCT) ->where('vision')->eq($this->config->vision) ->andWhere('deleted')->eq(0) ->andWhere('shadow')->eq(0) ->fetchAll('id'); foreach($productList as $id => $product) { if(isset($programs[$product->program]) and $this->config->systemMode == 'ALM') $product->name = $programs[$product->program] . '/' . $product->name; $products[$product->id] = $product->name; } return $products; } /** * 获取项目管理员。 * Get project admins for manage project admin. * * @access public * @return array */ public function getProjectAdmins() { $admins = $this->dao->select('*')->from(TABLE_PROJECTADMIN)->fetchGroup('group', 'account'); $projectAdmins = array(); foreach($admins as $adminGroup) { if(!empty($adminGroup)) { $accounts = implode(',', array_keys($adminGroup)); if(isset($projectAdmins[$accounts])) { $adminGroup = current($adminGroup); $projectAdmins[$accounts]->programs .= ',' . $adminGroup->programs; $projectAdmins[$accounts]->projects .= ',' . $adminGroup->projects; $projectAdmins[$accounts]->products .= ',' . $adminGroup->products; $projectAdmins[$accounts]->executions .= ',' . $adminGroup->executions; } else { $projectAdmins[$accounts] = current($adminGroup); } } } return $projectAdmins; } /** * Get admins by object id list. * * @param array $idList * @param string $field * @access public * @return array */ public function getAdmins($idList, $field = 'programs') { $objects = array(); foreach($idList as $id) { $objects[$id] = $this->dao->select('DISTINCT account')->from(TABLE_PROJECTADMIN) ->where("CONCAT(',', $field, ',')")->like("%,$id,%") ->orWhere($field)->eq('all') ->fetchPairs(); } return $objects; } /** * 删除分组。 * Remove group. * * @param int $groupID * @access public * @return void */ public function remove($groupID) { $this->dao->delete()->from(TABLE_GROUP)->where('id')->eq($groupID)->exec(); $this->dao->delete()->from(TABLE_USERGROUP)->where('`group`')->eq($groupID)->exec(); $this->dao->delete()->from(TABLE_GROUPPRIV)->where('`group`')->eq($groupID)->exec(); } /** * Insert privs. * * @param array $privs * @access protected * @return bool */ public function insertPrivs($privs) { $groups = array(); foreach($privs as $priv) $groups[$priv->group] = $priv->group; $privMap = array(); $privList = $this->dao->select('`group`,module,method')->from(TABLE_GROUPPRIV)->where('group')->in($groups)->fetchAll(); foreach($privList as $priv) $privMap[$priv->group . '-' . $priv->module . '-' . $priv->method] = true; foreach($privs as $priv) { if(!isset($privMap[$priv->group . '-' . $priv->module . '-' . $priv->method])) { $this->dao->insert(TABLE_GROUPPRIV)->data($priv, 'id')->exec(); } } return true; } /** * 更新视野权限。 * Update view priv. * * @param int $groupID * @param array $actions * @access public * @return bool */ public function updateView($groupID, $actions) { /* 如果产品不为空,需要将影子产品追加上。Add shadow productID when select noProduct project or execution. */ if(($actions['projects'] || $actions['sprints']) && isset($actions['products'])) { /* Get all noProduct projects and executions . */ $noProductList = $this->loadModel('project')->getNoProductList(); $shadowProductIDList = $this->dao->select('id')->from(TABLE_PRODUCT)->where('shadow')->eq(1)->fetchPairs(); $noProductObjects = array_merge($actions['projects'], $actions['sprints']); foreach($noProductObjects as $objectID) { if(isset($noProductList[$objectID])) $actions['products'][] = $noProductList[$objectID]->product; } } /* 设置views。 Set views. */ if(!$actions['actionallchecker']) { $actions['views'] = empty($actions['views']) ? array() : array_keys($actions['views']); $actions['views'] = array_combine($actions['views'], $actions['views']); if(!isset($actions['actions'])) $actions['actions'] = array(); if(isset($actions['actions']['project']['started'])) $actions['actions']['project']['syncproject'] = 'syncproject'; if(isset($actions['actions']['execution']['started'])) $actions['actions']['execution']['syncexecution'] = 'syncexecution'; $dynamic = array(); foreach($actions['actions'] as $moduleName => $moduleActions) { $groupName = $moduleName; if(isset($this->lang->navGroup->$moduleName)) $groupName = $this->lang->navGroup->$moduleName; if($moduleName == 'case') $groupName = $this->lang->navGroup->testcase; if($groupName != 'my' and !isset($actions['views'][$groupName])) continue; $moduleActions = array_keys($moduleActions); $dynamic[$moduleName] = array_combine($moduleActions, $moduleActions); } $actions['actions'] = $dynamic; } $actions = empty($actions) ? '' : json_encode($actions); $this->dao->update(TABLE_GROUP)->set('acl')->eq($actions)->where('id')->eq($groupID)->exec(); return !dao::isError(); } /** * 按分组维护权限。 * Update privilege of a group. * * @param int $groupID * @param string $nav * @param string $version * @access public * @return bool */ public function updatePrivByGroup($groupID, $nav, $version = '') { /* Delete old. */ $privs = array_keys($this->getPrivsByNav($nav, $version)); $this->dao->delete()->from(TABLE_GROUPPRIV) ->where('`group`')->eq($groupID) ->beginIF(!empty($nav))->andWhere("CONCAT(module, '-', method)")->in($privs)->fi() ->exec(); $data = new stdclass(); $data->group = $groupID; $data->module = 'index'; $data->method = 'index'; $this->dao->replace(TABLE_GROUPPRIV)->data($data)->exec(); /* Insert new. */ if($this->post->actions) { $dependPrivs = array(); foreach($this->config->group->package as $packageCode => $packageData) { if(!isset($packageData->privs)) continue; foreach($packageData->privs as $privCode => $priv) { if(isset($priv['depend'])) $dependPrivs[$privCode] = $priv['depend']; } } $insertPrivs = array(); $insertPrivKeys = array(); foreach($this->post->actions as $moduleName => $moduleActions) { if(empty($moduleName) or empty($moduleActions)) continue; foreach($moduleActions as $actionName) { $data = new stdclass(); $data->group = $groupID; $data->module = $moduleName; $data->method = $actionName; $priKey = "{$moduleName}-{$actionName}"; $insertPrivs[$priKey] = $data; $insertPrivKeys[$priKey] = $priKey; } } $insertDependPrivs = $this->processDepends($dependPrivs, $insertPrivKeys, $insertPrivKeys); foreach($insertDependPrivs as $priKey) { if(isset($insertPrivs[$priKey])) continue; list($moduleName, $actionName) = explode('-', $priKey); $data = new stdclass(); $data->group = $groupID; $data->module = $moduleName; $data->method = $actionName; $insertPrivs[$priKey] = $data; } $this->insertPrivs($insertPrivs); return count($insertDependPrivs) != count($insertPrivKeys); } return true; } /** * 按模块维护权限。 * Update privilege by module. * * @access public * @return void */ public function updatePrivByModule() { if($this->post->module == false || array_filter($this->post->actions) == false || array_filter($this->post->groups) == false) return false; $privs = array(); foreach($this->post->actions as $action) { if(!$action) continue; list($module, $method) = explode('-', $action); foreach($this->post->groups as $group) { $data = new stdclass(); $data->group = $group; $data->module = $module; $data->method = $method; $privs[] = $data; } } return $this->insertPrivs($privs); } /** * 更新用户。 * Update users. * * @param int $groupID * @access public * @return bool */ public function updateUser($groupID) { $members = $this->post->members ? $this->post->members : array(); $groupUsers = $this->dao->select('account')->from(TABLE_USERGROUP)->where('`group`')->eq($groupID)->fetchPairs('account'); $newUsers = array_diff($members, $groupUsers); $delUsers = array_diff($groupUsers, $members); if(!empty($delUsers)) $this->dao->delete()->from(TABLE_USERGROUP)->where('`group`')->eq($groupID)->andWhere('account')->in($delUsers)->exec(); if(empty($newUsers)) return !dao::isError(); $data = new stdclass(); $data->group = $groupID; $data->project = ''; foreach($newUsers as $account) { $data->account = $account; $this->dao->insert(TABLE_USERGROUP)->data($data)->exec(); } return !dao::isError(); } /** * 更新项目管理员。 * Update project admins. * * @param array $formData * @access public * @return void */ public function updateProjectAdmin($formData) { $allUsers = $this->dao->select('account')->from(TABLE_PROJECTADMIN)->fetchPairs(); $this->dao->delete()->from(TABLE_PROJECTADMIN)->exec(); $noProductList = $this->loadModel('project')->getNoProductList(); $shadowProductIDList = $this->dao->select('id')->from(TABLE_PRODUCT)->where('shadow')->eq(1)->fetchPairs(); foreach($formData as $lineID => $data) { if(!in_array('all', $data['product'])) { /* 无产品项目的隐藏产品需要添加到product里。 Append products of 'No Product' project,execution. */ if($data['project'] || $data['execution']) { $objects = array_merge($data['project'], $data['execution']); foreach($objects as $objectID) { if(isset($noProductList[$objectID])) $data['product'][] = $noProductList[$objectID]->product; } } if((in_array('all', $data['execution']) || in_array('all', $data['project']))) $data['product'] = array_merge($data['product'], $shadowProductIDList); } foreach($data['accounts'] as $account) { if(!$account) continue; $projectAdmin = new stdclass(); $projectAdmin->group = $lineID; $projectAdmin->account = $account; $projectAdmin->programs = implode(',', $data['program']); $projectAdmin->projects = implode(',', $data['project']); $projectAdmin->products = implode(',', $data['product']); $projectAdmin->executions = implode(',', $data['execution']); $this->dao->replace(TABLE_PROJECTADMIN)->data($projectAdmin)->exec(); $allUsers[$account] = $account; } } $this->loadModel('user'); foreach($allUsers as $account) { if($account) $this->user->computeUserView($account, true); } return !dao::isError(); } /** * resource排序。 * Sort resource. * * @access public * @return void */ public function sortResource() { $resources = $this->lang->resource; $this->lang->resource = new stdclass(); /* sort moduleOrder. */ ksort($this->lang->moduleOrder, SORT_ASC); foreach($this->lang->moduleOrder as $moduleName) { if(!isset($resources->$moduleName)) continue; $resource = $resources->$moduleName; unset($resources->$moduleName); $this->lang->resource->$moduleName = $resource; } foreach($resources as $key => $resource) { $this->lang->resource->$key = $resource; } /* sort methodOrder. */ foreach($this->lang->resource as $moduleName => $resources) { $resources = (array)$resources; $tmpResources = new stdclass(); if(isset($this->lang->$moduleName->methodOrder)) { ksort($this->lang->$moduleName->methodOrder, SORT_ASC); foreach($this->lang->$moduleName->methodOrder as $key) { if(isset($resources[$key])) { $tmpResources->$key = $resources[$key]; unset($resources[$key]); } } if($resources) { foreach($resources as $key => $resource) { $tmpResources->$key = $resource; } } $this->lang->resource->$moduleName = $tmpResources; unset($tmpResources); } } } /** * 判断分组操作是否可点击。 * Judge an action is clickable or not. * * @param object $group * @param string $action * @static * @access public * @return bool */ public static function isClickable($group, $action) { $action = strtolower($action); if($group->role == 'projectAdmin' && $action != 'manageprojectadmin') return false; if($action == 'manageprojectadmin' && $group->role != 'projectAdmin') return false; if($action == 'manageview' && $group->role == 'limited') return false; if($action == 'copy' && $group->role == 'limited') return false; return true; } /** * 加载resource的语言配置。 * Load language of resource. * * @access public * @return void */ public function loadResourceLang() { foreach($this->lang->resource as $moduleName => $action) $this->app->loadLang($moduleName); $this->app->loadLang('doc'); $this->app->loadLang('api'); $this->lang->custom->common = $this->lang->group->config; $this->lang->doc->common = $this->lang->doc->manage; $this->lang->api->common = $this->lang->api->manage; if(($this->config->edition == 'max' or $this->config->edition == 'ipd') and $this->config->vision == 'rnd' and isset($this->lang->baseline)) $this->lang->baseline->common = $this->lang->group->docTemplate; } /** * 处理权限依赖关系 * Process circular dependency. * * @param array $depends * @param array $privs * @param array $excludes * @param array $processedPrivs * @access protected * @return array */ protected function processDepends($depends, $privs, $excludes, $processedPrivs = array()) { foreach($privs as $priv) { if(!isset($depends[$priv]) || isset($processedPrivs[$priv])) continue; /* 不重复处理权限,防止出现死循环。Avoid the infinite loop. */ $processedPrivs[$priv] = true; foreach($depends[$priv] as $dependPriv) { if(isset($privs[$dependPriv]) || in_array($dependPriv, $excludes)) continue; $privs[$dependPriv] = $dependPriv; $dependPrivs = $this->processDepends($depends, zget($depends, $dependPriv, array()), $excludes, $processedPrivs); foreach($dependPrivs as $depend) { if(!in_array($depend, $excludes)) $privs[$depend] = $depend; } } } return $privs; } /** * 检查subset是否属于该nav。 * Check nav have subset. * * @param string $nav * @param string $subset * @access protected * @return bool */ protected function checkNavSubset($nav, $subset) { if(empty($nav)) return true; if($nav == 'general') return !isset($this->config->group->subset->$subset) || !isset($this->config->group->subset->$subset->nav) || $this->config->group->subset->$subset->nav == 'general'; return isset($this->config->group->subset->$subset) && isset($this->config->group->subset->$subset->nav) && $this->config->group->subset->$subset->nav == $nav; } /** * Get priv list by nav. * * @param string $nav * @param string $version * @access public * @return array */ public function getPrivsByNav($nav = '', $version = '') { $privList = array(); $allPrivs = array(); /* Filter privs equal or greater than this version.*/ if($version) $versionPrivs = $this->getPrivsAfterVersion($version); $hiddenHost = $this->loadModel('zahost')->hiddenHost(); /* Privs in package. */ foreach($this->config->group->package as $packageCode => $packageData) { if(!isset($packageData->privs)) continue; $sortPriv = array(); foreach($packageData->privs as $privCode => $priv) { list($moduleName, $methodName) = explode('-', $privCode); $allPrivs[$privCode] = $privCode; if($hiddenHost && $moduleName == 'zahost') continue; if($hiddenHost && $moduleName == 'zanode' && !in_array($methodName, $this->config->group->showNodePriv)) continue; if(!$this->config->inQuickon && !$this->config->inCompose && in_array("{$moduleName}-{$methodName}", $this->config->group->hiddenPriv)) continue; if(strpos(',' . $priv['edition'] . ',', ',' . $this->config->edition . ',') === false) continue; if(strpos(',' . $priv['vision'] . ',', ',' . $this->config->vision . ',') === false) continue; if(!$this->checkNavSubset($nav, $packageData->subset)) continue; /* If version is selected, only show privs before the version. */ if(!empty($version) and strpos($versionPrivs, ",$privCode,") === false) continue; /* Add methods in workflow menus, remove privs unused in the edition. */ if(isset($this->lang->$moduleName->menus) && isset($this->lang->$moduleName->menus[$methodName])) { $privName = $this->lang->$moduleName->menus[$methodName]; } else { if(!isset($this->lang->resource->$moduleName) || !isset($this->lang->resource->$moduleName->$methodName)) continue; $methodLang = $this->lang->resource->$moduleName->$methodName; if(!isset($this->lang->$moduleName->$methodLang)) { $this->app->loadLang($moduleName); if($moduleName == 'requirement') $this->app->loadLang('story'); } $privName = isset($this->lang->$moduleName) && isset($this->lang->$moduleName->$methodLang) ? $this->lang->$moduleName->$methodLang : $privCode; } $privData = (object)array('code' => $privCode, 'subset' => $packageData->subset, 'package' => $packageCode, 'module' => $moduleName, 'method' => $methodName, 'selected' => false, 'name' => $privName); /* 将order作为键方便排序。 */ if(!empty($priv['order']) && !isset($sortPriv[$priv['order']])) { $sortPriv[$priv['order']] = $privData; } else { $sortPriv[] = $privData; } } /* 以order排序后再放入privList数组。 */ ksort($sortPriv); foreach($sortPriv as $priv) $privList[$priv->code] = $priv; } return $privList; } /** * Get privs list by group. * * @param int $groupID * @access public * @return array */ public function getPrivsByGroup($groupID) { return $this->dao->select("CONCAT(module, '-', method) AS action")->from(TABLE_GROUPPRIV)->where('`group`')->eq($groupID)->fetchPairs(); } /** * AJAX: Get privs by parents. * * @param string $selectedSubset * @param string $selectedPackages * @access public * @return array */ public function getPrivsByParents($selectedSubset, $selectedPackages = '') { $allPrivs = array(); $privs = array(); /* Privs in package. */ foreach($this->config->group->package as $packageCode => $packageData) { if(!isset($packageData->privs)) continue; foreach($packageData->privs as $privCode => $priv) { list($moduleName, $methodName) = explode('-', $privCode); /* Remove privs unused in the edition. */ if(isset($this->lang->$moduleName->menus) && isset($this->lang->$moduleName->menus[$methodName])) { $privName = $this->lang->$moduleName->menus[$methodName]; } else { if(!isset($this->lang->resource->$moduleName) || !isset($this->lang->resource->$moduleName->$methodName)) continue; $methodLang = $this->lang->resource->$moduleName->$methodName; if(!isset($this->lang->$moduleName->$methodLang)) { $this->app->loadLang($moduleName); if($moduleName == 'requirement') $this->app->loadLang('story'); } $privName = isset($this->lang->$moduleName) && isset($this->lang->$moduleName->$methodLang) ? $this->lang->$moduleName->$methodLang : "$moduleName-$methodName"; } $allPrivs[$privCode] = $privCode; $subset = $packageData->subset; if($subset !== $selectedSubset) continue; if($selectedPackages && strpos($selectedPackages, "|$packageCode|") === false) continue; $privs[$privCode] = $privName; } } return $privs; } /** * Get privs after version * * @param string $version * @access public * @return string */ public function getPrivsAfterVersion($version) { $realVersion = str_replace('_', '.', $version); $changelog = array(); foreach($this->lang->changelog as $currentVersion => $currentChangeLog) { if(version_compare($currentVersion, $realVersion, '>=')) $changelog[] = join(',', $currentChangeLog); } $versionPrivs = ',' . join(',', $changelog) . ','; return $versionPrivs; } /** * Get related privs. * * @param array $allPrivList * @param array $selectedPrivList * @param array $recommendSelect * @access public * @return array */ public function getRelatedPrivs($allPrivList, $selectedPrivList, $recommendSelect = array()) { $this->loadResourceLang(); $depends = array(); $privSubsets = array(); $relatedPrivs = array('depend' => array(), 'recommend' => array()); foreach($this->config->group->package as $packagePage => $package) { if(!isset($package->privs)) continue; foreach($package->privs as $privCode => $priv) { $privSubsets[$privCode] = $package->subset; foreach(array('depend', 'recommend') as $type) { /* Show related privs when select. */ if($type == 'recommend' && in_array($privCode, $recommendSelect)) $relatedPrivs[$type][$privCode] = $privCode; if(!in_array($privCode, $selectedPrivList) || !isset($priv[$type])) continue; foreach($priv[$type] as $code => $relatedPriv) { if(!in_array($relatedPriv, $selectedPrivList) && in_array($relatedPriv, $allPrivList)) { $relatedPrivs[$type][$relatedPriv] = $relatedPriv; if($type == 'depend') $depends[$privCode][$code] = $relatedPriv; } } } } } /* Process circular dependency. */ $relatedPrivs['depend'] = $this->processDepends($depends, $relatedPrivs['depend'], $selectedPrivList); $subsetPrivs = array('depend' => array(), 'recommend' => array()); foreach(array('depend', 'recommend') as $type) { foreach($relatedPrivs[$type] as $relatedPriv) { if($type == 'recommend' && isset($relatedPrivs['depend'][$relatedPriv])) continue; // Don't show depend privs to recommend. $subsetName = $privSubsets[$relatedPriv]; $subsetTitle = isset($this->lang->$subsetName) && isset($this->lang->$subsetName->common) ? $this->lang->$subsetName->common : $subsetName; if(!isset($subsetPrivs[$type][$subsetName])) $subsetPrivs[$type][$subsetName] = array('id' => $subsetName, 'text' => $subsetTitle, 'children' => array()); list($moduleName, $methodName) = explode('-', $relatedPriv); if(!isset($this->lang->resource->$moduleName->$methodName)) continue; $method = $this->lang->resource->$moduleName->$methodName; if(!isset($this->lang->$moduleName->$method)) $this->app->loadLang($moduleName); $subsetPrivs[$type][$subsetName]['children'][] = array('id' => $relatedPriv, 'data-module' => $moduleName, 'data-method' => $methodName, 'subset' => $subsetName, 'text' => $this->lang->$moduleName->$method, 'data-id' => $relatedPriv, 'title' => $this->lang->$moduleName->$method); } } return array('depend' => array_values($subsetPrivs['depend']), 'recommend' => array_values($subsetPrivs['recommend'])); } }