# Path: repocribro/security.py
# def init_login_manager(db):
#     def unauthorized():
#     def load_user(user_id):
#     def identity_loader():
#     def __init__(self, name):
#     def __getattr__(self, key):
#     def __init__(self):
#     def register_role(self, role_name):
#     def register_action(self, priv_name):
#     def all_roles(self):
#     def all_actions(self):
# def login(user_account):
# def logout():
# def clear_session(*args):
# def reload_anonymous_role(app, db):
# def get_default_user_role(app, db):
# def create_default_role(app, db, role):
# def on_identity_loaded(sender, identity):
# class PermissionsContainer:
# class Permissions:
# 
# Path: repocribro/models.py
# class UserAccount(db.Model, UserMixin, SearchableMixin):
#     """UserAccount in the repocribro app"""
#     __tablename__ = 'UserAccount'
# 
#     default_rolename = 'user'
# 
#     #: Unique identifier of the user account
#     id = sqlalchemy.Column(sqlalchemy.Integer, primary_key=True)
#     #: Timestamp where account was created
#     created_at = sqlalchemy.Column(
#         sqlalchemy.DateTime, default=datetime.datetime.now()
#     )
#     #: Flag if the account is active or banned
#     active = sqlalchemy.Column(sqlalchemy.Boolean, default=True)
#     #: Relation to the GitHub user connected to account
#     github_user = sqlalchemy.orm.relationship(
#         'User', back_populates='user_account',
#         uselist=False, cascade='all, delete-orphan'
#     )
#     #: Roles assigned to the user account
#     roles = sqlalchemy.orm.relationship(
#         'Role', back_populates='user_accounts',
#         secondary=roles_users,
#     )
# 
#     @property
#     def login(self):
#         """Get login name for user account from related GH user
# 
#         :return: Login name
#         :rtype: str
#         """
#         if self.github_user is None:
#             return '<unknown>'
#         return self.github_user.login
# 
#     def __repr__(self):
#         """Standard string representation of DB object
# 
#         :return: Unique string representation
#         :rtype: str
#         """
#         return '<UserAccount (#{})>'.format(self.id)
# 
# class Role(db.Model, RoleMixin):
#     """User account role in the application"""
#     __tablename__ = 'Role'
# 
#     #: Unique identifier of the role
#     id = sqlalchemy.Column(sqlalchemy.Integer(), primary_key=True)
#     #: Unique name of the role
#     name = sqlalchemy.Column(sqlalchemy.String(80), unique=True)
#     #: Description (purpose, notes, ...) of the role
#     description = sqlalchemy.Column(sqlalchemy.UnicodeText)
#     #: Serialized list of privileges
#     privileges = sqlalchemy.Column(sqlalchemy.Text)
#     #: User accounts assigned to the role
#     user_accounts = sqlalchemy.orm.relationship(
#         'UserAccount', back_populates='roles', secondary=roles_users
#     )
# 
#     def __init__(self, name, privileges, description):
#         self.name = name
#         self.privileges = privileges
#         self.description = description
# 
#     def __repr__(self):
#         """Standard string representation of DB object
# 
#         :return: Unique string representation
#         :rtype: str
#         """
#         return '<Role {} (#{})>'.format(
#             self.name, self.id
#         )


import flask_login
import pytest
from werkzeug.exceptions import Forbidden
from repocribro.security import login, logout, permissions
from repocribro.models import UserAccount, Role




def test_login_logout(app, empty_db_session):
    with app.test_request_context('/'):
        account = UserAccount()
        account.id = 666
        empty_db_session.add(account)
        empty_db_session.commit()
        login(account)
        assert flask_login.current_user.id == 666
        logout()
        assert flask_login.current_user.is_anonymous


def test_permission_admin(app, empty_db_session):
    with app.test_request_context('/'):
        @permissions.roles.admin.require(403)
        def test():
            return 200

        with pytest.raises(Forbidden):
            assert test() == 200

        role_admin = Role('testadmin', '*', '')

