PageRenderTime 67ms CodeModel.GetById 25ms RepoModel.GetById 1ms app.codeStats 0ms

/include/phpgacl/gacl_api.class.php

https://github.com/radicaldesigns/amp
PHP | 3900 lines | 2602 code | 556 blank | 742 comment | 347 complexity | 50f69ac11b735f2a3080a800abdd3c3b MD5 | raw file
Possible License(s): LGPL-2.1, GPL-2.0, BSD-3-Clause, LGPL-2.0, CC-BY-SA-3.0, AGPL-1.0

Large files files are truncated, but you can click here to view the full file

  1. <?php
  2. /**
  3. * phpGACL - Generic Access Control List
  4. * Copyright (C) 2002,2003 Mike Benoit
  5. *
  6. * This library is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 2.1 of the License, or (at your option) any later version.
  10. *
  11. * This library is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public
  17. * License along with this library; if not, write to the Free Software
  18. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  19. *
  20. * For questions, help, comments, discussion, etc., please join the
  21. * phpGACL mailing list. http://sourceforge.net/mail/?group_id=57103
  22. *
  23. * You may contact the author of phpGACL by e-mail at:
  24. * ipso@snappymail.ca
  25. *
  26. * The latest version of phpGACL can be obtained from:
  27. * http://phpgacl.sourceforge.net/
  28. *
  29. * @package phpGACL
  30. *
  31. */
  32. /*
  33. *
  34. * For examples, see example.php or the Administration interface,
  35. * as it makes use of nearly every API Call.
  36. *
  37. */
  38. /**
  39. * gacl_api Extended API Class
  40. *
  41. * Class gacl_api should be used for applications that must interface directly with
  42. * phpGACL's data structures, objects, and rules.
  43. *
  44. * @package phpGACL
  45. * @author Mike Benoit <ipso@snappymail.ca>
  46. *
  47. */
  48. require_once( 'phpgacl/gacl.class.php');
  49. class gacl_api extends gacl {
  50. /*
  51. *
  52. * Misc helper functions.
  53. *
  54. */
  55. /**
  56. * showarray()
  57. *
  58. * Dump all contents of an array in HTML (kinda)
  59. *
  60. * @param array
  61. *
  62. */
  63. function showarray($array) {
  64. echo "<br><pre>\n";
  65. var_dump($array);
  66. echo "</pre><br>\n";
  67. }
  68. /**
  69. * count_all()
  70. *
  71. * Recursively counts elements in an array and sub-arrays.
  72. *
  73. * This is different from count($arg, COUNT_RECURSIVE)
  74. * in PHP >= 4.2.0, which includes sub-arrays in the count.
  75. *
  76. * @return int The returned count is a count of all scalar elements found.
  77. *
  78. * @param array Array to count
  79. */
  80. function count_all($arg = NULL) {
  81. switch (TRUE) {
  82. case is_scalar($arg):
  83. case is_object($arg):
  84. // single object
  85. return 1;
  86. case is_array($arg):
  87. // call recursively for all elements of $arg
  88. $count = 0;
  89. foreach ($arg as $val) {
  90. $count += $this->count_all($val);
  91. }
  92. return $count;
  93. }
  94. return FALSE;
  95. }
  96. /**
  97. * get_version()
  98. *
  99. * Grabs phpGACL version from the database.
  100. *
  101. * @return string Version of phpGACL
  102. */
  103. function get_version() {
  104. $query = "select value from ".$this->_db_table_prefix."phpgacl where name = 'version'";
  105. $version = $this->db->GetOne($query);
  106. return $version;
  107. }
  108. /**
  109. * get_schema_version()
  110. *
  111. * Grabs phpGACL schema version from the database.
  112. *
  113. * @return string Schema Version
  114. */
  115. function get_schema_version() {
  116. $query = "select value from ".$this->_db_table_prefix."phpgacl where name = 'schema_version'";
  117. $version = $this->db->GetOne($query);
  118. return $version;
  119. }
  120. /*
  121. *
  122. * ACL
  123. *
  124. */
  125. /**
  126. * consolidated_edit_acl()
  127. *
  128. * Add's an ACL but checks to see if it can consolidate it with another one first.
  129. *
  130. * This ONLY works with ACO's and ARO's. Groups, and AXO are excluded.
  131. * As well this function is designed for handling ACLs with return values,
  132. * and consolidating on the return_value, in hopes of keeping the ACL count to a minimum.
  133. *
  134. * A return value of false must _always_ be handled outside this function.
  135. * As this function will remove AROs from ACLs and return false, in most cases
  136. * you will need to a create a completely new ACL on a false return.
  137. *
  138. * @return bool Special boolean return value. See note.
  139. *
  140. * @param string ACO Section Value
  141. * @param string ACO Value
  142. * @param string ARO Section Value
  143. * @param string ARO Value
  144. * @param string Return Value of ACL
  145. */
  146. function consolidated_edit_acl($aco_section_value, $aco_value, $aro_section_value, $aro_value, $return_value) {
  147. $this->debug_text("consolidated_edit_acl(): ACO Section Value: $aco_section_value ACO Value: $aco_value ARO Section Value: $aro_section_value ARO Value: $aro_value Return Value: $return_value");
  148. $acl_ids = array();
  149. if (empty($aco_section_value) ) {
  150. $this->debug_text("consolidated_edit_acl(): ACO Section Value ($aco_section_value) is empty, this is required!");
  151. return false;
  152. }
  153. if (empty($aco_value) ) {
  154. $this->debug_text("consolidated_edit_acl(): ACO Value ($aco_value) is empty, this is required!");
  155. return false;
  156. }
  157. if (empty($aro_section_value) ) {
  158. $this->debug_text("consolidated_edit_acl(): ARO Section Value ($aro_section_value) is empty, this is required!");
  159. return false;
  160. }
  161. if (empty($aro_value) ) {
  162. $this->debug_text("consolidated_edit_acl(): ARO Value ($aro_value) is empty, this is required!");
  163. return false;
  164. }
  165. if (empty($return_value) ) {
  166. $this->debug_text("consolidated_edit_acl(): Return Value ($return_value) is empty, this is required!");
  167. return false;
  168. }
  169. //See if a current ACL exists with the current objects, excluding return value
  170. $current_acl_ids = $this->search_acl($aco_section_value, $aco_value, $aro_section_value, $aro_value, FALSE, FALSE, FALSE, FALSE, FALSE);
  171. //showarray($current_acl_ids);
  172. if (is_array($current_acl_ids)) {
  173. $this->debug_text("add_consolidated_acl(): Found current ACL_IDs, counting ACOs");
  174. foreach ($current_acl_ids as $current_acl_id) {
  175. //Check to make sure these ACLs only have a single ACO mapped to them.
  176. $current_acl_array = &$this->get_acl($current_acl_id);
  177. //showarray($current_acl_array);
  178. $this->debug_text("add_consolidated_acl(): Current Count: ".$this->count_all($current_acl_array['aco'])."");
  179. if ( $this->count_all($current_acl_array['aco']) == 1) {
  180. $this->debug_text("add_consolidated_acl(): ACL ID: $current_acl_id has 1 ACO.");
  181. //Test to see if the return values match, if they do, no need removing or appending ARO. Just return true.
  182. if ($current_acl_array['return_value'] == $return_value) {
  183. $this->debug_text("add_consolidated_acl(): ACL ID: $current_acl_id has 1 ACO, and the same return value. No need to modify.");
  184. return true;
  185. }
  186. $acl_ids[] = $current_acl_id;
  187. }
  188. }
  189. }
  190. //showarray($acl_ids);
  191. $acl_ids_count = count($acl_ids);
  192. //If acl_id's turns up more then one ACL, lets remove the ARO from all of them in hopes to
  193. //eliminate any conflicts.
  194. if (is_array($acl_ids) AND $acl_ids_count > 0) {
  195. $this->debug_text("add_consolidated_acl(): Removing specified ARO from existing ACL.");
  196. foreach ($acl_ids as $acl_id) {
  197. //Remove ARO from current ACLs, so we don't create conflicting ACLs later on.
  198. if (!$this->shift_acl($acl_id, array($aro_section_value => array($aro_value)) ) ) {
  199. $this->debug_text("add_consolidated_acl(): Error removing specified ARO from ACL ID: $acl_id");
  200. return false;
  201. }
  202. }
  203. } else {
  204. $this->debug_text("add_consolidated_acl(): Didn't find any current ACLs with a single ACO. ");
  205. }
  206. //unset($acl_ids);
  207. $acl_ids = array();
  208. unset($acl_ids_count);
  209. //At this point there should be no conflicting ACLs, searching for an existing ACL with the new values.
  210. $new_acl_ids = $this->search_acl($aco_section_value, $aco_value, FALSE, FALSE, NULL, NULL, NULL, NULL, $return_value);
  211. $new_acl_count = count($new_acl_ids);
  212. //showarray($new_acl_ids);
  213. if (is_array($new_acl_ids)) {
  214. $this->debug_text("add_consolidated_acl(): Found new ACL_IDs, counting ACOs");
  215. foreach ($new_acl_ids as $new_acl_id) {
  216. //Check to make sure these ACLs only have a single ACO mapped to them.
  217. $new_acl_array = &$this->get_acl($new_acl_id);
  218. //showarray($new_acl_array);
  219. $this->debug_text("add_consolidated_acl(): New Count: ".$this->count_all($new_acl_array['aco'])."");
  220. if ( $this->count_all($new_acl_array['aco']) == 1) {
  221. $this->debug_text("add_consolidated_acl(): ACL ID: $new_acl_id has 1 ACO, append should be able to take place.");
  222. $acl_ids[] = $new_acl_id;
  223. }
  224. }
  225. }
  226. //showarray($acl_ids);
  227. $acl_ids_count = count($acl_ids);
  228. if (is_array($acl_ids) AND $acl_ids_count == 1) {
  229. $this->debug_text("add_consolidated_acl(): Appending specified ARO to existing ACL.");
  230. $acl_id=$acl_ids[0];
  231. if (!$this->append_acl($acl_id, array($aro_section_value => array($aro_value)) ) ) {
  232. $this->debug_text("add_consolidated_acl(): Error appending specified ARO to ACL ID: $acl_id");
  233. return false;
  234. }
  235. $this->debug_text("add_consolidated_acl(): Hot damn, ACL consolidated!");
  236. return true;
  237. } elseif($acl_ids_count > 1) {
  238. $this->debug_text("add_consolidated_acl(): Found more then one ACL with a single ACO. Possible conflicting ACLs.");
  239. return false;
  240. } elseif ($acl_ids_count == 0) {
  241. $this->debug_text("add_consolidated_acl(): No existing ACLs found, create a new one.");
  242. if (!$this->add_acl( array( $aco_section_value => array($aco_value) ),
  243. array( $aro_section_value => array($aro_value) ),
  244. NULL,
  245. NULL,
  246. NULL,
  247. TRUE,
  248. TRUE,
  249. $return_value,
  250. NULL)
  251. ) {
  252. $this->debug_text("add_consolidated_acl(): Error adding new ACL for ACO Section: $aco_section_value ACO Value: $aco_value Return Value: $return_value");
  253. return false;
  254. }
  255. $this->debug_text("add_consolidated_acl(): ADD_ACL() successfull, returning True.");
  256. return true;
  257. }
  258. $this->debug_text("add_consolidated_acl(): Returning false.");
  259. return false;
  260. }
  261. /**
  262. * search_acl()
  263. *
  264. * Searches for ACL's with specified objects mapped to them.
  265. *
  266. * NULL values are included in the search, if you want to ignore
  267. * for instance aro_groups use FALSE instead of NULL.
  268. *
  269. * @return array containing ACL IDs if search is successful
  270. *
  271. * @param string ACO Section Value
  272. * @param string ACO Value
  273. * @param string ARO Section Value
  274. * @param string ARO Value
  275. * @param string ARO Group Name
  276. * @param string AXO Section Value
  277. * @param string AXO Value
  278. * @param string AXO Group Name
  279. * @param string Return Value
  280. */
  281. function search_acl($aco_section_value=NULL, $aco_value=NULL, $aro_section_value=NULL, $aro_value=NULL, $aro_group_name=NULL, $axo_section_value=NULL, $axo_value=NULL, $axo_group_name=NULL, $return_value=NULL) {
  282. $this->debug_text("search_acl(): aco_section_value: $aco_section_value aco_value: $aco_value, aro_section_value: $aro_section_value, aro_value: $aro_value, aro_group_name: $aro_group_name, axo_section_value: $axo_section_value, axo_value: $axo_value, axo_group_name: $axo_group_name, return_value: $return_value");
  283. $query = '
  284. SELECT a.id
  285. FROM '. $this->_db_table_prefix .'acl a';
  286. $where_query = array();
  287. // ACO
  288. if ($aco_section_value !== FALSE AND $aco_value !== FALSE) {
  289. $query .= '
  290. LEFT JOIN '. $this->_db_table_prefix .'aco_map ac ON a.id=ac.acl_id';
  291. if ($aco_section_value == NULL AND $aco_value == NULL) {
  292. $where_query[] = '(ac.section_value IS NULL AND ac.value IS NULL)';
  293. } else {
  294. $where_query[] = '(ac.section_value='. $this->db->quote($aco_section_value) .' AND ac.value='. $this->db->quote($aco_value) .')';
  295. }
  296. }
  297. // ARO
  298. if ($aro_section_value !== FALSE AND $aro_value !== FALSE) {
  299. $query .= '
  300. LEFT JOIN '. $this->_db_table_prefix .'aro_map ar ON a.id=ar.acl_id';
  301. if ($aro_section_value == NULL AND $aro_value == NULL) {
  302. $where_query[] = '(ar.section_value IS NULL AND ar.value IS NULL)';
  303. } else {
  304. $where_query[] = '(ar.section_value='. $this->db->quote($aro_section_value) .' AND ar.value='. $this->db->quote($aro_value) .')';
  305. }
  306. }
  307. // AXO
  308. if ($axo_section_value !== FALSE AND $axo_value !== FALSE) {
  309. $query .= '
  310. LEFT JOIN '. $this->_db_table_prefix .'axo_map ax ON a.id=ax.acl_id';
  311. if ($axo_section_value == NULL AND $axo_value == NULL) {
  312. $where_query[] = '(ax.section_value IS NULL AND ax.value IS NULL)';
  313. } else {
  314. $where_query[] = '(ax.section_value='. $this->db->quote($axo_section_value) .' AND ax.value='. $this->db->quote($axo_value) .')';
  315. }
  316. }
  317. // ARO Group
  318. if ($aro_group_name !== FALSE) {
  319. $query .= '
  320. LEFT JOIN '. $this->_db_table_prefix .'aro_groups_map arg ON a.id=arg.acl_id
  321. LEFT JOIN '. $this->_db_table_prefix .'aro_groups rg ON arg.group_id=rg.id';
  322. if ($aro_group_name == NULL) {
  323. $where_query[] = '(rg.name IS NULL)';
  324. } else {
  325. $where_query[] = '(rg.name='. $this->db->quote($aro_group_name) .')';
  326. }
  327. }
  328. // AXO Group
  329. if ($axo_group_name !== FALSE) {
  330. $query .= '
  331. LEFT JOIN '. $this->_db_table_prefix .'axo_groups_map axg ON a.id=axg.acl_id
  332. LEFT JOIN '. $this->_db_table_prefix .'axo_groups xg ON axg.group_id=xg.id';
  333. if ($axo_group_name == NULL) {
  334. $where_query[] = '(xg.name IS NULL)';
  335. } else {
  336. $where_query[] = '(xg.name='. $this->db->quote($axo_group_name) .')';
  337. }
  338. }
  339. if ($return_value != FALSE) {
  340. if ($return_value == NULL) {
  341. $where_query[] = '(a.return_value IS NULL)';
  342. } else {
  343. $where_query[] = '(a.return_value='. $this->db->quote($return_value) .')';
  344. }
  345. }
  346. if (count($where_query) > 0) {
  347. $query .= '
  348. WHERE '. implode (' AND ', $where_query);
  349. }
  350. return $this->db->GetCol($query);
  351. }
  352. /**
  353. * append_acl()
  354. *
  355. * Appends objects on to a specific ACL.
  356. *
  357. * @return bool TRUE if successful, FALSE otherwise.
  358. *
  359. * @param int ACL ID #
  360. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  361. * @param array Array of Group IDs
  362. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  363. * @param array Array of Group IDs
  364. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  365. */
  366. function append_acl($acl_id, $aro_array=NULL, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $aco_array=NULL) {
  367. $this->debug_text("append_acl(): ACL_ID: $acl_id");
  368. $update = 0;
  369. if (empty($acl_id)) {
  370. $this->debug_text("append_acl(): No ACL_ID specified! ACL_ID: $acl_id");
  371. return false;
  372. }
  373. //Grab ACL data.
  374. $acl_array = &$this->get_acl($acl_id);
  375. //Append each object type seperately.
  376. if (is_array($aro_array) AND count($aro_array) > 0) {
  377. $this->debug_text("append_acl(): Appending ARO's");
  378. while (list($aro_section_value,$aro_value_array) = @each($aro_array)) {
  379. foreach ($aro_value_array as $aro_value) {
  380. if ( count($acl_array['aro'][$aro_section_value]) != 0 ) {
  381. if (!in_array($aro_value, $acl_array['aro'][$aro_section_value])) {
  382. $this->debug_text("append_acl(): ARO Section Value: $aro_section_value ARO VALUE: $aro_value");
  383. $acl_array['aro'][$aro_section_value][] = $aro_value;
  384. $update=1;
  385. } else {
  386. $this->debug_text("append_acl(): Duplicate ARO, ignoring... ");
  387. }
  388. } else { //Array is empty so add this aro value.
  389. $acl_array['aro'][$aro_section_value][] = $aro_value;
  390. $update = 1;
  391. }
  392. }
  393. }
  394. }
  395. if (is_array($aro_group_ids) AND count($aro_group_ids) > 0) {
  396. $this->debug_text("append_acl(): Appending ARO_GROUP_ID's");
  397. while (list(,$aro_group_id) = @each($aro_group_ids)) {
  398. if (!is_array($acl_array['aro_groups']) OR !in_array($aro_group_id, $acl_array['aro_groups'])) {
  399. $this->debug_text("append_acl(): ARO Group ID: $aro_group_id");
  400. $acl_array['aro_groups'][] = $aro_group_id;
  401. $update = 1;
  402. } else {
  403. $this->debug_text("append_acl(): Duplicate ARO_Group_ID, ignoring... ");
  404. }
  405. }
  406. }
  407. if (is_array($axo_array) AND count($axo_array) > 0) {
  408. $this->debug_text("append_acl(): Appending AXO's");
  409. while (list($axo_section_value,$axo_value_array) = @each($axo_array)) {
  410. foreach ($axo_value_array as $axo_value) {
  411. if (!in_array($axo_value, $acl_array['axo'][$axo_section_value])) {
  412. $this->debug_text("append_acl(): AXO Section Value: $axo_section_value AXO VALUE: $axo_value");
  413. $acl_array['axo'][$axo_section_value][] = $axo_value;
  414. $update = 1;
  415. } else {
  416. $this->debug_text("append_acl(): Duplicate AXO, ignoring... ");
  417. }
  418. }
  419. }
  420. }
  421. if (is_array($axo_group_ids) AND count($axo_group_ids) > 0) {
  422. $this->debug_text("append_acl(): Appending AXO_GROUP_ID's");
  423. while (list(,$axo_group_id) = @each($axo_group_ids)) {
  424. if (!is_array($acl_array['axo_groups']) OR !in_array($axo_group_id, $acl_array['axo_groups'])) {
  425. $this->debug_text("append_acl(): AXO Group ID: $axo_group_id");
  426. $acl_array['axo_groups'][] = $axo_group_id;
  427. $update = 1;
  428. } else {
  429. $this->debug_text("append_acl(): Duplicate ARO_Group_ID, ignoring... ");
  430. }
  431. }
  432. }
  433. if (is_array($aco_array) AND count($aco_array) > 0) {
  434. $this->debug_text("append_acl(): Appending ACO's");
  435. while (list($aco_section_value,$aco_value_array) = @each($aco_array)) {
  436. foreach ($aco_value_array as $aco_value) {
  437. if (!in_array($aco_value, $acl_array['aco'][$aco_section_value])) {
  438. $this->debug_text("append_acl(): ACO Section Value: $aco_section_value ACO VALUE: $aco_value");
  439. $acl_array['aco'][$aco_section_value][] = $aco_value;
  440. $update = 1;
  441. } else {
  442. $this->debug_text("append_acl(): Duplicate ACO, ignoring... ");
  443. }
  444. }
  445. }
  446. }
  447. if ($update == 1) {
  448. $this->debug_text("append_acl(): Update flag set, updating ACL.");
  449. //function edit_acl($acl_id, $aco_array, $aro_array, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $allow=1, $enabled=1, $return_value=NULL, $note=NULL) {
  450. return $this->edit_acl($acl_id, $acl_array['aco'], $acl_array['aro'], $acl_array['aro_groups'], $acl_array['axo'], $acl_array['axo_groups'], $acl_array['allow'], $acl_array['enabled'], $acl_array['return_value'], $acl_array['note']);
  451. }
  452. //Return true if everything is duplicate and no ACL id updated.
  453. $this->debug_text("append_acl(): Update flag not set, NOT updating ACL.");
  454. return true;
  455. }
  456. /**
  457. * shift_acl()
  458. *
  459. * Opposite of append_acl(). Removes objects from a specific ACL. (named after PHP's array_shift())
  460. *
  461. * @return bool TRUE if successful, FALSE otherwise.
  462. *
  463. * @param int ACL ID #
  464. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  465. * @param array Array of Group IDs
  466. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  467. * @param array Array of Group IDs
  468. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  469. */
  470. function shift_acl($acl_id, $aro_array=NULL, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $aco_array=NULL) {
  471. $this->debug_text("shift_acl(): ACL_ID: $acl_id");
  472. $update = 0;
  473. if (empty($acl_id)) {
  474. $this->debug_text("shift_acl(): No ACL_ID specified! ACL_ID: $acl_id");
  475. return false;
  476. }
  477. //Grab ACL data.
  478. $acl_array = &$this->get_acl($acl_id);
  479. //showarray($acl_array);
  480. //Remove each object type seperately.
  481. if (is_array($aro_array) AND count($aro_array) > 0) {
  482. $this->debug_text("shift_acl(): Removing ARO's");
  483. while (list($aro_section_value,$aro_value_array) = @each($aro_array)) {
  484. foreach ($aro_value_array as $aro_value) {
  485. $this->debug_text("shift_acl(): ARO Section Value: $aro_section_value ARO VALUE: $aro_value");
  486. //Only search if aro array contains data.
  487. if ( count($acl_array['aro'][$aro_section_value]) != 0 ) {
  488. $aro_key = array_search($aro_value, $acl_array['aro'][$aro_section_value]);
  489. if ($aro_key !== FALSE) {
  490. $this->debug_text("shift_acl(): Removing ARO. ($aro_key)");
  491. unset($acl_array['aro'][$aro_section_value][$aro_key]);
  492. $update = 1;
  493. } else {
  494. $this->debug_text("shift_acl(): ARO doesn't exist, can't remove it.");
  495. }
  496. }
  497. }
  498. }
  499. }
  500. if (is_array($aro_group_ids) AND count($aro_group_ids) > 0) {
  501. $this->debug_text("shift_acl(): Removing ARO_GROUP_ID's");
  502. while (list(,$aro_group_id) = @each($aro_group_ids)) {
  503. $this->debug_text("shift_acl(): ARO Group ID: $aro_group_id");
  504. $aro_group_key = array_search($aro_group_id, $acl_array['aro_groups']);
  505. if ($aro_group_key !== FALSE) {
  506. $this->debug_text("shift_acl(): Removing ARO Group. ($aro_group_key)");
  507. unset($acl_array['aro_groups'][$aro_group_key]);
  508. $update = 1;
  509. } else {
  510. $this->debug_text("shift_acl(): ARO Group doesn't exist, can't remove it.");
  511. }
  512. }
  513. }
  514. if (is_array($axo_array) AND count($axo_array) > 0) {
  515. $this->debug_text("shift_acl(): Removing AXO's");
  516. while (list($axo_section_value,$axo_value_array) = @each($axo_array)) {
  517. foreach ($axo_value_array as $axo_value) {
  518. $this->debug_text("shift_acl(): AXO Section Value: $axo_section_value AXO VALUE: $axo_value");
  519. $axo_key = array_search($axo_value, $acl_array['axo'][$axo_section_value]);
  520. if ($axo_key !== FALSE) {
  521. $this->debug_text("shift_acl(): Removing AXO. ($axo_key)");
  522. unset($acl_array['axo'][$axo_section_value][$axo_key]);
  523. $update = 1;
  524. } else {
  525. $this->debug_text("shift_acl(): AXO doesn't exist, can't remove it.");
  526. }
  527. }
  528. }
  529. }
  530. if (is_array($axo_group_ids) AND count($axo_group_ids) > 0) {
  531. $this->debug_text("shift_acl(): Removing AXO_GROUP_ID's");
  532. while (list(,$axo_group_id) = @each($axo_group_ids)) {
  533. $this->debug_text("shift_acl(): AXO Group ID: $axo_group_id");
  534. $axo_group_key = array_search($axo_group_id, $acl_array['axo_groups']);
  535. if ($axo_group_key !== FALSE) {
  536. $this->debug_text("shift_acl(): Removing AXO Group. ($axo_group_key)");
  537. unset($acl_array['axo_groups'][$axo_group_key]);
  538. $update = 1;
  539. } else {
  540. $this->debug_text("shift_acl(): AXO Group doesn't exist, can't remove it.");
  541. }
  542. }
  543. }
  544. if (is_array($aco_array) AND count($aco_array) > 0) {
  545. $this->debug_text("shift_acl(): Removing ACO's");
  546. while (list($aco_section_value,$aco_value_array) = @each($aco_array)) {
  547. foreach ($aco_value_array as $aco_value) {
  548. $this->debug_text("shift_acl(): ACO Section Value: $aco_section_value ACO VALUE: $aco_value");
  549. $aco_key = array_search($aco_value, $acl_array['aco'][$aco_section_value]);
  550. if ($aco_key !== FALSE) {
  551. $this->debug_text("shift_acl(): Removing ACO. ($aco_key)");
  552. unset($acl_array['aco'][$aco_section_value][$aco_key]);
  553. $update = 1;
  554. } else {
  555. $this->debug_text("shift_acl(): ACO doesn't exist, can't remove it.");
  556. }
  557. }
  558. }
  559. }
  560. if ($update == 1) {
  561. //We know something was changed, so lets see if no ACO's or no ARO's are left assigned to this ACL, if so, delete the ACL completely.
  562. //$this->showarray($acl_array);
  563. $this->debug_text("shift_acl(): ACOs: ". $this->count_all($acl_array['aco']) ." AROs: ".$this->count_all($acl_array['aro'])."");
  564. if ( $this->count_all($acl_array['aco']) == 0
  565. OR ( $this->count_all($acl_array['aro']) == 0
  566. AND ( $this->count_all($acl_array['axo']) == 0 OR $acl_array['axo'] == FALSE)
  567. AND (count($acl_array['aro_groups']) == 0 OR $acl_array['aro_groups'] == FALSE)
  568. AND (count($acl_array['axo_groups']) == 0 OR $acl_array['axo_groups'] == FALSE)
  569. ) ) {
  570. $this->debug_text("shift_acl(): No ACOs or ( AROs AND AXOs AND ARO Groups AND AXO Groups) left assigned to this ACL (ID: $acl_id), deleting ACL.");
  571. return $this->del_acl($acl_id);
  572. }
  573. $this->debug_text("shift_acl(): Update flag set, updating ACL.");
  574. return $this->edit_acl($acl_id, $acl_array['aco'], $acl_array['aro'], $acl_array['aro_groups'], $acl_array['axo'], $acl_array['axo_groups'], $acl_array['allow'], $acl_array['enabled'], $acl_array['return_value'], $acl_array['note']);
  575. }
  576. //Return true if everything is duplicate and no ACL id updated.
  577. $this->debug_text("shift_acl(): Update flag not set, NOT updating ACL.");
  578. return true;
  579. }
  580. /**
  581. * get_acl()
  582. *
  583. * Grabs ACL data.
  584. *
  585. * @return bool FALSE if not found, or Associative Array with the following items:
  586. *
  587. * - 'aco' => Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  588. * - 'aro' => Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  589. * - 'axo' => Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  590. * - 'aro_groups' => Array of Group IDs
  591. * - 'axo_groups' => Array of Group IDs
  592. * - 'acl_id' => int ACL ID #
  593. * - 'allow' => int Allow flag
  594. * - 'enabled' => int Enabled flag
  595. * - 'return_value' => string Return Value
  596. * - 'note' => string Note
  597. *
  598. * @param int ACL ID #
  599. */
  600. function get_acl($acl_id) {
  601. $this->debug_text("get_acl(): ACL_ID: $acl_id");
  602. if (empty($acl_id)) {
  603. $this->debug_text("get_acl(): No ACL_ID specified! ACL_ID: $acl_id");
  604. return false;
  605. }
  606. //Grab ACL information
  607. $query = "select id, allow, enabled, return_value, note from ".$this->_db_table_prefix."acl where id = ".$acl_id."";
  608. $acl_row = $this->db->GetRow($query);
  609. // return false if not found
  610. if (!$acl_row) {
  611. $this->debug_text("get_acl(): No ACL found for that ID! ACL_ID: $acl_id");
  612. return false;
  613. }
  614. list($retarr['acl_id'], $retarr['allow'], $retarr['enabled'], $retarr['return_value'], $retarr['note']) = $acl_row;
  615. //Grab selected ACO's
  616. $query = "select distinct a.section_value, a.value, c.name, b.name from ".$this->_db_table_prefix."aco_map a, ".$this->_db_table_prefix."aco b, ".$this->_db_table_prefix."aco_sections c
  617. where ( a.section_value=b.section_value AND a.value = b.value) AND b.section_value=c.value AND a.acl_id = $acl_id";
  618. $rs = $this->db->Execute($query);
  619. $rows = $rs->GetRows();
  620. $retarr['aco'] = array();
  621. while (list(,$row) = @each($rows)) {
  622. list($section_value, $value, $section, $aco) = $row;
  623. $this->debug_text("Section Value: $section_value Value: $value Section: $section ACO: $aco");
  624. $retarr['aco'][$section_value][] = $value;
  625. }
  626. //showarray($aco);
  627. //Grab selected ARO's
  628. $query = "select distinct a.section_value, a.value, c.name, b.name from ".$this->_db_table_prefix."aro_map a, ".$this->_db_table_prefix."aro b, ".$this->_db_table_prefix."aro_sections c
  629. where ( a.section_value=b.section_value AND a.value = b.value) AND b.section_value=c.value AND a.acl_id = $acl_id";
  630. $rs = $this->db->Execute($query);
  631. $rows = $rs->GetRows();
  632. $retarr['aro'] = array();
  633. while (list(,$row) = @each($rows)) {
  634. list($section_value, $value, $section, $aro) = $row;
  635. $this->debug_text("Section Value: $section_value Value: $value Section: $section ARO: $aro");
  636. $retarr['aro'][$section_value][] = $value;
  637. }
  638. //showarray($options_aro);
  639. //Grab selected AXO's
  640. $query = "select distinct a.section_value, a.value, c.name, b.name from ".$this->_db_table_prefix."axo_map a, ".$this->_db_table_prefix."axo b, ".$this->_db_table_prefix."axo_sections c
  641. where ( a.section_value=b.section_value AND a.value = b.value) AND b.section_value=c.value AND a.acl_id = $acl_id";
  642. $rs = $this->db->Execute($query);
  643. $rows = $rs->GetRows();
  644. $retarr['axo'] = array();
  645. while (list(,$row) = @each($rows)) {
  646. list($section_value, $value, $section, $axo) = $row;
  647. $this->debug_text("Section Value: $section_value Value: $value Section: $section AXO: $axo");
  648. $retarr['axo'][$section_value][] = $value;
  649. }
  650. //showarray($options_aro);
  651. //Grab selected ARO groups.
  652. $retarr['aro_groups'] = array();
  653. $query = "select distinct group_id from ".$this->_db_table_prefix."aro_groups_map where acl_id = $acl_id";
  654. $retarr['aro_groups'] = $this->db->GetCol($query);
  655. //showarray($selected_groups);
  656. //Grab selected AXO groups.
  657. $retarr['axo_groups'] = array();
  658. $query = "select distinct group_id from ".$this->_db_table_prefix."axo_groups_map where acl_id = $acl_id";
  659. $retarr['axo_groups'] = $this->db->GetCol($query);
  660. //showarray($selected_groups);
  661. return $retarr;
  662. }
  663. /**
  664. * is_conflicting_acl()
  665. *
  666. * Checks for conflicts when adding a specific ACL.
  667. *
  668. * @return bool Returns true if conflict is found.
  669. *
  670. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  671. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  672. * @param array Array of Group IDs
  673. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  674. * @param array Array of Group IDs
  675. * @param array Array of ACL IDs to ignore from the result set.
  676. *
  677. */
  678. function is_conflicting_acl($aco_array, $aro_array, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $ignore_acl_ids=NULL) {
  679. //Check for potential conflicts. Ignore groups, as groups will almost always have "conflicting" ACLs.
  680. //Thats part of inheritance.
  681. if (!is_array($aco_array)) {
  682. $this->debug_text('is_conflicting_acl(): Invalid ACO Array.');
  683. return FALSE;
  684. }
  685. if (!is_array($aro_array)) {
  686. $this->debug_text('is_conflicting_acl(): Invalid ARO Array.');
  687. return FALSE;
  688. }
  689. $query = '
  690. SELECT a.id
  691. FROM '. $this->_db_table_prefix .'acl a
  692. LEFT JOIN '. $this->_db_table_prefix .'aco_map ac ON ac.acl_id=a.id
  693. LEFT JOIN '. $this->_db_table_prefix .'aro_map ar ON ar.acl_id=a.id
  694. LEFT JOIN '. $this->_db_table_prefix .'axo_map ax ON ax.acl_id=a.id
  695. LEFT JOIN '. $this->_db_table_prefix .'axo_groups_map axg ON axg.acl_id=a.id
  696. LEFT JOIN '. $this->_db_table_prefix .'axo_groups xg ON xg.id=axg.group_id
  697. ';
  698. //ACO
  699. foreach ($aco_array as $aco_section_value => $aco_value_array) {
  700. $this->debug_text("is_conflicting_acl(): ACO Section Value: $aco_section_value ACO VALUE: $aco_value_array");
  701. //showarray($aco_array);
  702. if (!is_array($aco_value_array)) {
  703. $this->debug_text('is_conflicting_acl(): Invalid Format for ACO Array item. Skipping...');
  704. continue;
  705. // return TRUE;
  706. }
  707. //Move the below line in to the LEFT JOIN above for PostgreSQL sake.
  708. //'ac1' => 'ac.acl_id=a.id',
  709. $where_query = array(
  710. 'ac2' => '(ac.section_value='. $this->db->quote($aco_section_value) .' AND ac.value IN (\''. implode ('\',\'', $aco_value_array) .'\'))'
  711. );
  712. //ARO
  713. foreach ($aro_array as $aro_section_value => $aro_value_array) {
  714. $this->debug_text("is_conflicting_acl(): ARO Section Value: $aro_section_value ARO VALUE: $aro_value_array");
  715. if (!is_array($aro_value_array))
  716. {
  717. $this->debug_text('is_conflicting_acl(): Invalid Format for ARO Array item. Skipping...');
  718. continue;
  719. // return TRUE;
  720. }
  721. $this->debug_text("is_conflicting_acl(): Search: ACO Section: $aco_section_value ACO Value: $aco_value_array ARO Section: $aro_section_value ARO Value: $aro_value_array");
  722. //Move the below line in to the LEFT JOIN above for PostgreSQL sake.
  723. //$where_query['ar1'] = 'ar.acl_id=a.id';
  724. $where_query['ar2'] = '(ar.section_value='. $this->db->quote($aro_section_value) .' AND ar.value IN (\''. implode ('\',\'', $aro_value_array) .'\'))';
  725. if (is_array($axo_array) AND count($axo_array) > 0) {
  726. foreach ($axo_array as $axo_section_value => $axo_value_array) {
  727. $this->debug_text("is_conflicting_acl(): AXO Section Value: $axo_section_value AXO VALUE: $axo_value_array");
  728. if (!is_array($axo_value_array)) {
  729. $this->debug_text('is_conflicting_acl(): Invalid Format for AXO Array item. Skipping...');
  730. continue;
  731. // return TRUE;
  732. }
  733. $this->debug_text("is_conflicting_acl(): Search: ACO Section: $aco_section_value ACO Value: $aco_value_array ARO Section: $aro_section_value ARO Value: $aro_value_array AXO Section: $axo_section_value AXO Value: $axo_value_array");
  734. //$where_query['ax1'] = 'ax.acl_id=x.id';
  735. $where_query['ax1'] = 'ax.acl_id=a.id';
  736. $where_query['ax2'] = '(ax.section_value='. $this->db->quote($axo_section_value) .' AND ax.value IN (\''. implode ('\',\'', $axo_value_array) .'\'))';
  737. $where = 'WHERE ' . implode(' AND ', $where_query);
  738. $conflict_result = $this->db->GetCol($query . $where);
  739. if (is_array($conflict_result) AND !empty($conflict_result)) {
  740. // showarray($conflict_result);
  741. if (is_array($ignore_acl_ids)) {
  742. $conflict_result = array_diff($conflict_result, $ignore_acl_ids);
  743. }
  744. if (count($conflict_result) > 0) {
  745. $conflicting_acls_str = implode(',', $conflict_result);
  746. $this->debug_text("is_conflicting_acl(): Conflict FOUND!!! ACL_IDS: ($conflicting_acls_str)");
  747. return TRUE;
  748. }
  749. }
  750. }
  751. } else {
  752. $where_query['ax1'] = '(ax.section_value IS NULL AND ax.value IS NULL)';
  753. $where_query['ax2'] = 'xg.name IS NULL';
  754. $where = 'WHERE ' . implode(' AND ', $where_query);
  755. $conflict_result = $this->db->GetCol($query . $where);
  756. if (is_array($conflict_result) AND !empty($conflict_result)) {
  757. // showarray($conflict_result);
  758. if (is_array($ignore_acl_ids)) {
  759. $conflict_result = array_diff($conflict_result, $ignore_acl_ids);
  760. }
  761. if (count($conflict_result) > 0) {
  762. $conflicting_acls_str = implode(',', $conflict_result);
  763. $this->debug_text("is_conflicting_acl(): Conflict FOUND!!! ACL_IDS: ($conflicting_acls_str)");
  764. return TRUE;
  765. }
  766. }
  767. }
  768. }
  769. }
  770. $this->debug_text('is_conflicting_acl(): No conflicting ACL found.');
  771. return FALSE;
  772. }
  773. /**
  774. * add_acl()
  775. *
  776. * Add's an ACL. ACO_IDS, ARO_IDS, GROUP_IDS must all be arrays.
  777. *
  778. * @return bool Return ACL ID of new ACL if successful, FALSE otherewise.
  779. *
  780. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  781. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  782. * @param array Array of Group IDs
  783. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  784. * @param array Array of Group IDs
  785. * @param int Allow flag
  786. * @param int Enabled flag
  787. * @param string Return Value
  788. * @param string Note
  789. * @param string ACL Section Value
  790. * @param int ACL ID # Specific Request
  791. */
  792. function add_acl($aco_array, $aro_array, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $allow=1, $enabled=1, $return_value=NULL, $note=NULL, $section_value=NULL, $acl_id=FALSE ) {
  793. $this->debug_text("add_acl():");
  794. if (count($aco_array) == 0) {
  795. $this->debug_text("Must select at least one Access Control Object");
  796. return false;
  797. }
  798. if (count($aro_array) == 0 AND count($aro_group_ids) == 0) {
  799. $this->debug_text("Must select at least one Access Request Object or Group");
  800. return false;
  801. }
  802. if (empty($allow)) {
  803. $allow=0;
  804. }
  805. if (empty($enabled)) {
  806. $enabled=0;
  807. }
  808. if (!empty($section_value)
  809. AND !$this->get_object_section_section_id(NULL, $section_value, 'ACL')) {
  810. $this->debug_text("add_acl(): Section Value: $section_value DOES NOT exist in the database.");
  811. return false;
  812. }
  813. //Unique the group arrays. Later one we unique ACO/ARO/AXO arrays.
  814. if (is_array($aro_group_ids)) {
  815. $aro_group_ids = array_unique($aro_group_ids);
  816. }
  817. if (is_array($axo_group_ids)) {
  818. $axo_group_ids = array_unique($axo_group_ids);
  819. }
  820. //Check for conflicting ACLs.
  821. if ($this->is_conflicting_acl($aco_array,$aro_array,$aro_group_ids,$axo_array,$axo_group_ids,array($acl_id))) {
  822. $this->debug_text("add_acl(): Detected possible ACL conflict, not adding ACL!");
  823. return false;
  824. }
  825. //Edit ACL if acl_id is set. This is simply if we're being called by edit_acl().
  826. if ($this->get_acl($acl_id) == FALSE) {
  827. if ( empty($section_value) ) {
  828. $section_value='system';
  829. if( !$this->get_object_section_section_id(NULL, $section_value, 'ACL') ) {
  830. // Use the acl section with the lowest order value.
  831. $acl_sections_table = $this->_db_table_prefix .'acl_sections';
  832. $acl_section_order_value = $this->db->GetOne("SELECT min(order_value) from $acl_sections_table");
  833. $query = "
  834. SELECT value
  835. FROM $acl_sections_table
  836. WHERE order_value = $acl_section_order_value
  837. ";
  838. $section_value = $this->db->GetOne($query);
  839. if ( empty($section_value) ) {
  840. $this->debug_text("add_acl(): No valid acl section found.");
  841. return false;
  842. } else {
  843. $this->debug_text("add_acl(): Using default section value: $section_value.");
  844. }
  845. }
  846. }
  847. //ACL not specified, so create acl_id
  848. if (empty($acl_id)) {
  849. //Create ACL row first, so we have the acl_id
  850. $acl_id = $this->db->GenID($this->_db_table_prefix.'acl_seq',10);
  851. //Double check the ACL ID was generated.
  852. if (empty($acl_id)) {
  853. $this->debug_text("add_acl(): ACL_ID generation failed!");
  854. return false;
  855. }
  856. }
  857. //Begin transaction _after_ GenID. Because on the first run, if GenID has to create the sequence,
  858. //the transaction will fail.
  859. $this->db->BeginTrans();
  860. $query = 'INSERT INTO '.$this->_db_table_prefix.'acl (id,section_value,allow,enabled,return_value,note,updated_date) VALUES('. $acl_id .','. $this->db->quote($section_value) .','. $allow .','. $enabled .','. $this->db->quote($return_value) .', '. $this->db->quote($note) .','. time() .')';
  861. $result = $this->db->Execute($query);
  862. } else {
  863. $section_sql = '';
  864. if ( !empty($section_value) ) {
  865. $section_sql = 'section_value='. $this->db->quote ($section_value) .',';
  866. }
  867. $this->db->BeginTrans();
  868. //Update ACL row, and remove all mappings so they can be re-inserted.
  869. $query = '
  870. UPDATE '. $this->_db_table_prefix .'acl
  871. SET ' . $section_sql . '
  872. allow='. $allow .',
  873. enabled='. $enabled .',
  874. return_value='. $this->db->quote($return_value) .',
  875. note='. $this->db->quote($note) .',
  876. updated_date='. time() .'
  877. WHERE id='. $acl_id;
  878. $result = $this->db->Execute($query);
  879. if ($result) {
  880. $this->debug_text("Update completed without error, delete mappings...");
  881. //Delete all mappings so they can be re-inserted.
  882. foreach (array('aco_map', 'aro_map', 'axo_map', 'aro_groups_map', 'axo_groups_map') as $map) {
  883. $query = 'DELETE FROM '. $this->_db_table_prefix . $map .' WHERE acl_id='. $acl_id;
  884. $rs = $this->db->Execute($query);
  885. if (!is_object($rs))
  886. {
  887. $this->debug_db('add_acl');
  888. $this->db->RollBackTrans();
  889. return FALSE;
  890. }
  891. }
  892. }
  893. }
  894. if (!is_object($result)) {
  895. $this->debug_db('add_acl');
  896. $this->db->RollBackTrans();
  897. return false;
  898. }
  899. $this->debug_text("Insert or Update completed without error, insert new mappings.");
  900. // Insert ACO/ARO/AXO mappings
  901. foreach (array('aco', 'aro', 'axo') as $map) {
  902. $map_array = ${$map .'_array'};
  903. if (!is_array ($map_array)) {
  904. continue;
  905. }
  906. foreach ($map_array as $section_value => $value_array) {
  907. $this->debug_text ('Insert: '. strtoupper($map) .' Section Value: '. $section_value .' '. strtoupper($map) .' VALUE: '. $value_array);
  908. // $this->showarray ($aco_value_array);
  909. if (!is_array($value_array)) {
  910. $this->debug_text ('add_acl (): Invalid Format for '. strtoupper ($map) .' Array item. Skipping...');
  911. continue;
  912. // return true;
  913. }
  914. $value_array = array_unique($value_array);
  915. foreach ($value_array as $value) {
  916. $object_id = $this->get_object_id($section_value, $value, $map);
  917. if (empty($object_id))
  918. {
  919. $this->debug_text('add_acl(): '. strtoupper($map) . " Object Section Value: $section_value Value: $value DOES NOT exist in the database. Skipping...");
  920. $this->db->RollBackTrans();
  921. return false;
  922. }
  923. $query = 'INSERT INTO '. $this->_db_table_prefix . $map .'_map (acl_id,section_value,value) VALUES ('. $acl_id .', '. $this->db->quote($section_value) .', '. $this->db->quote($value) .')';
  924. $rs = $this->db->Execute($query);
  925. if (!is_object($rs))
  926. {
  927. $this->debug_db('add_acl');
  928. $this->db->RollBackTrans();
  929. return false;
  930. }
  931. }
  932. }
  933. }
  934. // Insert ARO/AXO GROUP mappings
  935. foreach (array('aro', 'axo') as $map) {
  936. $map_group_ids = ${$map .'_group_ids'};
  937. if (!is_array($map_group_ids)) {
  938. continue;
  939. }
  940. foreach ($map_group_ids as $group_id) {
  941. $this->debug_text ('Insert: '. strtoupper($map) .' GROUP ID: '. $group_id);
  942. $group_data = $this->get_group_data($group_id, $map);
  943. if (empty($group_data)) {
  944. $this->debug_text('add_acl(): '. strtoupper($map) . " Group: $group_id DOES NOT exist in the database. Skipping...");
  945. $this->db->RollBackTrans();
  946. return false;
  947. }
  948. $query = 'INSERT INTO '. $this->_db_table_prefix . $map .'_groups_map (acl_id,group_id) VALUES ('. $acl_id .', '. $group_id .')';
  949. $rs = $this->db->Execute($query);
  950. if (!is_object($rs)) {
  951. $this->debug_db('add_acl');
  952. $this->db->RollBackTrans();
  953. return false;
  954. }
  955. }
  956. }
  957. $this->db->CommitTrans();
  958. if ($this->_caching == TRUE AND $this->_force_cache_expire == TRUE) {
  959. //Expire all cache.
  960. $this->Cache_Lite->clean('default');
  961. }
  962. //Return only the ID in the first row.
  963. return $acl_id;
  964. }
  965. /**
  966. * edit_acl()
  967. *
  968. * Edit's an ACL, ACO_IDS, ARO_IDS, GROUP_IDS must all be arrays.
  969. *
  970. * @return bool Return TRUE if successful, FALSE otherewise.
  971. *
  972. * @param int ACL ID # to edit
  973. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  974. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  975. * @param array Array of Group IDs
  976. * @param array Associative array, item={Section Value}, key={Array of Object Values} i.e. ["<Section Value>" => ["<Value 1>", "<Value 2>", "<Value 3>"], ...]
  977. * @param array Array of Group IDs
  978. * @param int Allow flag
  979. * @param int Enabled flag
  980. * @param string Return Value
  981. * @param string Note
  982. * @param string ACL Section Value
  983. */
  984. function edit_acl($acl_id, $aco_array, $aro_array, $aro_group_ids=NULL, $axo_array=NULL, $axo_group_ids=NULL, $allow=1, $enabled=1, $return_value=NULL, $note=NULL, $section_value=NULL) {
  985. $this->debug_text("edit_acl():");
  986. if (empty($acl_id) ) {
  987. $this->debug_text("edit_acl(): Must specify a single ACL_ID to edit");
  988. return false;
  989. }
  990. if (count($aco_array) == 0) {
  991. $this->debug_text("edit_acl(): Must select at least one Access Control Object");
  992. return false;
  993. }
  994. if (count($aro_array) == 0 AND count($aro_group_ids) == 0) {
  995. $this->debug_text("edit_acl(): Must select at least one Access Request Object or Group");
  996. return false;
  997. }
  998. if (empty($allow)) {
  999. $allow=0;
  1000. }
  1001. if (empty($enabled)) {
  1002. $enabled=0;
  1003. }
  1004. //if ($this->add_acl($aco_array, $aro_array, $group_ids, $allow, $enabled, $acl_id)) {
  1005. if ($this->add_acl($aco_array, $aro_array, $aro_group_ids, $axo_array, $axo_group_ids, $allow, $enabled, $return_value, $note, $section_value, $acl_id)) {
  1006. return true;
  1007. } else {
  1008. $this->debug_text("edit_acl(): error in add_acl()");
  1009. return false;
  1010. }
  1011. }
  1012. /**
  1013. * del_acl()
  1014. *
  1015. * Deletes a given ACL
  1016. *
  1017. * @return bool Returns TRUE if successful, FALSE otherwise.
  1018. *
  1019. * @param int ACL ID # to delete
  1020. */
  1021. function del_acl($acl_id) {
  1022. $this->debug_text("del_acl(): ID: $acl_id");
  1023. if (empty($acl_id) ) {
  1024. $this->debug_text("del_acl(): ACL_ID ($acl_id) is empty, this is required");
  1025. return false;
  1026. }
  1027. $this->db->BeginTrans();
  1028. // Delete all mappings to the ACL first
  1029. foreach (array('aco_map', 'aro_map', 'axo_map', 'aro_groups_map', 'axo_groups_map') as $map) {
  1030. $query = 'DELETE FROM '. $this->_db_table_prefix . $map .' WHERE acl_id='. $acl_id;
  1031. $rs = $this->db->Execute($query);
  1032. if (!is_object($rs)) {
  1033. $this->debug_db('del_acl');
  1034. $this->db->RollBackTrans();
  1035. return false;
  1036. }
  1037. }
  1038. // Delete the ACL
  1039. $query = 'DELETE FROM '. $this->_db_table_prefix .'acl WHERE id='. $acl_id;
  1040. $this->debug_text('delete query: '. $query);
  1041. $rs = $this->db->Execute($query);
  1042. if (!is_object($rs)) {
  1043. $this->debug_db('del_acl');
  1044. $this->db->RollBackTrans();
  1045. return false;
  1046. }
  1047. $this->debug_text("del_acl(): deleted ACL ID: $acl_id");
  1048. $this->db->CommitTrans();
  1049. if ($this->_caching == TRUE AND $this->_force_cache_expire == TRUE) {
  1050. //Expire all cache.
  1051. $this->Cache_Lite->clean('default');
  1052. }
  1053. return TRUE;
  1054. }
  1055. /*
  1056. *
  1057. * Groups
  1058. *
  1059. */
  1060. /**
  1061. * sort_groups()
  1062. *
  1063. * Grabs all the groups from the database doing preliminary grouping by parent
  1064. *
  1065. * @return array Returns 2-Dimensional array: $array[<parent_id>][<group_id>] = <group_name>
  1066. *
  1067. * @param string Group Type, either 'ARO' or 'AXO'
  1068. */
  1069. function sort_groups($group_type='ARO') {
  1070. switch(strtolower(trim($group_type))) {
  1071. case 'axo':
  1072. $table = $this->_db_table_prefix .'axo_groups';
  1073. break;
  1074. default:
  1075. $table = $this->_db_table_prefix .'aro_groups';
  1076. break;
  1077. }
  1078. //Grab all groups from the database.
  1079. $query = 'SELECT id, parent_id, name FROM '. $table .' ORDER BY parent_id, name';
  1080. $rs = $this->db->Execute($query);
  1081. if (!is_object($rs)) {
  1082. $this->debug_db('sort_groups');
  1083. return false;
  1084. }
  1085. /*
  1086. * Save groups in an array sorted by parent. Should be make it easier for later on.
  1087. */
  1088. $sorted_groups = array();
  1089. while ($row = $rs->FetchRow()) {
  1090. $id = &$row[0];
  1091. $parent_id = &$row[1];
  1092. $name = &$row[2];
  1093. $sorted_groups[$parent_id][$id] = $name;
  1094. }
  1095. return $sorted_groups;
  1096. }
  1097. /**
  1098. * format_groups()
  1099. *
  1100. * Takes the array returned by sort_groups() and formats for human
  1101. * consumption. Recursively calls itself to produce the desired output.
  1102. *
  1103. * @return array Array of formatted text, ordered by group id, formatted according to $type
  1104. *
  1105. * @param array Output from gacl_api->sorted_groups($group_type)
  1106. * @param array Output type desired, either 'TEXT', 'HTML', or 'ARRAY'
  1107. * @param int Root of tree to produce
  1108. * @param int Current level of depth
  1109. * @param array Pass the current formatted groups object for appending via recursion.
  1110. */
  1111. function format_groups($sorted_groups, $type='TEXT', $root_id=0, $level=0, $formatted_groups=NULL) {
  1112. if ( !is_array ($sorted_groups) ) {
  1113. return FALSE;
  1114. }
  1115. if ( !is_array ($formatted_groups) ) {
  1116. $formatted_groups = array ();
  1117. }
  1118. //$this->showarray($formatted_groups);
  1119. //while (list($id,$name) = @each($sorted_groups[$root_id])) {
  1120. if (isset($sorted_groups[$root_id])) {
  1121. //$last_id = end( array_keys($sorted_groups[$root_id]));
  1122. //PHP5 compatibility
  1123. $keys = array_keys($sorted_groups[$root_id]);
  1124. $last_id = end($keys);
  1125. unset($keys);
  1126. foreach ($sorted_groups[$root_id] as $id => $name) {
  1127. switch (strtoupper($type)) {
  1128. case 'TEXT':
  1129. /*
  1130. * Formatting optimized for TEXT (combo box) output.
  1131. */
  1132. if ( is_numeric($level) ) {
  1133. $level = str_repeat('&nbsp;&nbsp; ', $level);
  1134. }
  1135. if ( strlen($level) >= 8 ) {
  1136. if ( $id == $last_id ) {
  1137. $spacing = substr($level, 0, -8) .'\'- ';
  1138. $level = substr($level, 0, -8) .'&nbsp;&nbsp; ';
  1139. } else {
  1140. $spacing = substr($level, 0, -8) .'|- ';
  1141. }
  1142. } else {
  1143. $spacing = $level;
  1144. }
  1145. $next = $level .'|&nbsp; ';
  1146. $text = $spacing.$name;
  1147. break;
  1148. case 'HTML':
  1149. /*
  1150. * Formatting optimized for HTML (tables) output.
  1151. */
  1152. $width= $level * 20;
  1153. $spacing = "<img src=\"s.gif\" width=\"$width\">";
  1154. $next = $level + 1;
  1155. $text = $spacing." ".$name;
  1156. break;
  1157. case 'ARRAY':
  1158. $next = $level;
  1159. $text = $name;
  1160. break;
  1161. default:
  1162. return FALSE;
  1163. }
  1164. $formatted_groups[$id] = $text;
  1165. /*
  1166. * Recurse if we can.
  1167. */
  1168. //if (isset($sorted_groups[$id]) AND count($sorted_groups[$id]) > 0) {
  1169. if (isset($sorted_groups[$id]) ) {
  1170. //$this->debug_text("format_groups(): Recursing! Level: $level");
  1171. $formatted_groups = $this->format_groups($sorted_groups, $type, $id, $next, $formatted_groups);
  1172. } else {
  1173. //$this->debug_text("format_groups(): Found last branch!");
  1174. }
  1175. }
  1176. }
  1177. //$this->debug_text("format_groups(): Returning final array.");
  1178. return $formatted_groups;
  1179. }
  1180. /**
  1181. * get_group_id()
  1182. *
  1183. * Gets the group_id given the name or value.
  1184. *
  1185. * Will only return one group id, so if there are duplicate names, it will return false.
  1186. *
  1187. * @return int Returns Group ID if found and Group ID is unique in database, otherwise, returns FALSE
  1188. *
  1189. * @param string Group Value
  1190. * @param string Group Name
  1191. * @param string Group Type, either 'ARO' or 'AXO'
  1192. */
  1193. function get_group_id($value = NULL, $name = NULL, $group_type = 'ARO') {
  1194. $this->debug_text("get_group_id(): Value: $value, Name: $name, Type: $group_type" );
  1195. switch(strtolower(trim($group_type))) {
  1196. case 'axo':
  1197. $table = $this->_db_table_prefix .'axo_groups';
  1198. break;
  1199. default:
  1200. $table = $this->_db_table_prefix .'aro_groups';
  1201. break;
  1202. }
  1203. $name = trim($name);
  1204. $value = trim($value);
  1205. if (empty($name) AND empty($value) ) {
  1206. $this->debug_text("get_group_id(): name and value, at least one is required");
  1207. return false;
  1208. }
  1209. $q

Large files files are truncated, but you can click here to view the full file