Skip to content

Commit

Permalink
📝 add sphinx django model field directive
Browse files Browse the repository at this point in the history
  • Loading branch information
Coperh committed Dec 4, 2024
1 parent c7f8401 commit e1d1d84
Show file tree
Hide file tree
Showing 6 changed files with 118 additions and 32 deletions.
16 changes: 16 additions & 0 deletions docs/_ext/model_field/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
from sphinx.application import Sphinx
from sphinx.util.typing import ExtensionMetadata

from .directives import ModelFieldsDirective
from .roles import ModelFieldRole


def setup(app: Sphinx) -> ExtensionMetadata:
app.add_role("model_field", ModelFieldRole())
app.add_directive("model_fields", ModelFieldsDirective)

return {
"version": "0.1",
"parallel_read_safe": True,
"parallel_write_safe": True,
}
31 changes: 31 additions & 0 deletions docs/_ext/model_field/directives.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
from __future__ import annotations

from django.utils.module_loading import import_string

from docutils import nodes
from sphinx.util.docutils import SphinxDirective

from .utils import get_field_representation


class ModelFieldsDirective(SphinxDirective):
"""Displays a model's fields with their name, helptext and default in a list"""

required_arguments = 1
has_content = True

def run(self) -> list[nodes.Node]:

model_path = self.arguments[0]
model = import_string(model_path)

field_list = []

for line in self.content:
field = model._meta.get_field(line)
node = nodes.paragraph("", "", *get_field_representation(field))
field_list.append(nodes.list_item("", node))

bullet_list = nodes.bullet_list("", *field_list)

return [bullet_list]
22 changes: 22 additions & 0 deletions docs/_ext/model_field/roles.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
from django.utils.module_loading import import_string

from docutils import nodes
from sphinx.util.docutils import SphinxRole

from .utils import get_field_representation


class ModelFieldRole(SphinxRole):
"""Displays a model field's name, helptext and default inline"""

def run(self) -> tuple[list[nodes.Node], list[nodes.system_message]]:

field_split = len(self.text) - self.text[::-1].index(".") - 1
model_path = self.text[:field_split]
field_name = self.text[field_split + 1 :]

model = import_string(model_path)
field = model._meta.get_field(field_name)

field_nodes = get_field_representation(field)
return field_nodes, []
20 changes: 20 additions & 0 deletions docs/_ext/model_field/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
from django.db.models.fields import Field

from docutils import nodes


def get_field_representation(field: Field) -> list[nodes.literal | nodes.Text]:

name = nodes.literal("", nodes.Text(field.name))
description = nodes.Text(f": {field.help_text}.")

field_nodes = [name, description]

# Should it include blank that default to empty string?
if field.has_default():
field_nodes.append(nodes.Text(" Defaults to "))
field_nodes.append(nodes.literal("", nodes.Text(field.get_default())))
else:
field_nodes.append(nodes.Text(" No default."))

return field_nodes
4 changes: 4 additions & 0 deletions docs/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,13 @@
# Add any Sphinx extension module names here, as strings. They can be
# extensions coming with Sphinx (named "sphinx.ext.*") or your custom
# ones.

sys.path.append(os.path.abspath("./_ext"))

extensions = [
"sphinx.ext.autodoc",
"sphinx.ext.todo",
"model_field",
]

