Flask

Flask

Tutorial Flask: Autorización con Flask-Principal

Flask Principal: Aprende a gestionar roles y permisos en Flask para una autorización y control de acceso efectivo en tu aplicación.

Aprende Flask GRATIS y certifícate

Creación y asignación de roles y permisos

Para implementar un sistema de autorización robusto en Flask, es fundamental gestionar correctamente los roles y permisos de los usuarios. La extensión Flask-Principal proporciona una forma estructurada de definir y asignar estos roles y permisos dentro de tu aplicación.

Primero, instala Flask-Principal utilizando pip:

pip install Flask-Principal

A continuación, integra Flask-Principal en tu aplicación Flask:

from flask import Flask
from flask_principal import Principal

app = Flask(__name__)

# Inicializa la extensión Principal
principals = Principal(app)

Con Flask-Principal configurado, puedes definir necesidades y permisos. Una necesidad representa una condición que debe cumplirse, como pertenecer a un rol específico. Los permisos agrupan estas necesidades.

Por ejemplo, define roles como necesidades:

from flask_principal import RoleNeed, Permission

# Define necesidades de rol
admin_need = RoleNeed('admin')
editor_need = RoleNeed('editor')

# Define permisos basados en roles
admin_permission = Permission(admin_need)
editor_permission = Permission(editor_need)

Ahora, es esencial asignar estos roles a los usuarios adecuados. Supongamos que utilizas Flask-Login para manejar la autenticación y tus usuarios tienen un atributo que indica su rol.

Configura la identidad del usuario y asigna los roles correspondientes:

from flask_login import current_user
from flask_principal import identity_loaded, UserNeed, Identity, AnonymousIdentity

@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    identity.user = current_user

    # Asigna una necesidad de usuario único
    if hasattr(current_user, 'id'):
        identity.provides.add(UserNeed(current_user.id))

    # Asigna roles basados en atributos del usuario
    if current_user.role == 'admin':
        identity.provides.add(RoleNeed('admin'))
    elif current_user.role == 'editor':
        identity.provides.add(RoleNeed('editor'))

En este ejemplo, la señal identity_loaded se utiliza para agregar necesidades a la identidad del usuario después de que se haya cargado. La función verifica el rol del usuario y asigna el RoleNeed correspondiente.

Con los roles y permisos definidos y asignados, puedes proteger las vistas utilizando el decorador @requires proporcionado por Flask-Principal:

from flask_principal import PermissionDenied
from flask import abort

@app.route('/admin')
@admin_permission.require()
def admin_dashboard():
    return "Bienvenido al panel de administración"

@app.route('/edit')
@editor_permission.require()
def edit_article():
    return "Edita el artículo aquí"

# Manejo de errores de permiso
@app.errorhandler(PermissionDenied)
def handle_permission_denied(error):
    abort(403)

Este decorador verifica que el usuario tenga el permiso necesario antes de acceder a la vista. Si el usuario no cumple con el permiso, se genera una excepción PermissionDenied, que manejamos devolviendo un error 403.

Para casos en los que múltiples roles puedan acceder a una vista, puedes combinar permisos:

# Permiso que permite acceso a administradores y editores
admin_or_editor = admin_permission.union(editor_permission)

@app.route('/dashboard')
@admin_or_editor.require()
def dashboard():
    return "Bienvenido al panel de control"

# Permiso que requiere ser administrador y editor simultáneamente
admin_and_editor = admin_permission & editor_permission

@app.route('/special')
@admin_and_editor.require()
def special_section():
    return "Acceso a sección especial"

La unión de permisos con .union() o el operador | permite que usuarios con cualquiera de los roles accedan a la vista, mientras que la intersección con & exige que el usuario tenga ambos roles.

Es posible también definir permisos más granulares utilizando necesidades personalizadas. Por ejemplo, si quieres controlar el acceso a recursos específicos:

from flask_principal import Need

class ArticleNeed(Need):
    def __init__(self, method, value):
        super().__init__('article', "%s:%s" % (method, value))

# Define una función para crear permisos de artículo
def article_permission(method, article_id):
    return Permission(ArticleNeed(method, article_id))

# Asigna necesidades al usuario
@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    # ... código previo ...
    for article in current_user.articles:
        identity.provides.add(ArticleNeed('edit', article.id))