# Path: repocribro/security.py
# def init_login_manager(db):
#     def unauthorized():
#     def load_user(user_id):
#     def identity_loader():
#     def __init__(self, name):
#     def __getattr__(self, key):
#     def __init__(self):
#     def register_role(self, role_name):
#     def register_action(self, priv_name):
#     def all_roles(self):
#     def all_actions(self):
# def login(user_account):
# def logout():
# def clear_session(*args):
# def reload_anonymous_role(app, db):
# def get_default_user_role(app, db):
# def create_default_role(app, db, role):
# def on_identity_loaded(sender, identity):
# class PermissionsContainer:
# class Permissions:
# 
# Path: repocribro/models.py
# class UserAccount(db.Model, UserMixin, SearchableMixin):
#     """UserAccount in the repocribro app"""
#     __tablename__ = 'UserAccount'
# 
#     default_rolename = 'user'
# 
#     #: Unique identifier of the user account
#     id = sqlalchemy.Column(sqlalchemy.Integer, primary_key=True)
#     #: Timestamp where account was created
#     created_at = sqlalchemy.Column(
#         sqlalchemy.DateTime, default=datetime.datetime.now()
#     )
#     #: Flag if the account is active or banned
#     active = sqlalchemy.Column(sqlalchemy.Boolean, default=True)
#     #: Relation to the GitHub user connected to account
#     github_user = sqlalchemy.orm.relationship(
#         'User', back_populates='user_account',
#         uselist=False, cascade='all, delete-orphan'
#     )
#     #: Roles assigned to the user account
#     roles = sqlalchemy.orm.relationship(
#         'Role', back_populates='user_accounts',
#         secondary=roles_users,
#     )
# 
#     @property
#     def login(self):
#         """Get login name for user account from related GH user
# 
#         :return: Login name
#         :rtype: str
#         """
#         if self.github_user is None:
#             return '<unknown>'
#         return self.github_user.login
# 
#     def __repr__(self):
#         """Standard string representation of DB object
# 
#         :return: Unique string representation
#         :rtype: str
#         """
#         return '<UserAccount (#{})>'.format(self.id)
# 
# class Role(db.Model, RoleMixin):
#     """User account role in the application"""
#     __tablename__ = 'Role'
# 
#     #: Unique identifier of the role
#     id = sqlalchemy.Column(sqlalchemy.Integer(), primary_key=True)
#     #: Unique name of the role
#     name = sqlalchemy.Column(sqlalchemy.String(80), unique=True)
#     #: Description (purpose, notes, ...) of the role
#     description = sqlalchemy.Column(sqlalchemy.UnicodeText)
#     #: Serialized list of privileges
#     privileges = sqlalchemy.Column(sqlalchemy.Text)
#     #: User accounts assigned to the role
#     user_accounts = sqlalchemy.orm.relationship(
#         'UserAccount', back_populates='roles', secondary=roles_users
#     )
# 
#     def __init__(self, name, privileges, description):
#         self.name = name
#         self.privileges = privileges
#         self.description = description
# 
#     def __repr__(self):
#         """Standard string representation of DB object
# 
#         :return: Unique string representation
#         :rtype: str
#         """
#         return '<Role {} (#{})>'.format(
#             self.name, self.id
#         )


# Path: tests/test_security.py
import flask_login
import pytest
from werkzeug.exceptions import Forbidden
from repocribro.security import login, logout, permissions
from repocribro.models import UserAccount, Role





def test_login_logout(app, empty_db_session):
    with app.test_request_context('/'):
        account = UserAccount()
        account.id = 666
        empty_db_session.add(account)
        empty_db_session.commit()
        login(account)
        assert flask_login.current_user.id == 666
        logout()
        assert flask_login.current_user.is_anonymous


def test_permission_admin(app, empty_db_session):
    with app.test_request_context('/'):
        @permissions.roles.admin.require(403)
        def test():
            return 200

        with pytest.raises(Forbidden):
            assert test() == 200

        role_admin = Role('testadmin', '*', '')

        account = UserAccount()