2008-11-10 9 views
5

Estoy trabajando en una aplicación web de Rails, y actualmente la utilizan unos 20 usuarios.¿La mejor manera de implementar la autorización detallada para una aplicación web?

Algunas partes de la aplicación solo son accesibles para algunos usuarios, por lo que ya contamos con un marco de autorización básico, que implementé utilizando el complemento acts_as_authenticated.

Los privilegios de los usuarios dependen del departamento en el que trabajan, por ejemplo, la administración tiene acceso a todas las partes de la aplicación, mientras que la contabilidad solo tiene acceso a las partes relacionadas con la contabilidad y las ventas solo tienen acceso a ventas partes, etc.

Por otro lado, los usuarios ven los enlaces a acciones para las cuales tienen privilegios insuficientes. Por ejemplo, aquellos en el departamento de ventas ven un enlace a los registros financieros en el menú principal, pero cuando hacen clic en él, no pasa nada. Esto es así porque AFAIK no hay una manera eficiente de consultar privilegios de usuario usando acts_as_authenticated.

Quiero cambiar esto de dos maneras:

  1. me gusta mostrar a la autorización de grano fino. Actualmente, la autorización se realiza a nivel de controlador. Quiero hacer esto a nivel de acción o modelo. Por ejemplo, quiero que aquellos en el departamento de ventas puedan crear y actualizar pagos, pero no eliminarlos.

  2. Quiero poder consultar los privilegios de usuario de manera eficiente, así puedo eliminar enlaces innecesarios (y confusos) de la interfaz.

¿Cuál cree que es la forma más elegante de implementar esto?

Las respuestas específicas de los raíles no son necesarias, solo quiero saber cómo esto debe implementarse en una aplicación basada en datos.

Por último, aquí es cómo se implementa actualmente:

def authorized? 
    current_user.role.foo? or current_user.role.bar? 
end 

Y aquí está mi idea inicial, que creo que no es la mejor manera de resolver esto:

 
+------------+------------+---------+ 
| department | controller | action | 
+------------+------------+---------+ 
| accounting | payments | index | 
| accounting | payments | new  | 
| accounting | payments | create | 
| accounting | payments | edit | 
| accounting | payments | update | 
| accounting | payments | destroy | 
| sales  | payments | new  | 
| sales  | payments | create | 
| sales  | payments | edit | 
| sales  | payments | update | 
+------------+------------+---------+ 

o

 
+------------+----------+-------+--------+------+--------+--------+ 
| department | model | list | create | read | update | delete | 
+------------+----------+-------+--------+------+--------+--------+ 
| accounting | payments | TRUE | TRUE | TRUE | TRUE | TRUE | 
| sales  | payments | FALSE | TRUE | TRUE | TRUE | FALSE | 
+------------+----------+-------+--------+------+--------+--------+ 

Respuesta

3

El concepto básico de autorización, tal como lo entiendo, es un rol. papel puede expresar varias cosas:

  1. relación de un usuario al sistema en su conjunto
  2. relación de un usuario a algún tipo de entidades (por ejemplo, para (por ejemplo, ser un administrador del sistema.). ser un moderador de comentarios)
  3. relación de un usuario con una entidad particular (por ejemplo, ser propietario de algún recurso)
  4. alguna otra relación compleja (por ejemplo, ser amigo de un usuario que es propietario de algún recurso)
  5. ese usuario tiene algún atributo (s) o responde a algún mensaje en algún particula r camino (ej. para ser un adolescente)

Un sistema de autorizaciones muy detallado debería permitirle definir el rol para un usuario basado en cualquiera de los criterios mencionados anteriormente. Además, debería permitirle establecer más de un rol para un usuario. (Las formas más simples de los complementos de autorización para Rails generalmente le permiten definir solo el primer tipo de roles y establecer un solo rol para un usuario).

La otra parte de authoriation es un mecanismo que decide qué parte del código ejecutar (o no para ejecutar) en función del hecho si un usuario se ajusta a algún rol (conjunto de roles) o no. Para aplicar este mecanismo, debemos encontrar los puntos donde debe tener lugar la autorización y seleccionar los roles para los cuales el código debe o no ejecutarse. La forma en que me funciona en Rails es definir roles en el modelo y dejar el mecanismo de autorización (establecer roles permitidos para partes de código que quiero autorizar y preguntar si el usuario actual tiene el rol permitido para ejecutar la pieza) completamente para controladores/vistas.

Para esto utilizo rails-authorization-plugin que tiene todas las posibilidades que acabo de mencionar incorporadas (varios tipos de roles, muchos roles para un usuario, autorización en el controlador y nivel de vista).

0

puede que necesite introducir la noción de 'puntos de función' o 'características' en su modelo como puntos de control para acc ess; una 'característica' puede tener una 'función principal' opcional para formar una jerarquía. Puede decidir qué es y qué no es una función y verificar los permisos de forma programática. Esto también debería permitirle verificar el acceso a las características antes de dibujar un menú, para que los usuarios nunca vean enlaces a páginas a las que no tienen acceso.

una situación/solución similar se describe here

0

de sus dos propuestas, la primera opción parece un poco mejor, ya que le permite añadir acciones que pueden no ser las acciones a nivel de modelo. Supongo que se encontrará con un caso en el que el segundo modelo no hace lo suficiente, y deberá cambiar el esquema o comenzar a rociar la lógica de permisos en su aplicación (ej."Los usuarios que no 'crean' de acceso también no se puede ejecutar el método xxx")

Creo que la razón la solución no parece muy seco es que no hay repetición:

  1. En los nombres de departamento, y
  2. En
  3. las capacidades del departamento

con respecto a # 1, que tendría sentido para crear una tabla de departamentos y dar a cada departamento de una identificación.

Con respecto al n. ° 2, estoy de acuerdo con el primer comentario. Probablemente pueda agrupar los diversos controladores y acciones en grupos funcionales, y luego establecer una relación muchos a muchos (tabla de asignación) entre usuarios y funciones. Las funciones tendrían entonces una relación uno a muchos con qué acciones/controladores permitían. Esto le permitiría, con una repetición mínima, decir cosas como "la contabilidad y las ventas deberían poder leer todas las tablas financieras".

+0

Ya tengo una tabla de departamentos y una tabla users_departments. Simplifiqué la tabla de ejemplos para abreviar. –

Cuestiones relacionadas