# Protege una vista con el permiso de editar un artículo específico
@app.route('/article/<int:article_id>/edit')
def edit_specific_article(article_id):
    perm = article_permission('edit', article_id)
    if perm.can():
        return f"Editando artículo {article_id}"
    else:
        abort(403)

En este caso, se crean necesidades específicas para cada artículo que el usuario puede editar, y se verifica el permiso dinámicamente en la vista.

Mecanismos de identificación (Identity)

En Flask-Principal, la gestión de la identidad es clave para implementar un sistema de autorización eficaz. La identidad representa la información relevante sobre el usuario que interactúa con la aplicación, incluyendo sus roles, permisos y otras características de seguridad. Mediante el uso de identidades, puedes asociar necesidades específicas a cada usuario y controlar el acceso a distintas partes de tu aplicación.

Concepto de identidad en Flask-Principal

La identidad en Flask-Principal es una abstracción que encapsula las necesidades (needs) que un usuario provee. Estas necesidades pueden ser roles, permisos o cualquier otra característica que definas. La identidad se crea y se actualiza utilizando señales (signals), permitiendo una integración flexible con otros sistemas de autenticación como Flask-Login.

Señal identity_changed

Cuando la identidad de un usuario cambia, es fundamental notificar a Flask-Principal para que actualice el estado interno de la aplicación. Esto se logra mediante la emisión de la señal identity_changed. Por ejemplo, al iniciar sesión un usuario:

from flask import current_app, redirect, url_for
from flask_login import login_user
from flask_principal import identity_changed, Identity

@app.route('/login', methods=['POST'])
def login():
    # Autenticar al usuario (omitir detalles de autenticación)
    user = authenticate_user()
    if user:
        # Iniciar sesión con Flask-Login
        login_user(user)
        # Enviar señal de cambio de identidad
        identity_changed.send(
            current_app._get_current_object(),
            identity=Identity(user.id))
        return redirect(url_for('dashboard'))
    else:
        return "Autenticación fallida", 401

En este ejemplo, después de autenticar al usuario y establecer la sesión con Flask-Login, se emite la señal identity_changed pasando una nueva instancia de Identity con el identificador del usuario. Esto permite que Flask-Principal actualice las necesidades y permisos asociados a esa identidad.

Señal identity_loaded

Una vez que la identidad ha cambiado, es necesario cargar las necesidades y permisos específicos del usuario. La señal identity_loaded se utiliza para agregar esta información a la identidad actual:

from flask_login import current_user
from flask_principal import identity_loaded, UserNeed, RoleNeed

@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    # Establecer el usuario actual en la identidad
    identity.user = current_user

    # Agregar necesidad de usuario (UserNeed)
    if hasattr(current_user, 'id'):
        identity.provides.add(UserNeed(current_user.id))

    # Agregar necesidades de rol (RoleNeed)
    if hasattr(current_user, 'roles'):
        for role in current_user.roles:
            identity.provides.add(RoleNeed(role.name))

La función on_identity_loaded se conecta a la señal y añade las necesidades correspondientes a la identidad. Se agregan necesidades de usuario y de rol según los atributos del current_user. Estas necesidades serán utilizadas posteriormente para verificar los permisos en las vistas protegidas.

Manejo de identidades anónimas

Cuando un usuario no está autenticado, Flask-Principal asigna una identidad anónima. Puedes personalizar las necesidades de la identidad anónima si deseas otorgar ciertos permisos a usuarios no autenticados:

from flask_principal import AnonymousIdentity

@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    if isinstance(identity, AnonymousIdentity):
        # Agregar necesidad de rol para usuarios anónimos
        identity.provides.add(RoleNeed('anonymous'))

En este caso, los usuarios anónimos reciben el rol 'anonymous', lo que permite controlar el acceso a determinadas partes de la aplicación para usuarios no autenticados mediante permisos asociados a ese rol.

Cambio de identidad al cerrar sesión

Es igualmente importante actualizar la identidad cuando un usuario cierra sesión. Al hacerlo, debes restablecer la identidad a una AnonymousIdentity:

from flask import current_app, redirect, url_for
from flask_login import logout_user
from flask_principal import identity_changed, AnonymousIdentity

@app.route('/logout')
def logout():
    # Cerrar sesión con Flask-Login
    logout_user()
    # Enviar señal de cambio de identidad a anónima
    identity_changed.send(
        current_app._get_current_object(),
        identity=AnonymousIdentity())
    return redirect(url_for('index'))

