[Answer]-How can I efficiently render an image in Django?

1👍

✅

In my opinion, and I think many share this point of view with me, a model shouldn’t be responsible for its representation in HTML, so having model.image.render_tag seems wrong to me.

The only parts in an app that know how to represent anything in HTML should be the views and their templates.

You can have a helper function that generates the HTML for an image, and use it in your views, you can also have a simple_tag that refers to that function so that you can use it in your templates.

If the performance of calling it in your templates is an issue, consider using a better performance template engine – you can refer to this SO answer for a benchmark of template engines -, or you can call that helper function in your view and pass the result(s) to your template via the context.

Update

I’ll demonstrate what I meant above by an example.

# inside html_utils.py

def image_to_html(image):
    return '<img src="%(path)s" title="%(title)s" alt="%(alt)s" />' % {
        'path': image.raw.path,
        'title': image.title,
        'alt': image.alt_text
    }

# inside html_template_utils.py

import html_utils
from django import template

register = template.Library()

@register.simple_tag
def image_tag(image):
    return html_utils.image_to_html(image)

{# inside images_template.html #}

{% load html_template_utils %}

<div class="images-container">
{% for image in images %}
    {% image_tag image %}
{% endfor %}
</div>

The code above uses the image_to_html helper function from the template by using the image_tag simple_tag we created. Another possible way would be by calling image_to_html in the view and passing the results to the template:

# inside views.py

import html_utils

def view_images(request):
    # ...

    images_html = [html_utils.image_to_html(image) for image in images]

    # ...

    return render_to_response('images_template.html', {
        'images_html': images_html
    }, context_instance=RequestContext(request))

{# inside images_template.html #}

<div class="images-container">
{% for image_html in images_html %}
    {{ image_html }}
{% endfor %}
</div>

Leave a comment