Example #1
0
    def render(self, value, record, bound_column):
        if not self.links:
            raise NotImplementedError('Links not assigned.')
        if not isinstance(self.links, (list, tuple, dict)):
            raise NotImplementedError('Links must be an iterable.')

        links = []

        for link in self.links:
            title = link['title']
            url = link['url']
            attrs = link['attrs'] if 'attrs' in link else None

            if 'args' in link:
                args = [
                    a.resolve(record) if isinstance(a, A) else a
                    for a in link['args']
                ]
            else:
                args = None

            attrs = AttributeDict(
                attrs if attrs is not None else self.attrs.get('a', {}))

            try:
                attrs['href'] = urlresolvers.reverse(url, args=args)
            except urlresolvers.NoReverseMatch:
                attrs['href'] = url

            links.append('<a {attrs}>{text}</a>'.format(attrs=attrs.as_html(),
                                                        text=mark_safe(title)))

        return mark_safe(self.delimiter.join(links))
Example #2
0
    def render(self, record, value):
        attrs = AttributeDict(self.attrs.get("span", {}))
        classes = [c for c in attrs.get("class", "").split(" ") if c]

        exists = None
        storage = getattr(value, "storage", None)
        if storage:
            # we'll assume value is a `django.db.models.fields.files.FieldFile`
            if self.verify_exists:
                exists = storage.exists(value.name)
        else:
            if self.verify_exists and hasattr(value, "name"):
                # ignore negatives, perhaps the file has a name but it doesn't
                # represent a local path... better to stay neutral than give a
                # false negative.
                exists = os.path.exists(value.name) or exists

        if exists is not None:
            classes.append("exists" if exists else "missing")

        attrs["title"] = value.name
        attrs["class"] = " ".join(classes)

        return format_html(
            "<span {attrs}>{text}</span>",
            attrs=attrs.as_html(),
            text=self.text_value(record, value),
        )
Example #3
0
    def attrs(self):
        '''
        Proxy to `.Column.attrs` but injects some values of our own.

        A ``th`` and ``td`` are guaranteed to be defined (irrespective of
        what's actually defined in the column attrs. This makes writing
        templates easier.
        '''
        # Start with table's attrs; Only 'th' and 'td' attributes will be used
        attrs = dict(self._table.attrs)

        # Update attrs to prefer column's attrs rather than table's
        attrs.update(dict(self.column.attrs))

        # we take the value for 'cell' as the basis for both the th and td attrs
        cell_attrs = attrs.get('cell', {})
        # override with attrs defined specifically for th and td respectively.
        kwargs = {'table': self._table}
        attrs['th'] = computed_values(attrs.get('th', cell_attrs), **kwargs)
        attrs['td'] = computed_values(attrs.get('td', cell_attrs), **kwargs)

        # wrap in AttributeDict
        attrs['th'] = AttributeDict(attrs['th'])
        attrs['td'] = AttributeDict(attrs['td'])

        # Override/add classes
        attrs['th']['class'] = self.get_th_class(attrs['th'])
        attrs['td']['class'] = self.get_td_class(attrs['td'])

        return attrs
Example #4
0
    def render(self, record, value):
        storage = getattr(value, 'storage', None)
        exists = None
        url = None
        if storage:
            # we'll assume value is a `django.db.models.fields.files.FieldFile`
            if self.verify_exists:
                exists = storage.exists(value.name)
            url = storage.url(value.name)

        else:
            if self.verify_exists and hasattr(value, 'name'):
                # ignore negatives, perhaps the file has a name but it doesn't
                # represent a local path... better to stay neutral than give a
                # false negative.
                exists = os.path.exists(value.name) or exists

        tag = 'a' if url else 'span'
        attrs = AttributeDict(self.attrs.get(tag, {}))
        attrs['title'] = value.name

        classes = [c for c in attrs.get('class', '').split(' ') if c]
        if exists is not None:
            classes.append('exists' if exists else 'missing')
        attrs['class'] = ' '.join(classes)

        if url:
            return self.render_link(url, record=record, value=value, attrs=attrs)
        else:
            return format_html(
                '<span {attrs}>{text}</span>',
                attrs=attrs.as_html(),
                text=self.text_value(record, value)
            )