Al emitir la señal identity_changed con una AnonymousIdentity, te aseguras de que todas las necesidades y permisos asociados al usuario anterior se eliminen, y que el estado de seguridad de la aplicación refleje correctamente que ya no hay un usuario autenticado.

Acceso a la identidad en las vistas

Puedes acceder a la identidad actual en tus vistas para obtener información sobre el usuario o sus necesidades:

from flask_principal import identity

@app.route('/profile')
def profile():
    # Obtener las necesidades de la identidad actual
    user_needs = identity.provides
    return f"Necesidades actuales: {user_needs}"

Este acceso puede ser útil para depuración o para personalizar el contenido de las páginas según los permisos del usuario.

Integración con sistemas de autenticación

Flask-Principal está diseñado para integrarse fácilmente con sistemas de autenticación como Flask-Login. Al utilizar current_user proporcionado por Flask-Login, puedes sincronizar la identidad de Flask-Principal con la sesión de usuario:

from flask_login import current_user
from flask_principal import Identity, AnonymousIdentity, identity_changed

# Al iniciar sesión
identity_changed.send(
    current_app._get_current_object(),
    identity=Identity(current_user.id))

# Al cerrar sesión
identity_changed.send(
    current_app._get_current_object(),
    identity=AnonymousIdentity())

Esta integración asegura una experiencia coherente para el usuario y facilita la gestión de autorización en tu aplicación.

Suplantación de identidad (Impersonation)

En ciertos casos administrativos, puede ser necesario que un usuario con permisos elevados suplante la identidad de otro usuario. Esto puede lograrse cambiando temporalmente la identidad:

from flask_principal import identity_changed, Identity

@app.route('/impersonate/<int:user_id>')
@admin_permission.require()
def impersonate(user_id):
    # Cambiar identidad a la del usuario especificado
    identity_changed.send(
        current_app._get_current_object(),
        identity=Identity(user_id))
    return redirect(url_for('dashboard'))

Es importante manejar esta funcionalidad con cuidado y asegurar que solo usuarios autorizados puedan realizar la suplantación, aplicando los permisos necesarios con Flask-Principal.

Revocación y actualización de necesidades

Si las necesidades o permisos de un usuario cambian durante su sesión (por ejemplo, si se modifica su rol), es necesario actualizar su identidad para reflejar estos cambios:

# Después de cambiar el rol del usuario
@some_event_handler
def update_user_role(user):
    # Actualizar roles en la base de datos
    user.role = 'new_role'
    db.session.commit()

    # Emitir señal para actualizar la identidad
    identity_changed.send(
        current_app._get_current_object(),
        identity=Identity(user.id))

Al volver a emitir identity_changed, la señal identity_loaded se activará de nuevo, recargando las necesidades y permisos del usuario.

Mejoras avanzadas de identidad

Flask-Principal permite personalizar aún más el sistema de identidades mediante la creación de necesidades y permisos personalizados. Puedes definir tus propias clases de necesidad para cubrir casos específicos en tu aplicación:

from flask_principal import Need

class ActionNeed(Need):
    def __init__(self, method, value):
        super().__init__(method, value)

# Uso de necesidades personalizadas
@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    # Agregar necesidades personalizadas
    identity.provides.add(ActionNeed('upload', 'images'))

Esto te permite crear un sistema de permisos más granular y adaptado a tus requisitos particulares.

Protección de vistas mediante permisos

Una vez establecidos los roles y las identidades con Flask-Principal, es fundamental implementar mecanismos para proteger las vistas de la aplicación. Esto asegura que solo los usuarios autorizados puedan acceder a ciertas funcionalidades o recursos, reforzando la seguridad y el control de acceso.

Para proteger las vistas, Flask-Principal proporciona el decorador @requires, que verifica que el usuario actual cumpla con los permisos necesarios antes de acceder a la vista. Por ejemplo, si deseas que solo los usuarios con el rol de administrador puedan acceder a una ruta específica, puedes hacerlo de la siguiente manera:

from flask import abort
from flask_principal import PermissionDenied

# Definir el permiso de administrador (definido previamente)
admin_permission = Permission(RoleNeed('admin'))

@app.route('/admin')
@admin_permission.require()
def admin_panel():
    return "Bienvenido al panel de administración"

# Manejador de errores de permiso
@app.errorhandler(PermissionDenied)
def handle_permission_denied(error):
    return abort(403)

