You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

306 lines
7.8 KiB

3 years ago
  1. <?php
  2. /**
  3. * @copyright Copyright (c) 2016, ownCloud, Inc.
  4. *
  5. * @author Arthur Schiwon <blizzz@arthur-schiwon.de>
  6. * @author Bart Visscher <bartv@thisnet.nl>
  7. * @author Christoph Wurst <christoph@winzerhof-wurst.at>
  8. * @author Georg Ehrke <oc.list@georgehrke.com>
  9. * @author Joas Schilling <coding@schilljs.com>
  10. * @author John Molakvoæ (skjnldsv) <skjnldsv@protonmail.com>
  11. * @author Lukas Reschke <lukas@statuscode.ch>
  12. * @author Mikael Hammarin <mikael@try2.se>
  13. * @author Morris Jobke <hey@morrisjobke.de>
  14. * @author Roeland Jago Douma <roeland@famdouma.nl>
  15. *
  16. * @license AGPL-3.0
  17. *
  18. * This code is free software: you can redistribute it and/or modify
  19. * it under the terms of the GNU Affero General Public License, version 3,
  20. * as published by the Free Software Foundation.
  21. *
  22. * This program is distributed in the hope that it will be useful,
  23. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  24. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  25. * GNU Affero General Public License for more details.
  26. *
  27. * You should have received a copy of the GNU Affero General Public License, version 3,
  28. * along with this program. If not, see <http://www.gnu.org/licenses/>
  29. *
  30. */
  31. namespace OC;
  32. use OC\Hooks\PublicEmitter;
  33. use OCP\Group\ISubAdmin;
  34. use OCP\IDBConnection;
  35. use OCP\IGroup;
  36. use OCP\IGroupManager;
  37. use OCP\IUser;
  38. use OCP\IUserManager;
  39. class SubAdmin extends PublicEmitter implements ISubAdmin {
  40. /** @var IUserManager */
  41. private $userManager;
  42. /** @var IGroupManager */
  43. private $groupManager;
  44. /** @var IDBConnection */
  45. private $dbConn;
  46. /**
  47. * @param IUserManager $userManager
  48. * @param IGroupManager $groupManager
  49. * @param IDBConnection $dbConn
  50. */
  51. public function __construct(IUserManager $userManager,
  52. IGroupManager $groupManager,
  53. IDBConnection $dbConn) {
  54. $this->userManager = $userManager;
  55. $this->groupManager = $groupManager;
  56. $this->dbConn = $dbConn;
  57. $this->userManager->listen('\OC\User', 'postDelete', function ($user) {
  58. $this->post_deleteUser($user);
  59. });
  60. $this->groupManager->listen('\OC\Group', 'postDelete', function ($group) {
  61. $this->post_deleteGroup($group);
  62. });
  63. }
  64. /**
  65. * add a SubAdmin
  66. * @param IUser $user user to be SubAdmin
  67. * @param IGroup $group group $user becomes subadmin of
  68. */
  69. public function createSubAdmin(IUser $user, IGroup $group): void {
  70. $qb = $this->dbConn->getQueryBuilder();
  71. $qb->insert('group_admin')
  72. ->values([
  73. 'gid' => $qb->createNamedParameter($group->getGID()),
  74. 'uid' => $qb->createNamedParameter($user->getUID())
  75. ])
  76. ->execute();
  77. $this->emit('\OC\SubAdmin', 'postCreateSubAdmin', [$user, $group]);
  78. \OC_Hook::emit("OC_SubAdmin", "post_createSubAdmin", ["gid" => $group->getGID()]);
  79. }
  80. /**
  81. * delete a SubAdmin
  82. * @param IUser $user the user that is the SubAdmin
  83. * @param IGroup $group the group
  84. */
  85. public function deleteSubAdmin(IUser $user, IGroup $group): void {
  86. $qb = $this->dbConn->getQueryBuilder();
  87. $qb->delete('group_admin')
  88. ->where($qb->expr()->eq('gid', $qb->createNamedParameter($group->getGID())))
  89. ->andWhere($qb->expr()->eq('uid', $qb->createNamedParameter($user->getUID())))
  90. ->execute();
  91. $this->emit('\OC\SubAdmin', 'postDeleteSubAdmin', [$user, $group]);
  92. \OC_Hook::emit("OC_SubAdmin", "post_deleteSubAdmin", ["gid" => $group->getGID()]);
  93. }
  94. /**
  95. * get groups of a SubAdmin
  96. * @param IUser $user the SubAdmin
  97. * @return IGroup[]
  98. */
  99. public function getSubAdminsGroups(IUser $user): array {
  100. $groupIds = $this->getSubAdminsGroupIds($user);
  101. $groups = [];
  102. foreach ($groupIds as $groupId) {
  103. $group = $this->groupManager->get($groupId);
  104. if ($group !== null) {
  105. $groups[$group->getGID()] = $group;
  106. }
  107. }
  108. return $groups;
  109. }
  110. /**
  111. * Get group ids of a SubAdmin
  112. * @param IUser $user the SubAdmin
  113. * @return string[]
  114. */
  115. public function getSubAdminsGroupIds(IUser $user): array {
  116. $qb = $this->dbConn->getQueryBuilder();
  117. $result = $qb->select('gid')
  118. ->from('group_admin')
  119. ->where($qb->expr()->eq('uid', $qb->createNamedParameter($user->getUID())))
  120. ->execute();
  121. $groups = [];
  122. while ($row = $result->fetch()) {
  123. $groups[] = $row['gid'];
  124. }
  125. $result->closeCursor();
  126. return $groups;
  127. }
  128. /**
  129. * get an array of groupid and displayName for a user
  130. * @param IUser $user
  131. * @return array ['displayName' => displayname]
  132. */
  133. public function getSubAdminsGroupsName(IUser $user): array {
  134. return array_map(function ($group) {
  135. return ['displayName' => $group->getDisplayName()];
  136. }, $this->getSubAdminsGroups($user));
  137. }
  138. /**
  139. * get SubAdmins of a group
  140. * @param IGroup $group the group
  141. * @return IUser[]
  142. */
  143. public function getGroupsSubAdmins(IGroup $group): array {
  144. $qb = $this->dbConn->getQueryBuilder();
  145. $result = $qb->select('uid')
  146. ->from('group_admin')
  147. ->where($qb->expr()->eq('gid', $qb->createNamedParameter($group->getGID())))
  148. ->execute();
  149. $users = [];
  150. while ($row = $result->fetch()) {
  151. $user = $this->userManager->get($row['uid']);
  152. if (!is_null($user)) {
  153. $users[] = $user;
  154. }
  155. }
  156. $result->closeCursor();
  157. return $users;
  158. }
  159. /**
  160. * get all SubAdmins
  161. * @return array
  162. */
  163. public function getAllSubAdmins(): array {
  164. $qb = $this->dbConn->getQueryBuilder();
  165. $result = $qb->select('*')
  166. ->from('group_admin')
  167. ->execute();
  168. $subadmins = [];
  169. while ($row = $result->fetch()) {
  170. $user = $this->userManager->get($row['uid']);
  171. $group = $this->groupManager->get($row['gid']);
  172. if (!is_null($user) && !is_null($group)) {
  173. $subadmins[] = [
  174. 'user' => $user,
  175. 'group' => $group
  176. ];
  177. }
  178. }
  179. $result->closeCursor();
  180. return $subadmins;
  181. }
  182. /**
  183. * checks if a user is a SubAdmin of a group
  184. * @param IUser $user
  185. * @param IGroup $group
  186. * @return bool
  187. */
  188. public function isSubAdminOfGroup(IUser $user, IGroup $group): bool {
  189. $qb = $this->dbConn->getQueryBuilder();
  190. /*
  191. * Primary key is ('gid', 'uid') so max 1 result possible here
  192. */
  193. $result = $qb->select('*')
  194. ->from('group_admin')
  195. ->where($qb->expr()->eq('gid', $qb->createNamedParameter($group->getGID())))
  196. ->andWhere($qb->expr()->eq('uid', $qb->createNamedParameter($user->getUID())))
  197. ->execute();
  198. $fetch = $result->fetch();
  199. $result->closeCursor();
  200. $result = !empty($fetch) ? true : false;
  201. return $result;
  202. }
  203. /**
  204. * checks if a user is a SubAdmin
  205. * @param IUser $user
  206. * @return bool
  207. */
  208. public function isSubAdmin(IUser $user): bool {
  209. // Check if the user is already an admin
  210. if ($this->groupManager->isAdmin($user->getUID())) {
  211. return true;
  212. }
  213. $qb = $this->dbConn->getQueryBuilder();
  214. $result = $qb->select('gid')
  215. ->from('group_admin')
  216. ->andWhere($qb->expr()->eq('uid', $qb->createNamedParameter($user->getUID())))
  217. ->setMaxResults(1)
  218. ->execute();
  219. $isSubAdmin = $result->fetch();
  220. $result->closeCursor();
  221. return $isSubAdmin !== false;
  222. }
  223. /**
  224. * checks if a user is a accessible by a subadmin
  225. * @param IUser $subadmin
  226. * @param IUser $user
  227. * @return bool
  228. */
  229. public function isUserAccessible(IUser $subadmin, IUser $user): bool {
  230. if (!$this->isSubAdmin($subadmin)) {
  231. return false;
  232. }
  233. if ($this->groupManager->isAdmin($user->getUID())) {
  234. return false;
  235. }
  236. $accessibleGroups = $this->getSubAdminsGroupIds($subadmin);
  237. $userGroups = $this->groupManager->getUserGroupIds($user);
  238. return !empty(array_intersect($accessibleGroups, $userGroups));
  239. }
  240. /**
  241. * delete all SubAdmins by $user
  242. * @param IUser $user
  243. */
  244. private function post_deleteUser(IUser $user) {
  245. $qb = $this->dbConn->getQueryBuilder();
  246. $qb->delete('group_admin')
  247. ->where($qb->expr()->eq('uid', $qb->createNamedParameter($user->getUID())))
  248. ->execute();
  249. }
  250. /**
  251. * delete all SubAdmins by $group
  252. * @param IGroup $group
  253. */
  254. private function post_deleteGroup(IGroup $group) {
  255. $qb = $this->dbConn->getQueryBuilder();
  256. $qb->delete('group_admin')
  257. ->where($qb->expr()->eq('gid', $qb->createNamedParameter($group->getGID())))
  258. ->execute();
  259. }
  260. }