ox.apps.content

This application provides basis to allow content edition for different kind of media.

It allows user to edit rich text, ensuring input sanitization. The rich text content may also contains custom blocks as defined by blocks.DynamicBlock. Those are translated in Django template code.

So what does it provides?

  • RichTextField (for models and serializers);

  • Renderer that containerize user’s django templates;

  • Dynamic blocks that can be reused by user for rich text edition (such as variable, conditional variables);

  • Messages: basic models, serializers, views and components for creating messages.

It is planned later to also add support for template packs (eg. for CMS).

Models

class ox.apps.content.models.RichTextField(*args, allowed_tags=None, allowed_attributes=None, allowed_protocols=None, allowed_styles=None, **kwargs)[source]

Bases: RichTextFieldMixin, TextField

Provide rich text value, ensuring input text is cleaned based on ox_content_settings.

It uses bleach, and provided attributes reflects bleach’s clean() settings.

Note though that strings are not marked as safe. This is up to the user to do so.

to_python(value)[source]

Convert the input value into the expected Python data type, raising django.core.exceptions.ValidationError if the data can’t be converted. Return the converted value. Subclasses should override this.

validate(value, model_instance)[source]

Validate value and raise ValidationError if necessary. Subclasses should override this to provide validation logic.

class ox.apps.content.models.TemplatePack(*args, **kwargs)[source]

Bases: PackageInfo

Base abstract model used to provide content templates.

A bundle consist of different elements:

  • templates: used to render the content;

  • statics: assets;

  • user_fields: user specific fields;

Templates and static directories are provided at class level, in order to allow users to create a new template inheriting from another one.

classmethod get_source_dirname()[source]

Return directory name in which templates and statics are put. This typically takes the format of app_label.model_name (lower cased).

Return type:

str

classmethod get_static_dir()[source]

Return static directory used for this model class.

Return type:

Path

classmethod get_template_dir()[source]

Return template directory used for this model class.

Return type:

Path

source_dir = ''

[class attribute] Directory name in which to store packs.

If not provided, use model’s label_lower.

property static_dir: Path

Static directory for this template.

property template_dir: Path

Template directory for this template.

template_files = [('index.html', 'Index')]

[class attribute] Allowed template files that user can select.

It is set as choices of related content’s template.

ox.apps.content.apps

class ox.apps.content.apps.AppConfig(*args, **kwargs)[source]

Bases: AppConfig

icon: str = 'mdi-flag'

Material design icon class.

npm_package: str | None = '@oxylus/content'

Name of the corresponding NPM package to look up for.

Defaults to app label.

root_url: str = 'ox/content'

Provide an alternative to app label when we target application in paths.

For example Oxylus will nest template directories as ox/core/ instead of ox_core. The same happens for urls.

ox.apps.content.conf

class ox.apps.content.conf.Settings(key, source=<LazySettings "instance.settings">)[source]

Bases: Settings

ALLOWED_ATTRIBUTES = {'*': ['style'], 'a': ['href', 'title', 'target'], 'div': ['data-block', 'data-block-variable'], 'span': ['data-block', 'data-block-variable'], 'td': ['colspan', 'rowspan'], 'th': ['colspan', 'rowspan']}

Allowed tags attributes.

Pay attention to allow data-block* attribute as they are used by Oxylus.

ALLOWED_PROTOCOLS = ['https', 'mailto', 'tel']

Allowed URL protocols.

ALLOWED_STYLES = ['text-align', 'font-weight', 'font-style', 'color', 'background-color']

Allowed inline tags styles.

ALLOWED_TAGS = ['p', 'br', 'strong', 'em', 'ul', 'ol', 'li', 'table', 'thead', 'tbody', 'tr', 'th', 'td', 'span', 'div', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'a', 'pre', 'code']

Allowed tags

STATIC_DIR = 'ox_content/bundles'

Directory in static where to store bundles.

TEMPLATE_DIR = 'ox_content/bundles'

Directory in templates where to store bundles.

property static_dir: Path

Static directory path where to store bundles’ statics.

property template_dir: Path

Template directory path where to store bundle templates.

ox.apps.content.conf.ox_content_settings: Settings = <ox.apps.content.conf.Settings object>

Settings used by ox_content application, using key OX_CONTENT.

ox.apps.content.mixins

class ox.apps.content.mixins.RichTextFieldMixin(*args, allowed_tags=None, allowed_attributes=None, allowed_protocols=None, allowed_styles=None, **kwargs)[source]

Bases: object

Mixin class used in order to clean richtext input using ox_content_settings.

It uses bleach, and provided attributes reflects bleach’s clean() settings.

allowed_attributes = {'*': ['style'], 'a': ['href', 'title', 'target'], 'div': ['data-block', 'data-block-variable'], 'span': ['data-block', 'data-block-variable'], 'td': ['colspan', 'rowspan'], 'th': ['colspan', 'rowspan']}

Allowed tags attributes.

allowed_protocols = ['https', 'mailto', 'tel']

Allowed protocols.

allowed_tags = ['p', 'br', 'strong', 'em', 'ul', 'ol', 'li', 'table', 'thead', 'tbody', 'tr', 'th', 'td', 'span', 'div', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'a', 'pre', 'code']

Allowed HTML tags inside the content.

ox.apps.content.renderers

class ox.apps.content.renderers.Renderer(blocks=<factory>, variables=<factory>, template_dirs=<factory>)[source]

Bases: object

Base class for rendering content.

This class ensures:
  • contenerization: only provided template classes can be loaded.

  • the correct rendering between frontend editor blocks and template conversion.

blocks: list[DynamicBlock]

Dynamic blocks used to generate templates.

compile(source)[source]

From provided source code, return a Template instance.

It runs blocks in order to transform user’s dynamic blocks into jinja template code.

This is what you’ll use to transform user’s rich text content into a template.

Return type:

Template

property engine[source]

Engine to use in order to render templates.

get_template_dirs()[source]

Return template directory lookup.

Return type:

Iterable[str]

template_libraries = {'cache': 'django.templatetags.cache', 'i18n': 'django.templatetags.i18n', 'l10n': 'django.templatetags.l10n', 'tz': 'django.templatetags.tz'}

Libraries provided by template engine.

variables: dict[str, VariableInfo]

Allowed variables.

ox.apps.content.serializers

class ox.apps.content.serializers.DynamicBlockSerializer(*args, **kwargs)[source]

Bases: Serializer

Serialize a DynamicBlock.

class ox.apps.content.serializers.RendererSerializer(*args, **kwargs)[source]

Bases: Serializer

Serialize a Renderer informations.

Note: variables are rendered as a list with extra value name.

to_representation(instance)[source]

Object instance -> Dict of primitive datatypes.

class ox.apps.content.serializers.RichTextField(*args, **kwargs)[source]

Bases: RichTextFieldMixin, CharField

Handles cleaning input HTML rich text content.

class ox.apps.content.serializers.StripCharField(*args, **kwargs)[source]

Bases: CharField

Strip HTML tags of provided input.

to_internal_value(value)[source]

Transform the incoming primitive data into a native value.

class ox.apps.content.serializers.TemplatePackSerializer(*args, **kwargs)[source]

Bases: ModelSerializer

class ox.apps.content.serializers.VariableInfoSerializer(*args, **kwargs)[source]

Bases: Serializer