En este ejemplo, el decorador @admin_permission.require() garantiza que solo los usuarios con el permiso admin_permission puedan acceder a la ruta /admin. Si el usuario no tiene dicho permiso, se lanza una excepción PermissionDenied, que manejamos devolviendo un error 403.

Es posible combinar permisos para proteger vistas que requieran múltiples roles o que permitan el acceso a usuarios con diferentes perfiles. Flask-Principal permite combinar permisos utilizando operaciones lógicas, como la unión y la intersección.

La unión de permisos permite el acceso si el usuario cumple con al menos uno de los permisos especificados. Puedes utilizar el método .union() o el operador |:

# Permisos para administradores y editores
admin_permission = Permission(RoleNeed('admin'))
editor_permission = Permission(RoleNeed('editor'))

admin_or_editor = admin_permission.union(editor_permission)
# Equivalente: admin_or_editor = admin_permission | editor_permission

@app.route('/dashboard')
@admin_or_editor.require()
def dashboard():
    return "Bienvenido al panel de control"

En este caso, tanto los usuarios con rol de administrador como de editor pueden acceder a la ruta /dashboard.

Por otro lado, la intersección de permisos exige que el usuario cumpla con todos los permisos especificados:

# Permiso que requiere ser administrador y editor simultáneamente
admin_and_editor = admin_permission & editor_permission

@app.route('/settings')
@admin_and_editor.require()
def settings():
    return "Configuración avanzada del sistema"

Aquí, solo los usuarios que tienen ambos roles pueden acceder a la vista /settings.

Para escenarios donde es necesario proteger vistas basándose en atributos dinámicos, como el propietario de un recurso, puedes crear permisos personalizados en tiempo de ejecución. Por ejemplo, para permitir que los usuarios editen solo sus propios posts:

from flask_principal import ItemNeed, Permission

def user_can_edit_post(post_id):
    # Crear una necesidad específica para el post
    edit_post_need = ItemNeed('edit', post_id)
    edit_post_permission = Permission(edit_post_need)
    return edit_post_permission

@app.route('/posts/<int:post_id>/edit')
def edit_post(post_id):
    # Obtener el permiso para el post actual
    permission = user_can_edit_post(post_id)
    if permission.can():
        return f"Editando el post {post_id}"
    else:
        abort(403)

Para que este enfoque funcione, debes asignar las necesidades correspondientes a la identidad del usuario:

@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    # Asignar necesidades de edición de posts al usuario
    if hasattr(current_user, 'posts'):
        for post in current_user.posts:
            identity.provides.add(ItemNeed('edit', post.id))

De esta manera, cada usuario tiene permisos para editar solo los posts que les pertenecen, garantizando un control de acceso preciso y personalizado.

También es posible utilizar funciones personalizadas para verificar permisos en las vistas. Puedes crear un decorador que generalice la comprobación de permisos:

def permission_required(permission):
    def decorator(f):
        def decorated_function(*args, **kwargs):
            if not permission.can():
                abort(403)
            return f(*args, **kwargs)
        return decorated_function
    return decorator

@app.route('/reports')
@permission_required(admin_permission)
def view_reports():
    return "Accediendo a los informes confidenciales"

Esta técnica te permite reutilizar la lógica de autorización y aplicarla de manera consistente en diferentes partes de la aplicación, mejorando la modularidad y legibilidad del código.

Además de proteger las vistas en el lado del servidor, es recomendable gestionar los permisos en las plantillas Jinja2 para mejorar la experiencia del usuario. Puedes mostrar u ocultar elementos de la interfaz según los permisos del usuario:

{% if admin_permission.can() %}
    <a href="{{ url_for('admin_panel') }}">Panel de Administración</a>
{% endif %}

Para que los permisos estén disponibles en las plantillas, debes inyectarlos en el contexto de la aplicación:

@app.context_processor
def inject_permissions():
    return dict(admin_permission=admin_permission)

Esto permite que las plantillas accedan a los permisos y personalicen la interfaz de manera dinámica, mostrando solo las opciones relevantes para cada usuario.

Es importante también manejar adecuadamente los errores de permiso para proporcionar retroalimentación clara al usuario. Al capturar las excepciones PermissionDenied, puedes redirigir al usuario a una página informativa o mostrar un mensaje amigable:

@app.errorhandler(PermissionDenied)
def handle_permission_denied(error):
    return render_template('403.html'), 403

En el archivo 403.html, puedes incluir información sobre la falta de autorización y opciones para volver a la página de inicio o solicitar acceso, mejorando la usabilidad de tu aplicación.

