database = $database; $this->eventDispatcher = $eventDispatcher; } /** * @return bool */ public function canUserAccessByNodeId($nid, $uid = FALSE) { if (!$singleTermRestriction = \Drupal::config('permissions_by_term.settings.single_term_restriction')->get('value')) { $access_allowed = TRUE; } else { $access_allowed = FALSE; } $terms = $this->database ->query("SELECT tid FROM {taxonomy_index} WHERE nid = :nid", [':nid' => $nid])->fetchAll(); foreach ($terms as $term) { $access_allowed = $this->isAccessAllowedByDatabase($term->tid, $uid); if (!$access_allowed) { if ($singleTermRestriction) { return $access_allowed; } } if ($access_allowed && !$singleTermRestriction) { return $access_allowed; } } return $access_allowed; } /** * @param int $tid * @param bool|int $uid * @return array */ public function isAccessAllowedByDatabase($tid, $uid = FALSE) { if ($uid === FALSE) { $user = \Drupal::currentUser(); } elseif (is_numeric($uid)) { $user = User::load($uid); } // Admin can access everything (user id "1"). if ($user->id() == 1) { return TRUE; } $tid = intval($tid); if (!$this->isAnyPermissionSetForTerm($tid)) { return TRUE; } /* At this point permissions are enabled, check to see if this user or one * of their roles is allowed. */ $aUserRoles = $user->getRoles(); foreach ($aUserRoles as $sUserRole) { if ($this->isTermAllowedByUserRole($tid, $sUserRole)) { return TRUE; } } $iUid = intval($user->id()); if ($this->isTermAllowedByUserId($tid, $iUid)) { return TRUE; } return FALSE; } /** * @param int $tid * @param int $iUid * * @return bool */ private function isTermAllowedByUserId($tid, $iUid) { $query_result = $this->database->query("SELECT uid FROM {permissions_by_term_user} WHERE tid = :tid AND uid = :uid", [':tid' => $tid, ':uid' => $iUid])->fetchField(); if (!empty($query_result)) { return TRUE; } else { return FALSE; } } /** * @param int $tid * @param string $sUserRole * * @return bool */ public function isTermAllowedByUserRole($tid, $sUserRole) { $query_result = $this->database->query("SELECT rid FROM {permissions_by_term_role} WHERE tid = :tid AND rid IN (:user_roles)", [':tid' => $tid, ':user_roles' => $sUserRole])->fetchField(); if (!empty($query_result)) { return TRUE; } else { return FALSE; } } /** * @param int $tid * * @return bool */ public function isAnyPermissionSetForTerm($tid) { $iUserTableResults = intval($this->database->query("SELECT COUNT(1) FROM {permissions_by_term_user} WHERE tid = :tid", [':tid' => $tid])->fetchField()); $iRoleTableResults = intval($this->database->query("SELECT COUNT(1) FROM {permissions_by_term_role} WHERE tid = :tid", [':tid' => $tid])->fetchField()); if ($iUserTableResults > 0 || $iRoleTableResults > 0) { return TRUE; } } /** * @return AccessResult */ public function handleNode($nodeId) { if ($this->canUserAccessByNodeId($nodeId) === TRUE) { return AccessResult::neutral(); } else { $accessDeniedEvent = new PermissionsByTermDeniedEvent($nodeId); $this->eventDispatcher->dispatch(PermissionsByTermDeniedEvent::NAME, $accessDeniedEvent); return AccessResult::forbidden(); } } }