Example #5
0
    def attrs(self):
        """
        Proxy to `.Column.attrs` but injects some values of our own.

        A ``th`` and ``td`` are guaranteed to be defined (irrespective of
        what's actually defined in the column attrs. This makes writing
        templates easier.
        """
        # Work on a copy of the attrs object since we're tweaking stuff
        attrs = dict(self.column.attrs)

        # Find the relevant th attributes (fall back to cell if th isn't
        # explicitly specified).
        attrs["td"] = td = AttributeDict(attrs.get('td', attrs.get('cell',
                                                                   {})))
        attrs["th"] = th = AttributeDict(attrs.get("th", attrs.get("cell",
                                                                   {})))
        # make set of existing classes.
        th_class = set((c for c in th.get("class", "").split(" ") if c))  # pylint: disable=C0103
        td_class = set((c for c in td.get("class", "").split(" ") if c))  # pylint: disable=C0103
        # add classes for ordering
        if self.orderable:
            th_class.add("orderable")
            th_class.add("sortable")  # backwards compatible
        if self.is_ordered:
            th_class.add(
                "desc" if self.order_by_alias.is_descending else "asc")
        # Always add the column name as a class
        th_class.add(self.name)
        td_class.add(self.name)
        if th_class:
            th['class'] = " ".join(sorted(th_class))
        if td_class:
            td['class'] = " ".join(sorted(td_class))
        return attrs
Example #6
0
    def render(self, value, record, bound_column):
        if not self.links:
            raise NotImplementedError('Links not assigned.')
        if not isinstance(self.links, (list, tuple,dict)):
            raise NotImplementedError('Links must be an iterable.')

        links = []

        for link in self.links:
            title = link['title']
            url = link['url']
            attrs = link['attrs'] if 'attrs' in link else None

            if 'args' in link:
                args = [a.resolve(record) if isinstance(a, A) else a for a in link['args']]
            else:
                args = None

            attrs = AttributeDict(attrs if attrs is not None else self.attrs.get('a', {}))

            try:
                attrs['href'] = urlresolvers.reverse(url, args=args)
            except urlresolvers.NoReverseMatch:
                attrs['href'] = url

            links.append('<a {attrs}>{text}</a>'.format(
                attrs=attrs.as_html(),
                text=mark_safe(title)
            ))

        return mark_safe(self.delimiter.join(links))
Example #7
0
def render_attrs(attrs, **kwargs):
    ret = AttributeDict(kwargs)

    if attrs is not None:
        ret.update(attrs)

    return ret.as_html()
Example #8
0
    def render(self, record, value):
        storage = getattr(value, 'storage', None)
        exists = None
        url = None
        if storage:
            # we'll assume value is a `django.db.models.fields.files.FieldFile`
            if self.verify_exists:
                exists = storage.exists(value.name)
            url = storage.url(value.name)

        else:
            if self.verify_exists and hasattr(value, 'name'):
                # ignore negatives, perhaps the file has a name but it doesn't
                # represent a local path... better to stay neutral than give a
                # false negative.
                exists = os.path.exists(value.name) or exists

        tag = 'a' if url else 'span'
        attrs = AttributeDict(self.attrs.get(tag, {}))
        attrs['title'] = value.name

        classes = [c for c in attrs.get('class', '').split(' ') if c]
        if exists is not None:
            classes.append('exists' if exists else 'missing')
        attrs['class'] = ' '.join(classes)

        if url:
            return self.render_link(url, record=record, value=value, attrs=attrs)
        else:
            return format_html(
                '<span {attrs}>{text}</span>',
                attrs=attrs.as_html(),
                text=self.text_value(record, value)
            )
def render_attrs(attrs, **kwargs):
    ret = AttributeDict(kwargs)

    if attrs is not None:
        ret.update(attrs)

    return ret.as_html()