Para mantener la seguridad y coherencia en tu aplicación, es esencial actualizar la identidad del usuario si sus permisos cambian durante la sesión. Puedes emitir la señal identity_changed para refrescar los permisos:

from flask_principal import identity_changed, Identity

def update_user_permissions(user):
    # Actualizar permisos en la base de datos
    db.session.commit()
    # Emitir señal para actualizar la identidad
    identity_changed.send(current_app._get_current_object(), identity=Identity(user.id))

Esto garantiza que los cambios en los permisos se reflejen inmediatamente, sin requerir que el usuario cierre y vuelva a iniciar sesión.

Integración si ya se tiene Flask-Login

Si ya tienes una aplicación Flask que utiliza Flask-Login para la autenticación de usuarios, integrar Flask-Principal para agregar capacidades de autorización es un proceso sencillo. Flask-Principal complementa a Flask-Login al proporcionar un marco para gestionar roles y permisos, permitiéndote controlar el acceso a diferentes partes de tu aplicación según las necesidades específicas de tus usuarios.

Primero, asegúrate de tener Flask-Principal instalado en tu entorno:

pip install Flask-Principal

Luego, importa e inicializa Flask-Principal en tu aplicación Flask ya existente:

from flask import Flask
from flask_login import LoginManager
from flask_principal import Principal

app = Flask(__name__)
app.config['SECRET_KEY'] = 'tu_clave_secreta'

# Configura Flask-Login
login_manager = LoginManager(app)

# Inicializa Flask-Principal
principals = Principal(app)

Es importante inicializar Flask-Principal después de configurar Flask-Login, ya que aprovecharemos la integración entre ambos para gestionar la identidad del usuario autenticado.

Flask-Login requiere que definas una función que cargue un usuario basado en su identificador. Asegúrate de tenerla configurada:

from flask_login import UserMixin

# Modelo de usuario
class User(UserMixin):
    def __init__(self, id, username, role):
        self.id = id
        self.username = username
        self.role = role

# Diccionario simulado de usuarios
users = {
    1: User(1, 'alice', 'admin'),
    2: User(2, 'bob', 'editor'),
}

@login_manager.user_loader
def load_user(user_id):
    return users.get(int(user_id))

Este ejemplo simplificado utiliza un diccionario de usuarios, cada uno con un rol asignado. En una aplicación real, los usuarios y sus roles se gestionarían mediante una base de datos.

Para que Flask-Principal reconozca al usuario autenticado y sus permisos, es necesario conectar las señales de Flask-Login con Flask-Principal. Esto se logra manejando las señales identity_loaded e identity_changed.

Conecta una función a la señal identity_loaded para cargar las necesidades del usuario actual:

from flask_login import current_user
from flask_principal import identity_loaded, UserNeed, RoleNeed

@identity_loaded.connect_via(app)
def on_identity_loaded(sender, identity):
    # Establece el usuario en la identidad
    identity.user = current_user

    # Agrega la necesidad de usuario
    if hasattr(current_user, 'id'):
        identity.provides.add(UserNeed(current_user.id))

    # Agrega la necesidad de rol
    if hasattr(current_user, 'role'):
        identity.provides.add(RoleNeed(current_user.role))

Esta función se ejecuta cada vez que la identidad es cargada, agregando las necesidades de usuario y rol basadas en el current_user proporcionado por Flask-Login.

Cuando un usuario inicia sesión o cierra sesión, es necesario informar a Flask-Principal sobre el cambio de identidad. Modifica tus funciones de inicio y cierre de sesión para emitir la señal identity_changed.

Al autenticar al usuario y llamar a login_user, emite la señal:

from flask import request, redirect, url_for, current_app
from flask_login import login_user
from flask_principal import Identity, identity_changed

@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':
        # Autentica al usuario (simplificado para el ejemplo)
        user = users.get(int(request.form['user_id']))
        if user:
            login_user(user)
            # Emite la señal de cambio de identidad
            identity_changed.send(current_app._get_current_object(), identity=Identity(user.id))
            return redirect(url_for('index'))
    return '''
        <form method="post">
            <input type="text" name="user_id" placeholder="ID de usuario">
            <input type="submit" value="Iniciar sesión">
        </form>
    '''

Al emitir la señal identity_changed, Flask-Principal actualizará la identidad actual con la del usuario autenticado.

Al cerrar sesión con logout_user, también es necesario emitir la señal:

