mirror of
https://github.com/enpaul/keyosk.git
synced 2024-11-24 23:47:49 +00:00
Add domain and domain administration models
This commit is contained in:
parent
2b5eafa71a
commit
425d39cd48
123
keyosk/database/domain.py
Normal file
123
keyosk/database/domain.py
Normal file
@ -0,0 +1,123 @@
|
|||||||
|
"""Authentication domain model definition"""
|
||||||
|
import datetime
|
||||||
|
from typing import List
|
||||||
|
|
||||||
|
import peewee
|
||||||
|
|
||||||
|
from keyosk.database._shared import KeyoskBaseModel
|
||||||
|
from keyosk.database.domain_admin import DomainAdmin
|
||||||
|
|
||||||
|
|
||||||
|
class Domain(KeyoskBaseModel):
|
||||||
|
"""Authentication domain storage model
|
||||||
|
|
||||||
|
:attribute created: Datetime indicating when the domain was first created
|
||||||
|
:attribute updated: Datetime indicating when the domain was last modified
|
||||||
|
:attribute name: Simple URL-friendly name for the domain
|
||||||
|
:attribute audience: Value to populate the ``audience`` claim of issued JWTs with
|
||||||
|
when authenticating against this domain
|
||||||
|
:attribute title: Human-friendly display name for the domain
|
||||||
|
:attribute description: Human-friendly longer description of the domain's usage or
|
||||||
|
purpose
|
||||||
|
:attribute contact: Contact link for the domain
|
||||||
|
:attribute enabled: Whether the domain is enabled for authentication
|
||||||
|
:attribute enable_password: Whether to allow accounts to authenticate using the
|
||||||
|
client-set authentication secret
|
||||||
|
:attribute enable_autopassword: Whether to allow accounts to authenticate using the
|
||||||
|
server-set authentication secret
|
||||||
|
:attribute lifespan_access: Number of seconds that an issued JWT access token should
|
||||||
|
be valid for
|
||||||
|
:attribute lifespan_refresh: Number of seconds an an issued JWT refresh token should
|
||||||
|
be valid for
|
||||||
|
:attribute administration: Container of additional settings related to the
|
||||||
|
administration of the domain itself
|
||||||
|
:property access_list_names: List of Access Control Lists under the domain that accounts
|
||||||
|
can have permission entries on
|
||||||
|
:property permission_names: List of permissions that can be assigned to an account's ACL
|
||||||
|
entry
|
||||||
|
"""
|
||||||
|
|
||||||
|
class Meta: # pylint: disable=too-few-public-methods,missing-docstring
|
||||||
|
table_name = "domain"
|
||||||
|
|
||||||
|
created = peewee.DateTimeField(null=False, default=datetime.datetime.utcnow)
|
||||||
|
updated = peewee.DateTimeField(null=False, default=datetime.datetime.utcnow)
|
||||||
|
name = peewee.CharField(null=False, unique=True)
|
||||||
|
audience = peewee.CharField(null=False, unique=True)
|
||||||
|
title = peewee.CharField(null=True)
|
||||||
|
description = peewee.CharField(null=True)
|
||||||
|
contact = peewee.CharField(null=True)
|
||||||
|
enabled = peewee.BooleanField(null=False)
|
||||||
|
enable_password = peewee.BooleanField(null=False)
|
||||||
|
enable_autopassword = peewee.BooleanField(null=False)
|
||||||
|
enable_refresh = peewee.BooleanField(null=False)
|
||||||
|
lifespan_access = peewee.IntegerField(null=False)
|
||||||
|
lifespan_refresh = peewee.IntegerField(null=False)
|
||||||
|
administration = peewee.ForeignKeyField(DomainAdmin, null=False, unique=True)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def access_list_names(self) -> List[str]:
|
||||||
|
"""Return the list of ACL items from the backref"""
|
||||||
|
return [item.name for item in self._access_lists]
|
||||||
|
|
||||||
|
@property
|
||||||
|
def permission_names(self) -> List[str]:
|
||||||
|
"""Return the list of permission names from the backref"""
|
||||||
|
return [item.name for item in self._permissions]
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def dict_keys() -> List[str]:
|
||||||
|
return [
|
||||||
|
"uuid",
|
||||||
|
"created",
|
||||||
|
"updated",
|
||||||
|
"name",
|
||||||
|
"audience",
|
||||||
|
"title",
|
||||||
|
"description",
|
||||||
|
"contact",
|
||||||
|
"enabled",
|
||||||
|
"enable_password",
|
||||||
|
"enable_autopassword",
|
||||||
|
"enable_refresh",
|
||||||
|
"lifespan_access",
|
||||||
|
"lifespan_refresh",
|
||||||
|
"access_list_names",
|
||||||
|
"permission_names",
|
||||||
|
"administration",
|
||||||
|
]
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def foreign_ref() -> List[str]:
|
||||||
|
return ["administration"]
|
||||||
|
|
||||||
|
|
||||||
|
class DomainAccessList(KeyoskBaseModel):
|
||||||
|
"""Access list name model definition
|
||||||
|
|
||||||
|
:attribute name: Name of the access control list
|
||||||
|
:attribute domain: Authentication domain the ACL applies to
|
||||||
|
"""
|
||||||
|
|
||||||
|
class Meta: # pylint: disable=missing-docstring,too-few-public-methods
|
||||||
|
table_name = "domain_acl"
|
||||||
|
|
||||||
|
name = peewee.CharField(null=False)
|
||||||
|
domain = peewee.ForeignKeyField(Domain, backref="access_lists")
|
||||||
|
|
||||||
|
|
||||||
|
class DomainPermission(KeyoskBaseModel):
|
||||||
|
"""Permission name model definition
|
||||||
|
|
||||||
|
:attribute name: Name of the permission
|
||||||
|
:attribute bitindex: Index in the generated bitmask that indicates this permission;
|
||||||
|
zero-indexed
|
||||||
|
:attribute domain: Authentication domain the permission should apply to the ACLs of
|
||||||
|
"""
|
||||||
|
|
||||||
|
class Meta: # pylint: disable=missing-docstring,too-few-public-methods
|
||||||
|
table_name = "domain_permission"
|
||||||
|
|
||||||
|
name = peewee.CharField(null=False)
|
||||||
|
bitindex = peewee.IntegerField(null=False)
|
||||||
|
domain = peewee.ForeignKeyField(Domain, backref="permissions")
|
70
keyosk/database/domain_admin.py
Normal file
70
keyosk/database/domain_admin.py
Normal file
@ -0,0 +1,70 @@
|
|||||||
|
"""Authentication domain meta admin settings model definition
|
||||||
|
|
||||||
|
The domain administration settings allow access to be granted to accounts assigned to
|
||||||
|
the domain to manage the domain itself. This allows accounts to manage the parts of
|
||||||
|
Keyosk that they need to without granting permissions to every domain Keyosk knows
|
||||||
|
about.
|
||||||
|
|
||||||
|
However, to avoid circular foreign key references, the admin settings need their own
|
||||||
|
relation tabel. If these settings were part of the main :class:`Domain` model then there
|
||||||
|
would be circular references between it and the :class:`DomainAccessList` and
|
||||||
|
:class:`DomainPermission` models.
|
||||||
|
"""
|
||||||
|
from typing import Generator
|
||||||
|
from typing import Tuple
|
||||||
|
|
||||||
|
import peewee
|
||||||
|
|
||||||
|
from keyosk.database._shared import KeyoskBaseModel
|
||||||
|
from keyosk.database.mappings import DomainAccessList
|
||||||
|
from keyosk.database.mappings import DomainPermission
|
||||||
|
|
||||||
|
|
||||||
|
class DomainAdmin(KeyoskBaseModel):
|
||||||
|
"""Authentication domain meta administration storage model
|
||||||
|
|
||||||
|
:attribute access_list: The ACL that an account must have permissions for to manage
|
||||||
|
the domain settings
|
||||||
|
:attribute domain_read: Permission granted by the ACL entry that gives the assigned
|
||||||
|
account read access to the domain settings
|
||||||
|
:attribute domain_update: Permission granted by the ACL entry that gives the
|
||||||
|
assigned account update access to the domain settings
|
||||||
|
:attribute account_create: Permission granted by the ACL entry that gives the
|
||||||
|
assigned account access to create new accounts assigned
|
||||||
|
to the domain
|
||||||
|
:attribute account_read: Permission granted by the ACL entry that gives the
|
||||||
|
assigned account read access to the accounts assigned to
|
||||||
|
the domain
|
||||||
|
:attribute account_delete: Permission granted by the ACL entry that gives the
|
||||||
|
assigned account access to unassign an account from the
|
||||||
|
domain
|
||||||
|
|
||||||
|
There are two permissions not available via this model that may make sense to
|
||||||
|
implement in the future: ``account_update`` and ``domain_delete``. The first is not
|
||||||
|
implemented due to the potential conflicts it causes: an account can be assigned to
|
||||||
|
multiple domains, so granting permissions on one domain to modify an account may
|
||||||
|
implicitly grant that same permission on one or more accounts assigned to another
|
||||||
|
domain; this seemed ill advised. The second is not implemented for no real good
|
||||||
|
reason, other than it seemed out of the inteneded usage of "domain management".
|
||||||
|
|
||||||
|
.. note:: Both the permissions denoted above, as well as other permissions not
|
||||||
|
enumerated here, are available through the primary Keyosk authentication
|
||||||
|
domain.
|
||||||
|
"""
|
||||||
|
|
||||||
|
class Meta: # pylint: disable=missing-docstring,too-few-public-methods
|
||||||
|
table_name = "domain_admin"
|
||||||
|
|
||||||
|
access_list = peewee.ForeignKeyField(DomainAccessList, null=True)
|
||||||
|
domain_read = peewee.ForeignKeyField(DomainPermission, null=True)
|
||||||
|
domain_update = peewee.ForeignKeyField(DomainPermission, null=True)
|
||||||
|
account_create = peewee.ForeignKeyField(DomainPermission, null=True)
|
||||||
|
account_read = peewee.ForeignKeyField(DomainPermission, null=True)
|
||||||
|
account_delete = peewee.ForeignKeyField(DomainPermission, null=True)
|
||||||
|
|
||||||
|
def __iter__(self) -> Generator[Tuple[str, str], None, None]:
|
||||||
|
yield "access_list", self.access_list.name
|
||||||
|
yield "domain_read", self.domain_read.name
|
||||||
|
yield "account_create", self.account_create.name
|
||||||
|
yield "account_read", self.account_read.name
|
||||||
|
yield "account_delete", self.account_delete.name
|
Loading…
Reference in New Issue
Block a user