Example #10
0
    def attrs(self):
        """
        Proxy to `.Column.attrs` but injects some values of our own.

        A ``th`` and ``td`` are guaranteed to be defined (irrespective of
        what's actually defined in the column attrs. This makes writing
        templates easier.
        """
        # Work on a copy of the attrs object since we're tweaking stuff
        attrs = dict(self.column.attrs)

        # Find the relevant th attributes (fall back to cell if th isn't
        # explicitly specified).
        attrs['th'] = AttributeDict(attrs.get('th', attrs.get('cell', {})))
        attrs['td'] = AttributeDict(attrs.get('td', attrs.get('cell', {})))

        # make set of existing classes.
        th_class = set((c for c in attrs['th'].get('class', '').split(' ') if c))
        td_class = set((c for c in attrs['td'].get('class', '').split(' ') if c))

        # add classes for ordering
        if self.orderable:
            th_class.add('orderable')
        if self.is_ordered:
            th_class.add('desc' if self.order_by_alias.is_descending else 'asc')

        # Always add the column name as a class
        th_class.add(self.name)
        td_class.add(self.name)

        attrs['th']['class'] = ' '.join(sorted(th_class))
        attrs['td']['class'] = ' '.join(sorted(td_class))
        return attrs
Example #11
0
 def header(self):
     default = {"type": "checkbox",
                "class": "toggle-all",
                }
     general = self.attrs.get('input')
     specific = self.attrs.get('th__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s /> ' % attrs.as_html())
Example #12
0
 def render_link(self, uri, record, value, attrs=None):
     super(OpenColumn, self).render_link(uri, record, value, attrs)
     attrs = AttributeDict(
         attrs if attrs is not None else self.attrs.get('a', {}))
     attrs['href'] = uri
     html = '<a {attrs}><span class="fa fa-{icon}"></span> {text}</a>'.format(
         attrs=attrs.as_html(), icon=self.icon, text='Open')
     return mark_safe(html)
Example #13
0
 def header(self):
     """Render the header cell."""
     default = {"type": "checkbox"}
     general = self.attrs.get("input")
     specific = self.attrs.get("th__input")
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe("<label><input %s/><span></span></label>" %
                      attrs.as_html())  # noqa
 def header(self):
     if self.header_check:
         default = {'type': 'checkbox'}
         general = self.attrs.get('input')
         specific = self.attrs.get('th__input')
         attrs = AttributeDict(default, **(specific or general or {}))
         return mark_safe('<input %s/>' % attrs.as_html())
     else:
         return super(CheckBoxColumn, self).header
    def render(self, value, bound_column, record):
        default = {"type": "checkbox", "name": bound_column.name, "value": value}
        if self.is_checked(value, record):
            default.update({"checked": "checked"})

        general = self.attrs.get("input")
        specific = self.attrs.get("td__input")
        attrs = AttributeDict(default, **(specific or general or {}))
        return mark_safe("<input %s/>" % attrs.as_html())