from flask_login import logout_user
from flask_principal import AnonymousIdentity

@app.route('/logout')
def logout():
    logout_user()
    # Emite la señal de cambio de identidad a anónima
    identity_changed.send(current_app._get_current_object(), identity=AnonymousIdentity())
    return redirect(url_for('index'))

Esto asegura que la identidad se restablezca a una identidad anónima, removiendo cualquier necesidad o permiso asociado al usuario anterior.

Con la identidad sincronizada, puedes definir permisos basados en las necesidades añadidas. Por ejemplo, crea permisos para diferentes roles:

from flask_principal import Permission, RoleNeed

# Permisos basados en roles
admin_permission = Permission(RoleNeed('admin'))
editor_permission = Permission(RoleNeed('editor'))

Luego, protege las vistas utilizando estos permisos:

from flask_principal import PermissionDenied

@app.route('/admin')
@admin_permission.require(http_exception=403)
def admin():
    return 'Panel de administración'

@app.route('/edit')
@editor_permission.require(http_exception=403)
def edit():
    return 'Página de edición'

# Manejo de errores de permiso
@app.errorhandler(PermissionDenied)
def handle_permission_denied(error):
    return 'Permiso denegado', 403

El decorador @permission.require() verifica que el usuario cumpla con el permiso antes de acceder a la vista. Si no es así, lanza la excepción PermissionDenied.

Puedes utilizar los permisos en tus plantillas Jinja2 para mostrar u ocultar elementos según los permisos del usuario:

@app.context_processor
def inject_permissions():
    return dict(admin_permission=admin_permission, editor_permission=editor_permission)

En tu plantilla:

{% if admin_permission.can() %}
    <a href="{{ url_for('admin') }}">Panel de administración</a>
{% endif %}

Esto mejora la experiencia de usuario, evitando mostrar enlaces o botones que no están autorizados a utilizar.

Considera algunas consideraciones adicionales:

  • Roles múltiples: Si un usuario puede tener múltiples roles, asegúrate de agregar todas las necesidades de rol en la función on_identity_loaded:
  if hasattr(current_user, 'roles'):
      for role in current_user.roles:
          identity.provides.add(RoleNeed(role))
  • Actualización de permisos: Si los roles o permisos de un usuario cambian durante la sesión, emite la señal identity_changed para actualizar la identidad:
  # Después de cambiar el rol del usuario
  identity_changed.send(current_app._get_current_object(), identity=Identity(current_user.id))
  • Protección adicional: Considera proteger tus rutas con el decorador @login_required de Flask-Login además de los permisos de Flask-Principal, para garantizar que solo usuarios autenticados puedan acceder:
  from flask_login import login_required

  @app.route('/secure')
  @login_required
  @editor_permission.require(http_exception=403)
  def secure_edit():
      return 'Página segura de edición'
  • Uso de http_exception: Al especificar http_exception=403 en el decorador require, permites que Flask-Principal lance una excepción HTTP en lugar de PermissionDenied, simplificando el manejo de errores.

Integrar Flask-Principal en una aplicación que ya utiliza Flask-Login te permite aprovechar el sistema de autenticación existente y agregar un control de autorización más robusto. Al manejar adecuadamente las señales y sincronizar la identidad, puedes definir permisos basados en roles y necesidades personalizadas, protegiendo tus vistas y recursos de acuerdo con las políticas de acceso definidas.

Para seguir leyendo hazte Plus

¿Ya eres Plus? Accede a la app

20 % DE DESCUENTO

Plan mensual

19.00 /mes

15.20 € /mes

Precio normal mensual: 19 €
58 % DE DESCUENTO

Plan anual

10.00 /mes

8.00 € /mes

Ahorras 132 € al año
Precio normal anual: 120 €
Aprende Flask GRATIS online

Todas las lecciones de Flask

Accede a todas las lecciones de Flask y aprende con ejemplos prácticos de código y ejercicios de programación con IDE web sin instalar nada.

Accede GRATIS a Flask y certifícate

En esta lección

Objetivos de aprendizaje de esta lección

  • Instalar y configurar Flask-Principal para gestionar roles y permisos.
  • Definir roles y permisos utilizando necesidades específicas.
  • Asignar roles a usuarios empleados de Flask-Login.
  • Proteger vistas mediante decoradores de permiso.
  • Integrar mecanismos de identificación con señales de Flask-Principal.
  • Gestionar la revocación y actualización de permisos de usuario.