Check file extension in template - Django

Asked

Viewed 666 times

7

I have a Django application where in the template I need to validate a file extension coming from filefield.

<div class="row">
  <p class="anexos">
    {% trans 'Anexos' %}
  </p>
  #if .jpg .png
  <div class="col-sm-3 col-md-2">
    <img class="img-thumbnail" src="{[{ anexo.trajeto }]}"/>
  </div>
  #elif .mp4 .avi
  <div class="col-sm-3 col-md-2">
    <img class="video-thumbnail" src="{[{ anexo.trajeto }]}"/>
  </div>
  #elif .zip
  <a href="{[{ anexo.trajeto }]}">Arquivo Compactado</a>
  #endif
</div>

How do I solve this problem?

  • That one {[{ anexo.trajeto }]} that’s the way it is, or it would be {{ anexo.trajeto }}? I’ve never seen this syntax before, if it’s right, what it does?

2 answers

4


You can use the filter slice, it works the same way as the array slicing python. That is, if you want the extension, just look at the last 4 characters of the file name (assuming a 3 letter extension, but can adapt to other type extensions .jpeg).

Example (note: I haven’t tested, I have little experience with template tags, I’m not sure if it is possible to compare elements this way)

#if .jpg .png
{% if anexo.trajeto|slice:"-4:" == ".jpg" or
      anexo.trajeto|slice:"-4:" == ".png" %}
<div class="col-sm-3 col-md-2">
<img class="img-thumbnail" src="{{ anexo.trajeto }}"/>
</div>
#elif .mp4 .avi
{% elif anexo.trajeto|slice:"-4:" == ".mp4" or
        anexo.trajeto|slice:"-4:" == ".avi" %}
...

Source: that answer in Soen. Anyway, I would suggest doing this at view instead of the template, if possible (already delivering the file extension pro template in the form of a simple variable).

3

In addition to the mgibsonbr solution, I would prefer to make a template so that you can reuse logic in other templates.

seuprojeto/seuapp/templatetags/extensao.py

from django import template
register = template.Library()

@register.filter()
def extensao(value):
    # retorna a extensao:
    return value[-4:] 

@register.filter()
def class_da_extensao(value):
    # retorna a class dependendo da extensao:
    ext = value[-4:]
    if ext in ['.jpg', '.png']:
        return 'img-thumbnail'
    elif ext in ['.mp4', '.avi']:
        return 'video-thumbnail'

html template. (in this case I only used the tag class_da_extensao)

{% load extensao %}
<div class="col-sm-3 col-md-2">
   <img class="{{ arquivo|class_da_extensao }}" src="{[{ anexo.trajeto }]}"/>
</div>

Using only extension:

{% load extensao %}
<div class="col-sm-3 col-md-2">
   {% if arquivo|extensao in ".jpg .png" %}
       <img class="img-thumbnail" src="{[{ anexo.trajeto }]}"/>
   {% endif %}
</div>

You can learn more about how to create your template tags at this link: https://docs.djangoproject.com/en/1.8/howto/custom-template-tags/

  • The problem of this solution is html. If it uploads a video file, by the code you are using, it will define a video class in a <img>

  • @jpklzm just repeated the code you put in the question, so your question is bugged.

  • Template tags solves your problem, just adapt to suit the way you want.

  • Your solution makes sense to check the file type, but how will I make the conditional within the template? For example, how do I say that if it is . jpg will output a <img> and with . zip will output a <a href>?

  • 2

    {% if arquivo|extensao == '.jpg' %}...{% endif %}, you must choose how to use, can modify the templatetag, matter of creativity. As I said, is one more solution.

  • 1

    @jpklzm edited the answer and added new example

Show 1 more comment

Browser other questions tagged

You are not signed in. Login or sign up in order to post.