Example #16
0
 def render(self, value, bound_column):  # pylint: disable=W0221
     default = {
         'type': 'text',
         'name': bound_column.name,
     }
     general = self.attrs.get('input')
     specific = self.attrs.get('td__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #17
0
 def render(self, value, bound_column):  # pylint: disable=W0221
     default = {
         'type': 'text',
         'name': bound_column.name,
     }
     general = self.attrs.get('input')
     specific = self.attrs.get('td__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #18
0
    def render_link(self, uri, value, attrs=None):
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html(
            '<a {attrs}>{text}</a>',
            attrs=attrs.as_html(),
            text=value,
        )
Example #19
0
 def render(self, value, bound_column):
     default = {
         'type': 'checkbox',
         'name': bound_column.name,
         'value': value
     }
     general = self.attrs.get('input')
     specific = self.attrs.get('td__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #20
0
 def render(self, value, bound_column):  # pylint: disable=W0221
     default = {
         'type': 'checkbox',
         'name': bound_column.name,
         'value': value
     }
     general = self.attrs.get('input')
     specific = self.attrs.get('td__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<label><input %s/><span class="lbl"></span></label>' % attrs.as_html())
Example #21
0
    def render_link(self, uri, text, attrs=None):

        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri
        html = '<a {attrs}>{text}</a>'.format(
            attrs=attrs.as_html(),
            text=text.encode('utf-8')
        )
        return mark_safe(html)
Example #22
0
    def render_link(self, uri, text, attrs=None):

        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri
        html = '<a {attrs}>{text}</a>'.format(
            attrs=attrs.as_html(),
            text=text.encode('utf-8')
        )
        return mark_safe(html)
Example #23
0
    def render_link(self, uri, value, attrs=None):
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html(
            '<a {attrs}>{text}</a>',
            attrs=attrs.as_html(),
            text=value,
        )
Example #24
0
 def render(self, value, record, bound_column):
     if self.action:
         url = crud_url(record, self.action)
     else:
         url = record.get_absolute_url()
     attrs = AttributeDict((("href", url),))
     return format_html(
         "<a {attrs}>{text}</a>",
         attrs=attrs.as_html(),
         text=self.action_name,
     )
Example #25
0
 def header(self):
     default = {
         'type': 'checkbox',
         'class': "tableflat",
         'id': "checkboxall",
         'name': 'for_action',
     }
     general = self.attrs.get('input')
     specific = self.attrs.get('th__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #26
0
    def render(self, value, bound_column, record):
        default = {'type': 'radio', 'name': bound_column.name, 'value': value}
        if self.is_checked(value, record):
            default.update({
                'checked': 'checked',
            })

        general = self.attrs.get('input')
        specific = self.attrs.get('td__input')
        attrs = AttributeDict(default, **(specific or general or {}))
        return mark_safe('<input %s/>' % attrs.as_html())
Example #27
0
 def render(self, value, record, bound_column):
     try:
         url = value.get_absolute_url()
     except (AttributeError, NoReverseMatch):
         return force_str(value)
     attrs = AttributeDict((("href", url),))
     return format_html(
         "<a {attrs}>{text}</a>",
         attrs=attrs.as_html(),
         text=value,
     )
Example #28
0
    def render_link(self, uri, text, attrs=None):
        """
        Render a hyperlink.

        :param   uri: URI for the hyperlink
        :param  text: value wrapped in ``<a></a>``
        :param attrs: ``<a>`` tag attributes
        """
        attrs = AttributeDict(attrs if attrs is not None else self.attrs.get("a", {}))
        attrs["href"] = uri
        html = "<a {attrs}>{text}</a>".format(attrs=attrs.as_html(), text=escape(text))
        return mark_safe(html)
Example #29
0
    def attrs(self):
        '''
        Proxy to `.Column.attrs` but injects some values of our own.

        A ``th``, ``td`` and ``tf`` are guaranteed to be defined (irrespective
        of what's actually defined in the column attrs. This makes writing
        templates easier. ``tf`` is not actually a HTML tag, but this key name
        will be used for attributes for column's footer, if the column has one.
        '''

        # prepare kwargs for computed_values()
        kwargs = {
            'table': self._table,
            'bound_column': self,
        }
        # BoundRow.items() sets current_record and current_value when iterating over
        # the records in a table.
        if getattr(self, 'current_record', None) is not None and getattr(
                self, 'current_value', None) is not None:
            kwargs.update({
                'record': self.current_record,
                'value': self.current_value
            })

        # Start with table's attrs; Only 'th' and 'td' attributes will be used
        attrs = dict(self._table.attrs)

        # Update attrs to prefer column's attrs rather than table's
        attrs.update(dict(self.column.attrs))

        # we take the value for 'cell' as the basis for both the th and td attrs
        cell_attrs = attrs.get('cell', {})

        # override with attrs defined specifically for th and td respectively.
        attrs['th'] = computed_values(attrs.get('th', cell_attrs),
                                      kwargs=kwargs)
        attrs['td'] = computed_values(attrs.get('td', cell_attrs),
                                      kwargs=kwargs)
        attrs['tf'] = computed_values(attrs.get('tf', cell_attrs),
                                      kwargs=kwargs)

        # wrap in AttributeDict
        attrs['th'] = AttributeDict(attrs['th'])
        attrs['td'] = AttributeDict(attrs['td'])
        attrs['tf'] = AttributeDict(attrs['tf'])

        # Override/add classes
        attrs['th']['class'] = self.get_th_class(attrs['th'])
        attrs['td']['class'] = self.get_td_class(attrs['td'])
        attrs['tf']['class'] = self.get_td_class(attrs['tf'])

        return attrs
Example #30
0
    def render(self, value, bound_column, record):
        default = {
            "type": "checkbox",
            "name": bound_column.name,
            "value": value
        }
        if self.is_checked(value, record):
            default.update({"checked": "checked"})

        general = self.attrs.get("input")
        specific = self.attrs.get("td__input")
        attrs = AttributeDict(default, **(specific or general or {}))
        return mark_safe("<input %s/>" % attrs.as_html())
Example #31
0
    def __init__(self, id, source=None, params=(), sortable=None,
                 empty_text=None, attrs=None, template=None, data=None):
        """Initialize the table.

        Options that Table supports that affect the data presented are not
        supported in this subclass.  Extra paramters are:

        :param id: The id of the table in the resulting HTML.  You just need
            to provide something that will be unique in the generated page.
        :param source: The URL to get json data from.
        :param params: A tuple of arguments to pass to the get_queryset()
            method.
        :param data: The data to base the table on, if any.
        """
        if data is not None:
            if source is not None or self.source is not None:
                raise AssertionError(
                    "Do not specify both data and source when building a "
                    "DataTablesTable")
            self.params = params
            data_backed_table = True
        else:
            data_backed_table = False
            data = []
            if source is not None:
                self.source = source
        if template is None:
            template = 'ajax_table.html'
        # Even if this is an ajax backed table, we pass data here and patch
        # the queryset in below because of a bootstrapping issue: we want to
        # sort the initial queryset, and this is much cleaner if the table has
        # has its .columns set up which is only done in Table.__init__...
        super(DataTablesTable, self).__init__(
            data=data, sortable=sortable, empty_text=empty_text, attrs=attrs,
            template=template)
        self._full_length = None
        if not data_backed_table:
            self._compute_queryset(params)
        # We are careful about modifying the attrs here -- if it comes from
        # class Meta:-type options, we don't want to modify the original
        # value!
        if self.attrs:
            attrs = AttributeDict(self.attrs)
        else:
            attrs = AttributeDict()
        attrs.update({
            'id': id,
            # Forcing class to display here is a bit specific really.
            'class': 'display',
        })
        self.attrs = attrs
Example #32
0
    def render_link(self, uri, text, attrs=None):
        """
        Render a hyperlink.

        :param   uri: URI for the hyperlink
        :param  text: value wrapped in ``<a></a>``
        :param attrs: ``<a>`` tag attributes
        """
        attrs = AttributeDict(
            attrs if attrs is not None else self.attrs.get('a', {}))
        attrs['href'] = uri
        html = '<a {attrs}>{text}</a>'.format(attrs=attrs.as_html(),
                                              text=escape(text))
        return mark_safe(html)
 def render(self, value, bound_column, record):  # pylint: disable=W0221
     default = {
         'type': 'checkbox',
         'name': bound_column.name,
         'value': value
     }
     if self.is_checked(value, record):
         default.update({
             'checked': 'checked',
         })
     general = self.attrs.get('input')
     specific = self.attrs.get('td__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #34
0
    def render_link(self, uri, text, attrs=None):
        """
        Render a hyperlink.

        :param   uri: URI for the hyperlink
        :param  text: value wrapped in ``<a></a>``
        :param attrs: ``<a>`` tag attributes
        """
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html('<a {attrs}>{text}</a>',
                           attrs=attrs.as_html(),
                           text=text)
Example #35
0
    def test_render_attributes_test(self):
        template = Template('{% load django_tables2 %}{% render_attrs attrs class="table" %}')
        html = template.render(Context({}))
        self.assertEqual(html, 'class="table"')

        html = template.render(Context({"attrs": AttributeDict({"class": "table table-striped"})}))
        self.assertEqual(html, 'class="table table-striped"')
Example #36
0
    def render_link(self, uri, text, attrs=None, get_params_dict={}):
        """
        Render a hyperlink.

        :param   uri: URI for the hyperlink
        :param  text: value wrapped in ``<a></a>``
        :param attrs: ``<a>`` tag attributes
        """
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = "%s%s" % (uri, '' if not get_params_dict else '?'+"&".join( "%s=%s"%item for item in get_params_dict.items() ))
        html = '<a {attrs}>{text}</a>'.format(
            attrs=attrs.as_html(),
            text=escape(text)
        )
        return mark_safe(html)
Example #37
0
 def render(self, value):
     value = bool(value)
     text = self.yesno[int(not value)]
     html = '<span %s>%s</span>'
     attrs = {"class": unicode(value).lower()}
     attrs.update(self.attrs.get("span", {}))
     return mark_safe(html % (AttributeDict(attrs).as_html(), escape(text)))
    def render(self, value, record, bound_column):
        value = self._get_bool_value(record, value, bound_column)
        text = self.yesno[int(not value)]
        attrs = {'class': six.text_type(value).lower()}
        attrs.update(self.attrs.get('span', {}))

        return format_html('<span {}>{}</span>', AttributeDict(attrs).as_html(), escape(text))
Example #39
0
 def header(self):
     default = {'type': 'checkbox'}
     general = self.attrs.get('input')
     specific = self.attrs.get('th__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe(
         self.th__before_input)  # +'<input %s/>' % attrs.as_html())
Example #40
0
 def test_handles_escaping(self):
     # django==3.0 replaces &#39; with &#x27;, drop first option if django==2.2 support is removed
     self.assertIn(
         AttributeDict({
             "x": "\"'x&"
         }).as_html(),
         ('x="&quot;&#39;x&amp;"', 'x="&quot;&#x27;x&amp;"'),
     )
Example #41
0
    def render_link(self, uri, record, value, attrs=None):
        '''
        Render a hyperlink.

        Arguments:
            uri (str): URI for the hyperlink
            record: record currently being rendered
            value (str): value to be wrapped in ``<a></a>``, might be overridden
                by ``self.text``
            attrs (dict): ``<a>`` tag attributes
        '''
        attrs = AttributeDict(
            attrs if attrs is not None else self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html('<a {attrs}>{text}</a>',
                           attrs=attrs.as_html(),
                           text=self.text_value(record, value))
    def render_link(self, uri, record, value, attrs=None):
        """
        Render a link (`<a>`).

        Arguments:
            uri (str): URI for the link
            record: record currently being rendered
            value (str): value to be wrapped in ``<a></a>``, might be overridden
                by ``self.text``
            attrs (dict): ``<a>`` tag attributes
        """
        attrs = AttributeDict(
            attrs if attrs is not None else self.attrs.get("a", {}))
        attrs["href"] = uri

        return format_html("<a {attrs}>{text}</a>",
                           attrs=attrs.as_html(),
                           text=self.text_value(record, value))
Example #43
0
    def render_link(self, uri, record, value, attrs=None):
        """
        Render a hyperlink.

        :param    uri: URI for the hyperlink
        :param record: record currently being rendered
        :param  value: value wrapped in ``<a></a>``, might be overridden by ``self.text``
        :param  attrs: ``<a>`` tag attributes
        """
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html(
            '<a {attrs}>{text}</a>',
            attrs=attrs.as_html(),
            text=self.text_value(record, value)
        )
Example #44
0
    def attrs(self):
        """
        Proxy to `.Column.attrs` but injects some values of our own.

        A ``th`` and ``td`` are guaranteed to be defined (irrespective of
        what's actually defined in the column attrs. This makes writing
        templates easier.
        """
        # Start with table's attrs; Only 'th' and 'td' attributes will be used
        attrs = dict(self.table.attrs)

        # Update attrs to prefer column's attrs rather than table's
        attrs.update(dict(self.column.attrs))

        # Column ordering class names
        ordering_class = attrs.get('th', {}).get('_ordering', {})

        # Find the relevant th attributes (fall back to cell if th isn't
        # explicitly specified).
        attrs['th'] = AttributeDict(attrs.get('th', attrs.get('cell', {})))
        attrs['td'] = AttributeDict(attrs.get('td', attrs.get('cell', {})))

        # make set of existing classes.
        th_class = set(
            (c for c in attrs['th'].get('class', '').split(' ') if c))
        td_class = set(
            (c for c in attrs['td'].get('class', '').split(' ') if c))

        # add classes for ordering
        if self.orderable:
            th_class.add(ordering_class.get('orderable', 'orderable'))
        if self.is_ordered:
            th_class.add(
                ordering_class.get('descending', 'desc') if self.order_by_alias
                .is_descending else ordering_class.get('ascending', 'asc'))

        # Always add the column name as a class
        th_class.add(self.name)
        td_class.add(self.name)

        attrs['th']['class'] = ' '.join(sorted(th_class))
        attrs['td']['class'] = ' '.join(sorted(td_class))
        return attrs
Example #45
0
    def render_link(self, uri, record, value, attrs=None):
        '''
        Render a hyperlink.

        Arguments:
            uri (str): URI for the hyperlink
            record: record currently being rendered
            value (str): value to be wrapped in ``<a></a>``, might be overridden
                by ``self.text``
            attrs (dict): ``<a>`` tag attributes
        '''
        attrs = AttributeDict(attrs if attrs is not None else
                              self.attrs.get('a', {}))
        attrs['href'] = uri

        return format_html(
            '<a {attrs}>{text}</a>',
            attrs=attrs.as_html(),
            text=self.text_value(record, value)
        )
Example #46
0
    def render(self, value, record, bound_column):
        if not self.links:
            raise NotImplementedError("Links not assigned.")
        if not isinstance(self.links, (list, tuple, dict)):
            raise NotImplementedError("Links must be an iterable.")

        links = []
        for link in self.links:
            title = link["title"]
            url = link["url"]
            urlme = None
            attrs = link["attrs"] if "attrs" in link else None

            if "args" in link:
                args = [a.resolve(record) if isinstance(a, A) else a for a in link["args"]]
            else:
                args = None

            if "url" in link and not isinstance(url, str):
                urlme = [a.resolve(record) if isinstance(a, A) else a for a in link["url"]][0]
            else:
                urlme = None

            attrs = AttributeDict(attrs if attrs is not None else self.attrs.get("a", {}))
            try:
                if isinstance(urlme, str):
                    attrs["href"] = urlresolvers.reverse(urlme, args=args)
                else:
                    attrs["href"] = urlresolvers.reverse(url, args=args)
            except urlresolvers.NoReverseMatch:
                if isinstance(urlme, str):
                    attrs["href"] = urlme
                else:
                    attrs["href"] = url

            links.append("<a {attrs}>{text}</a>".format(attrs=attrs.as_html(), text=mark_safe(title)))

        return mark_safe(self.delimiter.join(links))
Example #47
0
    def render(self, value):
        storage = getattr(value, "storage", None)
        exists = None
        url = None
        if storage:
            # we'll assume value is a `django.db.models.fields.files.FieldFile`
            if self.verify_exists:
                exists = storage.exists(value.name)
            url = storage.url(value.name)

        else:
            if self.verify_exists and hasattr(value, "name"):
                # ignore negatives, perhaps the file has a name but it doesn't
                # represent a local path... better to stay neutral than give a
                # false negative.
                exists = os.path.exists(value.name) or exists

        tag = 'a' if url else 'span'
        attrs = AttributeDict(self.attrs.get(tag, {}))
        attrs['title'] = value.name
        if url:
            attrs['href'] = url

        # add "exists" or "missing" to the class list
        classes = [c for c in attrs.get('class', '').split(' ') if c]
        if exists is True:
            classes.append("exists")
        elif exists is False:
            classes.append("missing")
        attrs['class'] = " ".join(classes)

        html = '<{tag} {attrs}>{text}</{tag}>'.format(
            tag=tag,
            attrs=attrs.as_html(),
            text=os.path.basename(value.name))
        return mark_safe(html)
 def header(self):
     default = {"type": "checkbox"}
     general = self.attrs.get("input")
     specific = self.attrs.get("th__input")
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe("<input %s/>" % attrs.as_html())
Example #49
0
 def header(self):
     default = {'type': 'checkbox'}
     general = self.attrs.get('input')
     specific = self.attrs.get('th__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<label><input name="checkall" %s/><span class="lbl"></span></label>' % attrs.as_html())
Example #50
0
 def header(self):
     default = {'type': 'checkbox'}
     general = self.attrs.get('input')
     specific = self.attrs.get('th__input')
     attrs = AttributeDict(default, **(specific or general or {}))
     return mark_safe('<input %s/>' % attrs.as_html())
Example #51
0
def attribute_dict_handles_escaping():
    x = AttributeDict({"x": '"\'x&'})
    assert x.as_html() == 'x="&quot;&#39;x&amp;"'
Example #52
0
 def test_handles_escaping(self):
     x = AttributeDict({'x': '"\'x&'})
     self.assertEqual(x.as_html(), 'x="&quot;&#39;x&amp;"')
Example #53
0
 def test_omits_None(self):
     x = AttributeDict({'x': None})
     self.assertEqual(x.as_html(), '')