Zend_Acl.xml 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464
  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <!-- EN-Revision: 15103 -->
  3. <!-- Reviewed: no -->
  4. <sect1 id="zend.acl.introduction">
  5. <title>Introducción</title>
  6. <para>
  7. <classname>Zend_Acl</classname> provee la implementación de un sistema simple y
  8. flexible de Listas de Control de Acceso (ACL, por sus siglas en
  9. inglés) para la administración de privilegios. En general, una
  10. aplicación puede utilizar las ACL para controlar el acceso a
  11. ciertos objetos protegidos, que son requeridos por otros
  12. objetos.
  13. </para>
  14. <para>
  15. Para los propósitos de esta documentación,
  16. <itemizedlist>
  17. <listitem>
  18. <para>
  19. Un
  20. <emphasis>recurso</emphasis>
  21. es un objeto al cual el acceso esta controlado.
  22. </para>
  23. </listitem>
  24. <listitem>
  25. <para>
  26. Un
  27. <emphasis>rol</emphasis>
  28. es un objeto que puede solicitar acceso a un
  29. recurso.
  30. </para>
  31. </listitem>
  32. </itemizedlist>
  33. En términos generales,
  34. <emphasis>
  35. Los roles solicitan acceso a los recursos
  36. </emphasis>
  37. . Por ejemplo, si una persona solicita acceso a un automóvil,
  38. entonces la persona se convierte en el rol solicitante, y el
  39. automóvil en el recurso, puesto que el acceso al automóvil puede
  40. no estar disponible a cualquiera.
  41. </para>
  42. <para>
  43. A través de la especificación y uso de Listas de Control de
  44. Acceso (ACL), una aplicación puede controlar cómo los objetos
  45. solicitantes (roles) han obtenido acceso a objetos protegidos
  46. (recursos).
  47. </para>
  48. <sect2 id="zend.acl.introduction.resources">
  49. <title>Acerca de los Recursos</title>
  50. <para>
  51. En <classname>Zend_Acl</classname>, crear un recurso es muy sencillo. <classname>Zend_Acl</classname>
  52. proporciona el
  53. <classname>Zend_Acl_Resource_Interface</classname>
  54. para facilitar a los desarrolladores la creación de
  55. recursos. Una clase solo necesita implementar su interfaz,
  56. la cual consiste en un método único,
  57. <code>getResourceId()</code>
  58. , para que <classname>Zend_Acl</classname> considere el objeto como un recurso.
  59. Adicionalmente,
  60. <classname>Zend_Acl_Resource</classname>
  61. es proporcionado por <classname>Zend_Acl</classname> como un recurso básico de
  62. aplicación para que los desarrolladores puedan extenderla hasta
  63. donde lo deseen.
  64. </para>
  65. <para>
  66. <classname>Zend_Acl</classname> provee un estructura de árbol a la cual pueden ser
  67. agregados múltiples recursos (o "Áreas con Controles de
  68. Acceso").Ya que los recursos son almacenados en esta
  69. estructura de árbol, estos pueden ser organizados desde lo
  70. general (hacia la raíz del árbol) a lo específico (hacia las
  71. ramas del árbol). Consultas sobre un recurso específico
  72. buscarán automáticamente, en la jerarquía del
  73. recurso, reglas asignadas a recursos anteriores a los que
  74. el recurso actual haga referencia, permitiendo la herencia
  75. simple de reglas. Por ejemplo, si una regla por defecto se
  76. aplica a cada edificio en una ciudad, uno simplemente
  77. podría asignar la regla a la ciudad, en lugar de asignar la
  78. misma regla a cada edificio. Algunos edificios pueden
  79. necesitar excepciones a la regla, sin embargo, y esto es
  80. fácil de hacer en <classname>Zend_Acl</classname> asignando esta excepción a
  81. cada edificio que necesite una excepción a la regla. Un
  82. recurso sólo puede heredar de un recurso padre, aunque este
  83. recurso padre puede tener a la vez su propio recurso padre,
  84. y así; sucesivamente.
  85. </para>
  86. <para>
  87. <classname>Zend_Acl</classname> también soporta privilegios sobre recursos (ej.
  88. "crear","leer","actualizar", "borrar"), y el desarrollador
  89. puede asignar reglas que afecten o a todos los privilegios o
  90. a privilegios específicos sobre un recurso.
  91. </para>
  92. </sect2>
  93. <sect2 id="zend.acl.introduction.roles">
  94. <title>Acerca de las Reglas</title>
  95. <para>
  96. Al igual que los recursos, la creación de un rol
  97. también es muy simple. <classname>Zend_Acl</classname> proporciona
  98. <classname>Zend_Acl_Role_Interface</classname>
  99. para facilitar a los desarrolladores la creación de
  100. roles. Una clase solo necesita la implementación de su
  101. interfaz, la cual consiste en un método único,
  102. <code>getRoleId()</code>
  103. , para que <classname>Zend_Acl</classname> considere que el objeto es un Rol.
  104. Adicionalmente,
  105. <classname>Zend_Acl_Role</classname>
  106. está incluido con <classname>Zend_Acl</classname> como una implementación principal
  107. del rol para que los desarrolladores la extiendan hasta
  108. donde lo deseen.
  109. </para>
  110. <para>
  111. En <classname>Zend_Acl</classname>, un Rol puede heredar de otro o más roles. Esto
  112. es para soportar herencia de reglas entre roles. Por ejemplo,
  113. un Rol de usuario, como "sally", puede estar bajo uno o más
  114. roles padre, como "editor" y "administrador". El
  115. desarrollador puede asignar reglas a "editor" y
  116. "administrador" por separado, y "sally" puede heredar tales
  117. reglas de ambos, sin tener que asignar reglas directamente a
  118. "sally".
  119. </para>
  120. <para>
  121. Dado que la habilidad de herencia desde múltiples roles es
  122. muy útil, múltiples herencias también introduce cierto grado
  123. de complejidad. El siguiente ejemplo ilustra la condición de
  124. ambiguedad y como <classname>Zend_Acl</classname> soluciona esto.
  125. </para>
  126. <example
  127. id="zend.acl.introduction.roles.example.multiple_inheritance">
  128. <title>Herencia Múlltiple entre Roles</title>
  129. <para>
  130. El siguiente código define tres roles principales - "
  131. <code>invitado</code>
  132. ", "
  133. <code>miembro</code>
  134. ", y "
  135. <code>admin</code>
  136. " - de los cuales otros roles pueden heredar. Entonces,
  137. un rol identificado como "
  138. <code>unUsuario</code>
  139. " es colocado y hereda de los otros tres roles. El orden en
  140. el cual estos roles aparecen en el array
  141. <code>$parents</code>
  142. es importante. Cuando es necesario, <classname>Zend_Acl</classname> busca por
  143. reglas de acceso definidas no solo para el rol
  144. solicitado (aquí, "
  145. <code>unUsuario</code>
  146. "), sino también sobre los roles heredados (aquí, "
  147. <code>invitado</code>
  148. ", "
  149. <code>miembro</code>
  150. ", y "
  151. <code>admin</code>
  152. "):
  153. </para>
  154. <programlisting role="php"><![CDATA[
  155. require_once 'Zend/Acl.php';
  156. $acl = new Zend_Acl();
  157. require_once 'Zend/Acl/Role.php';
  158. $acl->addRole(new Zend_Acl_Role('invitado'))
  159. ->addRole(new Zend_Acl_Role('miembro'))
  160. ->addRole(new Zend_Acl_Role('admin'));
  161. $parents = array('invitado', 'miembro', 'admin');
  162. $acl->addRole(new Zend_Acl_Role('unUsuario'), $parents);
  163. require_once 'Zend/Acl/Resource.php';
  164. $acl->add(new Zend_Acl_Resource('unRecurso'));
  165. $acl->deny('invitado', 'unRecurso');
  166. $acl->allow('miembro', 'unRecurso');
  167. echo $acl->isAllowed('unUsuario', 'unRecurso') ? 'permitido' : 'denegado';
  168. ]]></programlisting>
  169. <para>
  170. Ya que no hay reglas específicamente definidas para
  171. el rol "
  172. <code>unUsuario</code>
  173. " y "
  174. <code>unRecurso</code>
  175. ", <classname>Zend_Acl</classname> debe buscar por reglas que puedan estar
  176. definidas para roles "
  177. <code>unUsuario</code>
  178. " hereda. Primero, el rol "
  179. <code>admin</code>
  180. " es visitado, y no hay regla de acceso definida
  181. para éste. Luego, el rol "
  182. <code>miembro</code>
  183. " es visitado, y <classname>Zend_Acl</classname> encuentra que aquí hay una
  184. regla especificando que "
  185. <code>miembro</code>
  186. " tiene permiso para acceder a "
  187. <code>unRecurso</code>
  188. ".
  189. </para>
  190. <para>
  191. Así, <classname>Zend_Acl</classname> va a seguir examinando las reglas definidas
  192. para otros roles padre, sin embargo, encontraría que "
  193. <code>invitado</code>
  194. " tiene el acceso denegado a "
  195. <code>unRecurso</code>
  196. ". Este hecho introduce una ambigüedad debido a que
  197. ahora "
  198. <code>unUsuario</code>
  199. " está tanto denegado como permitido para acceder a "
  200. <code>unRecurso</code>
  201. ", por la razón de tener un conflicto de reglas
  202. heredadas de diferentes roles padre.
  203. </para>
  204. <para>
  205. <classname>Zend_Acl</classname> resuelve esta ambigüedad completando la
  206. consulta cuando encuentra la primera regla que es
  207. directamente aplicable a la consulta. En este caso, dado
  208. que el rol "
  209. <code>miembro</code>
  210. " es examinado antes que el rol "
  211. <code>invitado</code>
  212. ", el código de ejemplo mostraría "
  213. <code>permitido</code>
  214. ".
  215. </para>
  216. </example>
  217. <note>
  218. <para>
  219. Cuando se especifican múltiples padres para un Rol, se
  220. debe tener en cuenta que el último padre listado es el
  221. primero en ser buscado por reglas aplicables para una
  222. solicitud de autorización.
  223. </para>
  224. </note>
  225. </sect2>
  226. <sect2 id="zend.acl.introduction.creating">
  227. <title>Creando las Listas de Control de Acceso (ACL)</title>
  228. <para>
  229. Una ACL puede representar cualquier grupo de objetos físicos
  230. o virtuales que desee. Para propósitos de demostración,
  231. sin embargo, crearemos un ACL básico para un Sistema de
  232. Administración de Contenido que mantendrá varias escalas de
  233. grupos sobre una amplia variedad de áreas. Para crear un
  234. nuevo objeto ACL, iniciamos la ACL sin parámetros:
  235. </para>
  236. <programlisting role="php"><![CDATA[
  237. require_once 'Zend/Acl.php';
  238. $acl = new Zend_Acl();
  239. ]]></programlisting>
  240. <note>
  241. <para>
  242. Hasta que un desarrollador especifique una regla
  243. "permitido", <classname>Zend_Acl</classname> deniega el acceso a cada privilegio
  244. sobre cada recurso para cada rol.
  245. </para>
  246. </note>
  247. </sect2>
  248. <sect2 id="zend.acl.introduction.role_registry">
  249. <title>Registrando Roles</title>
  250. <para>
  251. El Sistema de Administración de Contenido casi
  252. siempre necesita una jerarquía de permisos para determinar
  253. la capacidad de identificación de sus usuarios. Puede haber
  254. un grupo de 'Invitados' para permitir acceso limitado para
  255. demostraciones, un grupo de 'Personal' para la mayoría de
  256. usuarios del CMS quienes realizan la mayor parte de
  257. operaciones del día a día, un grupo 'Editores' para las
  258. responsabilidades de publicación, revisión, archivo y
  259. eliminación de contenido, y finalmente un grupo
  260. 'Administradores' cuyas tareas pueden incluir todas las de los
  261. otros grupos y también el mantenimiento de la información
  262. delicada, manejo de usuarios, configuración de los datos
  263. básicos y su respaldo/exportación. Este grupo de permisos
  264. pueden ser representados en un registro de roles,
  265. permitiendo a cada grupo heredar los privilegios de los
  266. grupos 'padre', al igual que proporcionando distintos
  267. privilegios solo para su grupo individual. Los permisos pueden
  268. ser expresados como:
  269. </para>
  270. <table
  271. id="zend.acl.introduction.role_registry.table.example_cms_access_controls">
  272. <title>Controles de Acceso para un CMS de ejemplo</title>
  273. <tgroup cols="3">
  274. <thead>
  275. <row>
  276. <entry>Nombre</entry>
  277. <entry>Permisos Individuales</entry>
  278. <entry>Hereda permisos de</entry>
  279. </row>
  280. </thead>
  281. <tbody>
  282. <row>
  283. <entry>Invitado</entry>
  284. <entry>View</entry>
  285. <entry>N/A</entry>
  286. </row>
  287. <row>
  288. <entry>Personal</entry>
  289. <entry>Editar, Enviar, Revisar</entry>
  290. <entry>Invitado</entry>
  291. </row>
  292. <row>
  293. <entry>Editor</entry>
  294. <entry>Publicar, Archivar, Eliminar</entry>
  295. <entry>Personal</entry>
  296. </row>
  297. <row>
  298. <entry>Administrador</entry>
  299. <entry>(Todos los accesos permitidos)</entry>
  300. <entry>N/A</entry>
  301. </row>
  302. </tbody>
  303. </tgroup>
  304. </table>
  305. <para>
  306. Para este ejemplo, se usa
  307. <classname>Zend_Acl_Role</classname>
  308. , pero cualquier objeto que implemente
  309. <classname>Zend_Acl_Role_Interface</classname>
  310. es admisible. Estos grupos pueden ser agregados al registro
  311. de roles de la siguiente manera:
  312. </para>
  313. <programlisting role="php"><![CDATA[
  314. require_once 'Zend/Acl.php';
  315. $acl = new Zend_Acl();
  316. // Agregar grupos al registro de roles usando <classname>Zend_Acl</classname>_Role
  317. require_once 'Zend/Acl/Role.php';
  318. // Invitado no hereda controles de acceso
  319. $rolInvitado = new Zend_Acl_Role('invitado');
  320. $acl->addRole($rolInvitado);
  321. // Personal hereda de Invitado
  322. $acl->addRole(new Zend_Acl_Role('personal'), $rolInvitado);
  323. /* alternativamente, lo de arriba puede ser escrito así:
  324. $rolInvitado = $acl->addRole(new Zend_Acl_Role('personal'), 'invitado');
  325. //*/
  326. // Editor hereda desde personal
  327. $acl->addRole(new Zend_Acl_Role('editor'), 'personal');
  328. // Administrador no hereda controles de acceso
  329. $acl->addRole(new Zend_Acl_Role('administrador'));
  330. ]]></programlisting>
  331. </sect2>
  332. <sect2 id="zend.acl.introduction.defining">
  333. <title>Definiendo Controles de Acceso</title>
  334. <para>
  335. Ahora que la ACL contiene los roles relevantes, se pueden
  336. establecer reglas que definan cómo los roles pueden acceder
  337. a los recursos. Tenga en cuenta que no definiremos ningún
  338. recurso en particular para este ejemplo, el cual está
  339. simplificado para ilustrar que las reglas se aplican a todos
  340. los recursos. <classname>Zend_Acl</classname> proporciona una forma práctica por la
  341. cual las reglas solo necesitan ser asignadas de lo general a
  342. lo especifico, minimizando el número de reglas necesarias,
  343. porque los recursos y roles heredan reglas que están
  344. definidas en sus padres.
  345. </para>
  346. <para>
  347. Consecuentemente, podemos definir un grupo razonablemente
  348. complejo de reglas con un mínimo de código. Para aplicar
  349. estos permisos básicos como están definidos arriba:
  350. </para>
  351. <programlisting role="php"><![CDATA[
  352. require_once 'Zend/Acl.php';
  353. $acl = new Zend_Acl();
  354. require_once 'Zend/Acl/Role.php';
  355. $rolInvitado = new Zend_Acl_Role('invitado');
  356. $acl->addRole($rolInvitado);
  357. $acl->addRole(new Zend_Acl_Role('personal'), $rolInvitado);
  358. $acl->addRole(new Zend_Acl_Role('editor'), 'personal');
  359. $acl->addRole(new Zend_Acl_Role('administrador'));
  360. // Invitado solo puede ver el contenido
  361. $acl->allow($rolInvitado, null, 'ver');
  362. /* Lo de arriba puede ser escrito de la siguiente forma alternativa:
  363. $acl->allow('invitado', null, 'ver');
  364. //*/
  365. // Personal hereda el privilegio de ver de invitado, pero también necesita privilegios adicionales
  366. $acl->allow('personal', null, array('editar', 'enviar', 'revisar'));
  367. // Editor hereda los privilegios de ver, editar, enviar, y revisar de personal,
  368. // pero también necesita privilegios adicionales
  369. $acl->allow('editor', null, array('publicar', 'archivar', 'eliminar'));
  370. // Administrador no hereda nada, pero tiene todos los privilegios permitidos
  371. $acl->allow('administrador');
  372. ]]></programlisting>
  373. <para>
  374. El valor
  375. <code>null</code>
  376. en las llamadas de
  377. <code>allow()</code>
  378. es usado para indicar que las reglas de permiso se aplican a
  379. todos los recursos.
  380. </para>
  381. </sect2>
  382. <sect2 id="zend.acl.introduction.querying">
  383. <title>Consultando la ACL</title>
  384. <para>
  385. Ahora tenemos una ACL flexible que puede ser usada para
  386. determinar qué solicitantes tienen permisos para realizar
  387. funciones a través de la aplicación web. Ejecutar
  388. consultas es la forma más simple de usar el método
  389. <code>isAllowed()</code>
  390. :
  391. </para>
  392. <programlisting role="php"><![CDATA[
  393. echo $acl->isAllowed('invitado', null, 'ver') ?
  394. "permitido" : "denegado"; // permitido
  395. echo $acl->isAllowed('personal', null, 'publicar') ?
  396. "permitido" : "denegado"; // denegado
  397. echo $acl->isAllowed('personal', null, 'revisar') ?
  398. "permitido" : "denegado"; // permitido
  399. echo $acl->isAllowed('editor', null, 'ver') ?
  400. "permitido" : "denegado"; // permitido debido a la herencia de invitado
  401. echo $acl->isAllowed('editor', null, 'actualizar') ?
  402. "permitido" : "denegado"; // denegado debido a que no hay regla de permiso para 'actualizar'
  403. echo $acl->isAllowed('administrador', null, 'ver') ?
  404. "permitido" : "denegado"; // permitido porque administrador tiene permitidos todos los privilegios
  405. echo $acl->isAllowed('administrador') ?
  406. "permitido" : "denegado"; // permitido porque administrador tiene permitidos todos los privilegios
  407. echo $acl->isAllowed('administrador', null, 'actualizar') ?
  408. "permitido" : "denegado"; // permitido porque administrador tiene permitidos todos los privilegios
  409. ]]></programlisting>
  410. </sect2>
  411. </sect1>
  412. <!--
  413. vim:se ts=4 sw=4 et:
  414. -->