# Add any paths that contain templates here, relative to this directory.
Expand Down
57 changes: 25 additions & 32 deletions docs/setup_configuration.rst
Original file line number Diff line number Diff line change
Expand Up @@ -65,18 +65,17 @@ Required Fields:
""""""""""""""""


* ``oidc_rp_client_id``: OpenID Connect client ID from the OIDC Provider.
* ``oidc_rp_client_secret``: OpenID Connect secret from the OIDC Provider.
* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_rp_client_id`
* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_rp_client_secret`
* ``endpoint_config``: Dictionary containing endpoint information

* ``oidc_op_discovery_endpoint``: URL of your OpenID Connect provider discovery endpoint ending with a slash (`.well-known/...` will be added automatically).
* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_op_discovery_endpoint`

**OR**

* ``oidc_op_authorization_endpoint``: URL of your OpenID Connect provider authorization endpoint
* ``oidc_op_token_endpoint``: URL of your OpenID Connect provider token endpoint
* ``oidc_op_user_endpoint``: URL of your OpenID Connect provider userinfo endpoint

* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_op_authorization_endpoint`
* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_op_token_endpoint`
* :model_field:`mozilla_django_oidc_db.models.OpenIDConnectConfig.oidc_op_user_endpoint`

The endpoints must be provided in the ``endpoint_config`` dictionary.
You can add the discovery endpoint to automatically fetch the other endpoints.
Expand All @@ -85,35 +84,29 @@ Providing both will cause the validation to fail.

Optional Fields:
""""""""""""""""

.. warning::

Values that are not provided will use the default or empty value and will overwrite any setting changed in the admin.
Make sure settings that were manually changed in the admin are added to the configuration yaml.

All the following keys are placed in the ``oidc_db_config_admin_auth`` dictionary.

* ``enabled``: whether OIDC is enabled for admin login. Defaults to ``True``.
* ``oidc_op_jwks_endpoint``: URL of your OpenID Connect provider JSON Web Key Set endpoint.
Required if ``RS256`` is used as signing algorithm. No default value.
* ``claim_mapping``: Mapping from user-model fields to OIDC claims.
Defaults to ``{"email": ["email"], "first_name": ["given_name"], "last_name": ["family_name"]}``
* ``username_claim``: The name of the OIDC claim that is used as the username. Defaults to ``["sub"]``
* ``groups_claim``: The name of the OIDC claim that holds the values to map to local user groups. Defaults to ``["roles"]``
* ``default_groups``: The default groups to which every user logging in with OIDC will be assigned. No default values.
* ``superuser_group_names``: If any of these group names are present in the claims upon login, the user will be marked as a superuser.
If none of these groups are present the user will lose superuser permissions. Defaults to empty list.
* ``make_users_staff``: Users will be flagged as being a staff user automatically.
This allows users to login to the admin interface. Defaults to ``False``.
* ``oidc_use_nonce``: Controls whether the OpenID Connect client uses nonce verification. Defaults to ``True``.
* ``oidc_nonce_size``: Sets the length of the random string used for OpenID Connect nonce verification. Defaults to ``32``.
* ``oidc_state_size``: Sets the length of the random string used for OpenID Connect state verification. Defaults to ``32``.
* ``oidc_rp_idp_sign_key``: Key the Identity Provider uses to sign ID tokens in the case of an RSA sign algorithm.
Should be the signing key in PEM or DER format. No default.
* ``oidc_rp_scopes_list``: OpenID Connect scopes that are requested during login. Defaults to ``["openid", "email", "profile"]``.
* ``oidc_rp_sign_algo``: Algorithm the Identity Provider uses to sign ID tokens. Defaults to ``"HS256"``.
* ``sync_groups``: If checked, local user groups will be created for group names present in the groups claim,
if they do not exist yet locally. Defaults to ``True``.
* ``sync_groups_glob_pattern``: The glob pattern that groups must match to be synchronized to the local database. Defaults to ``"*"``.
* ``userinfo_claims_source``: Indicates the source from which the user information claims should be extracted
(``"userinfo_endpoint"`` or ``"id_token"``). Defaults to ``"userinfo_endpoint"``.
.. model_fields:: mozilla_django_oidc_db.models.OpenIDConnectConfig

enabled
oidc_op_jwks_endpoint
claim_mapping
username_claim
groups_claim
default_groups
superuser_group_names
make_users_staff
oidc_use_nonce
oidc_nonce_size
oidc_state_size
oidc_rp_idp_sign_key
oidc_rp_scopes_list
oidc_rp_sign_algo
sync_groups
sync_groups_glob_pattern
userinfo_claims_source

0 comments on commit e1d1d84

Please sign in to comment.