class Media

from django.forms import Media

Ancestors (MRO)

  1. Media
Expand Collapse

Properties

def _css(): Media

Getter

    @property
    def _css(self):
        css = defaultdict(list)
        for css_list in self._css_lists:
            for medium, sublist in css_list.items():
                css[medium].append(sublist)
        return {medium: self.merge(*lists) for medium, lists in css.items()}

def _js(): Media

Getter

    @property
    def _js(self):
        return self.merge(*self._js_lists)
Expand Collapse

Methods

def absolute_path(self, path): Media

Given a relative or absolute path to a static asset, return an absolute
path. An absolute path will be returned unchanged while a relative path
will be passed to django.templatetags.static.static().
    def absolute_path(self, path):
        """
        Given a relative or absolute path to a static asset, return an absolute
        path. An absolute path will be returned unchanged while a relative path
        will be passed to django.templatetags.static.static().
        """
        if path.startswith(("http://", "https://", "/")):
            return path
        return static(path)

def merge(*lists): Media

Merge lists while trying to keep the relative order of the elements.
Warn if the lists have the same elements in a different relative order.

For static assets it can be important to have them included in the DOM
in a certain order. In JavaScript you may not be able to reference a
global or in CSS you might want to override a style.
    @staticmethod
    def merge(*lists):
        """
        Merge lists while trying to keep the relative order of the elements.
        Warn if the lists have the same elements in a different relative order.

        For static assets it can be important to have them included in the DOM
        in a certain order. In JavaScript you may not be able to reference a
        global or in CSS you might want to override a style.
        """
        ts = TopologicalSorter()
        for head, *tail in filter(None, lists):
            ts.add(head)  # Ensure that the first items are included.
            for item in tail:
                if head != item:  # Avoid circular dependency to self.
                    ts.add(item, head)
                head = item
        try:
            return list(ts.static_order())
        except CycleError:
            warnings.warn(
                "Detected duplicate Media files in an opposite order: {}".format(
                    ", ".join(repr(list_) for list_ in lists)
                ),
                MediaOrderConflictWarning,
            )
            return list(dict.fromkeys(chain.from_iterable(filter(None, lists))))

def render(self): Media

    def render(self):
        return mark_safe(
            "\n".join(
                chain.from_iterable(
                    getattr(self, "render_" + name)() for name in MEDIA_TYPES
                )
            )
        )

def render_css(self): Media

    def render_css(self):
        # To keep rendering order consistent, we can't just iterate over
        # items(). We need to sort the keys, and iterate over the sorted list.
        media = sorted(self._css)
        return chain.from_iterable(
            [
                (
                    path.__html__()
                    if hasattr(path, "__html__")
                    else format_html(
                        '<link href="{}" media="{}" rel="stylesheet">',
                        self.absolute_path(path),
                        medium,
                    )
                )
                for path in self._css[medium]
            ]
            for medium in media
        )

def render_js(self): Media

    def render_js(self):
        return [
            (
                path.__html__()
                if hasattr(path, "__html__")
                else format_html('<script src="{}"></script>', self.absolute_path(path))
            )
            for path in self._js
        ]