Thumbnails for Django

Overview

Jazzband sorl-thumbnail on PyPI Documentation for latest version gh-actions Coverage

Thumbnails for Django.

Features at a glance

  • Support for Django 2.2, 3.0 and 3.1 following the Django supported versions policy
  • Python 3 support
  • Storage support
  • Pluggable Engine support for Pillow, ImageMagick, PIL, Wand, pgmagick, and vipsthumbnail
  • Pluggable Key Value Store support (cached db, redis, and dynamodb by AWS)
  • Pluggable Backend support
  • Admin integration with possibility to delete
  • Dummy generation (placeholders)
  • Flexible, simple syntax, generates no html
  • ImageField for model that deletes thumbnails (only compatible with django 1.2.5 or less)
  • CSS style cropping options
  • Back smart cropping, and remove borders from the images when cropping
  • Margin calculation for vertical positioning
  • Alternative resolutions versions of a thumbnail

Read more in the documentation (latest version)

Developers

Jazzband

This is a Jazzband project. By contributing you agree to abide by the Contributor Code of Conduct and follow the guidelines.

Feel free to create a new Pull request if you want to propose a new feature. If you need development support or want to discuss with other developers join us in the channel #sorl-thumnbnail at freenode.net or Gitter.

For releases updates and more in deep development discussion use our mailing list in Google Groups.

Tests

The tests should run with tox and pytest. Running tox will run all tests for all environments. However, it is possible to run a certain environment with tox -e <env>, a list of all environments can be found with tox -l. These tests require the dependencies of the different engines defined in the documentation. It is possible to install these dependencies into a vagrant image with the Vagrantfile in the repo.

User Support

If you need help using sorl-thumbnail browse http://stackoverflow.com/questions/tagged/sorl-thumbnail and posts your questions with the sorl-thumbnail tag.

How to Use

Get the code

Getting the code for the latest stable release use 'pip'.

$ pip install sorl-thumbnail

Install in your project

Then register 'sorl.thumbnail', in the 'INSTALLED_APPS' section of your project's settings.

INSTALLED_APPS = [
    'django.contrib.auth',
    'django.contrib.admin',
    'django.contrib.sites',
    'django.contrib.comments',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.contenttypes',

    'sorl.thumbnail',
]

Templates Usage

All of the examples assume that you first load the thumbnail template tag in your template.:

{% load thumbnail %}

A simple usage.

{% thumbnail item.image "100x100" crop="center" as im %}
    <img src="{{ im.url }}" width="{{ im.width }}" height="{{ im.height }}">
{% endthumbnail %}

See more examples in the section Template examples in the Documentation

Model Usage

Using the ImageField that automatically deletes references to itself in the key value store and its thumbnail references and the thumbnail files when deleted. Please note that this is only compatible with django 1.2.5 or less.:

from django.db import models
from sorl.thumbnail import ImageField

class Item(models.Model):
    image = ImageField(upload_to='whatever')

See more examples in the section Model examples in the Documentation

Low level API

You can use the 'get_thumbnail':

from sorl.thumbnail import get_thumbnail
from sorl.thumbnail import delete

im = get_thumbnail(my_file, '100x100', crop='center', quality=99)
delete(my_file)

See more examples in the section Low level API examples in the Documentation

Using in combination with other thumbnailers

Alternatively, you load the templatetags by {% load sorl_thumbnail %} instead of traditional {% load thumbnail %}. It's especially useful in projects that do make use of multiple thumbnailer libraries that use the same name (thumbnail) for the templatetag module:

{% load sorl_thumbnail %}
{% thumbnail item.image "100x100" crop="center" as im %}
    <img src="{{ im.url }}" width="{{ im.width }}" height="{{ im.height }}">
{% endthumbnail %}

Frequently asked questions

Is so slow in Amazon S3!

Possible related to the implementation of your Amazon S3 Backend, see the issue #351 due the storage backend reviews if there is an existing thumbnail when tries to generate the thumbnail that makes an extensive use of the S3 API

A fast workaround if you are not willing to tweak your storage backend is to set:

THUMBNAIL_FORCE_OVERWRITE = True

So it will avoid to overly query the S3 API.

Comments
  • Refactor QA setup

    Refactor QA setup

    Fixes jazzband-roadies/help#182

    Some notable changes:

    • Deprecate explicit support for Python 3.4 and 3.5 in order to simplify the test matrix.
    • Clean up the test runner setup with tox and Travis
    opened by aleksihakli 22
  • Serious performance issues in 12.2 (AWS S3)

    Serious performance issues in 12.2 (AWS S3)

    Hello,

    There is a serious performance issue in current 12.2 branch. Problem is that we have ~2M thumbnails, so if execution goes here (marked line):

    # /sorl/thumbnail/base.py:101 (get_thumbnail)
            # We have to check exists() because the Storage backend does not
            # overwrite in some implementations.
            if not thumbnail.exists(): # <---- This is the root of the problem!
                try:
                    source_image = default.engine.get_image(source)
                except IOError:
                    if settings.THUMBNAIL_DUMMY:
                        return DummyImageFile(geometry_string)
                    else:
                        # if S3Storage says file doesn't exist remotely, don't try to
                        # create it and exit early.
                        # Will return working empty image type; 404'd image
                        logger.warn(text_type('Remote file [%s] at [%s] does not exist'),
                                    file_, geometry_string)
    
                        return thumbnail
    
                # We might as well set the size since we have the image in memory
                image_info = default.engine.get_image_info(source_image)
                options['image_info'] = image_info
                size = default.engine.get_image_size(source_image)
                source.set_size(size)
    
                try:
                    self._create_thumbnail(source_image, geometry_string, options,
                                           thumbnail)
                    self._create_alternative_resolutions(source_image, geometry_string,
                                                         options, thumbnail.name)
                finally:
                    default.engine.cleanup(source_image)
    

    it is actually asks boto to return LIST of all stored thumbnails (without even using prefix), so appliction hangs with 100% CPU and high memory usage (well, not a surprise actually).

    Wouldn't it be better to provide a prefix for lookup (constructed with the same function as used to store thumbnail) ?

    In a mean time we've had to revert to 11.12.1b which works better.

    This is related to a fix introduced in #92

    Performance 
    opened by pySilver 18
  • Django 1.7 problem?

    Django 1.7 problem?

    Hello I am experiencing problems with sorl and django 1.7 (testing environment):

    (zenbframework)vagrant@precise64:/python-projects/zenbframework/zenframework$ pip freeze
    Django==1.7b1
    Pillow==2.4.0
    argparse==1.2.1
    django-braces==1.4.0
    django-crispy-forms==1.4.0
    django-mptt==0.6.0
    redis==2.9.1
    six==1.6.1
    sorl-thumbnail==11.12
    unicode-slugify==0.1.1
    wsgiref==0.1.2
    

    My settings:

    INSTALLED_APPS = (
        'django.contrib.admin',
        'django.contrib.auth',
        'django.contrib.contenttypes',
        'django.contrib.sessions',
        'django.contrib.messages',
        'django.contrib.staticfiles',
    
        'sorl.thumbnail',
        'posts',
        'news',
    )
    

    Trying to run migrate (replaces syncdb):

    (zenbframework)vagrant@precise64:/python-projects/zenbframework/zenframework$ ./manage.py migrate
    Traceback (most recent call last):
      File "./manage.py", line 10, in <module>
        execute_from_command_line(sys.argv)
      File "/home/vagrant/.virtualenvs/zenbframework/local/lib/python2.7/site-packages/django/core/management/__init__.py", line 427, in execute_from_command_line
        utility.execute()
      File "/home/vagrant/.virtualenvs/zenbframework/local/lib/python2.7/site-packages/django/core/management/__init__.py", line 391, in execute
        django.setup()
      File "/home/vagrant/.virtualenvs/zenbframework/local/lib/python2.7/site-packages/django/__init__.py", line 21, in setup
        apps.populate(settings.INSTALLED_APPS)
      File "/home/vagrant/.virtualenvs/zenbframework/local/lib/python2.7/site-packages/django/apps/registry.py", line 85, in populate
        app_config = AppConfig.create(entry)
      File "/home/vagrant/.virtualenvs/zenbframework/local/lib/python2.7/site-packages/django/apps/config.py", line 120, in create
        "cannot import name '%s' from '%s'" % (cls_name, mod_path))
    ImportError: cannot import name 'thumbnail' from 'sorl'
    
    opened by petkostas 18
  • PNG files haven't transparency.

    PNG files haven't transparency.

    Hi, how are you?

    Here have a new issue, i think.

    My png file haven't background color, have transparency, and, when i upload using sorl-thumbnail's ImageField the image have black background color, see:

    sorl-thumbnailissue

    How can we fix this bug?

    opened by SalahAdDin 17
  • Deprecated `TEMPLATE_DEBUG` setting is required by sorl-thumbnail

    Deprecated `TEMPLATE_DEBUG` setting is required by sorl-thumbnail

    The TEMPLATE_DEBUG setting which was deprecated in Django 1.8 and 1.9, and is missing from 1.10's docs (so I assume it's now obsolete) is required by sorl-thumbnail.

    Without a TEMPLATE_DEBUG setting I get this when I try and use the {% thumbnail ... %} tag in a template:

    'Settings' object has no attribute 'TEMPLATE_DEBUG'

    If I add it to my settings, the template tag works.

    opened by philgyford 16
  • Issue with transparent PNGs: IOError(

    Issue with transparent PNGs: IOError("cannot use transparency for this mode")

    I'm trying to use sorl with pretty basic configuration (only change being THUMBNAIL_PRESERVE_FORMAT = True). Unfortunately, for some images (for example https://dl.dropboxusercontent.com/u/35354297/4.png), it fails with this traceback:

    Traceback (most recent call last):
      File "/Users/xaralis/Workspace/adventura/adv/app/models/photos.py", line 54, in get_thumbnail_in_format
        return get_thumbnail(img, **f['opts'])
      File "/Users/xaralis/.virtualenvs/adventura/src/sorl-thumbnail/sorl/thumbnail/shortcuts.py", line 8, in get_thumbnail
        return default.backend.get_thumbnail(file_, geometry_string, **options)
      File "/Users/xaralis/.virtualenvs/adventura/src/sorl-thumbnail/sorl/thumbnail/base.py", line 118, in get_thumbnail
        thumbnail)
      File "/Users/xaralis/.virtualenvs/adventura/src/sorl-thumbnail/sorl/thumbnail/base.py", line 151, in _create_thumbnail
        default.engine.write(image, options, thumbnail)
      File "/Users/xaralis/.virtualenvs/adventura/src/sorl-thumbnail/sorl/thumbnail/engines/base.py", line 142, in write
        progressive=progressive
      File "/Users/xaralis/.virtualenvs/adventura/src/sorl-thumbnail/sorl/thumbnail/engines/pil_engine.py", line 227, in _get_raw_data
        image.save(bf, **params)
      File "/Users/xaralis/.virtualenvs/adventura/lib/python2.7/site-packages/PIL/Image.py", line 1468, in save
        save_handler(self, fp, filename)
      File "/Users/xaralis/.virtualenvs/adventura/lib/python2.7/site-packages/PIL/PngImagePlugin.py", line 584, in _save
        raise IOError("cannot use transparency for this mode")
    IOError: cannot use transparency for this mode
    

    Which actually leads here: https://github.com/python-imaging/Pillow/blob/master/PIL/PngImagePlugin.py#L584. It looks like the sorl is giving some bad image data to PIL.

    Options passed to get_thumbnail are following:

    {'quality': 80, 'geometry_string': '1600x1200'}

    critical possible-duplicated 
    opened by xaralis 15
  • Do there any blockers to bump new release?

    Do there any blockers to bump new release?

    We are looking forward to using sorl-thumbnail with Django 3.2 on edX.

    Required PR - #674 is already merged into the master branch. Do there any chance a new version will be bumped soon?

    If any blockers with the release I would be happy to help.

    Thank you in advance.

    opened by jramnai 14
  • fix SuspiciousOperation in regex filters

    fix SuspiciousOperation in regex filters

    If the path is prefixed with MEDIA_URL it will be replaced with MEDIA_ROOT (updated in 1b0ba0d)

    Related to #251

    ~~The SuspiciousOperation is raised here if the read of the image gets permission denied. In many cases where this is wrong it is because the path given is /media/... which may refer to MEDIA_ROOT not /media.~~

    bug 
    opened by relekang 14
  • Getting thumbnail from S3 is still slow

    Getting thumbnail from S3 is still slow

    I'm running the latest version (34e1ffa2) and I'm (still) trying to optimize pages with a lot of thumbnails. This time, I'm running into troubles with our Amazon S3 storage. Getting thumbnails stored on there can take over a second per thumbnail unless it's cached, which does not always to seem the case. I hoped the replacement of exists() mentioned in #92 would fix my issue, but alas, it's still taking a very long time. A page with about 15 thumbnails on it can take up to 10-15 seconds to load because of this. I hope you guys can give me any pointers.

    I've used the same line profiling decorator as I mentioned in #232 which clearly adds some loading time (over 2 seconds per thumbnail), but it shows a notable difference between a cached thumbnail and one which has to be retrieved from S3:

    Example of a cached thumbnail:

    File: sorl/thumbnail/base.py
    Function: get_thumbnail at line 61
    Total time: 0.00121 s
    
    Line #      Hits         Time  Per Hit   % Time  Line Contents
    ==============================================================
        61                                               @profile_each_line
        62                                               def get_thumbnail(self, file_, geometry_string, **options):
        63                                                   """
        64                                                   Returns thumbnail as an ImageFile instance for file with geometry and
        65                                                   options given. First it will try to get it from the key value store,
        66                                                   secondly it will create it.
        67                                                   """
        68         1            4      4.0      0.3          logger.debug(text_type('Getting thumbnail for file [%s] at [%s]'), file_,
        69         1            9      9.0      0.7                       geometry_string)
        70         1            1      1.0      0.1          if file_:
        71         1           14     14.0      1.2              source = ImageFile(file_)
        72                                                   elif settings.THUMBNAIL_DUMMY:
        73                                                       return DummyImageFile(geometry_string)
        74                                                   else:
        75                                                       return None
        76
        77                                                   #preserve image filetype
        78         1            6      6.0      0.5          if settings.THUMBNAIL_PRESERVE_FORMAT:
        79                                                       options.setdefault('format', self._get_format(file_))
        80
        81        10           13      1.3      1.1          for key, value in self.default_options.items():
        82         9           12      1.3      1.0              options.setdefault(key, value)
        83
        84
        85                                                   # For the future I think it is better to add options only if they
        86                                                   # differ from the default settings as below. This will ensure the same
        87                                                   # filenames being generated for new options at default.
        88         4            6      1.5      0.5          for key, attr in self.extra_options:
        89         3           10      3.3      0.8              value = getattr(settings, attr)
        90         3            4      1.3      0.3              if value != getattr(default_settings, attr):
        91                                                           options.setdefault(key, value)
        92         1          327    327.0     27.0          name = self._get_thumbnail_filename(source, geometry_string, options)
        93         1           13     13.0      1.1          thumbnail = ImageFile(name, default.storage)
        94         1          787    787.0     65.0          cached = default.kvstore.get(thumbnail)
        95         1            3      3.0      0.2          if cached:
        96         1            1      1.0      0.1              return cached
    

    Example of a thumbnail retrieved from S3:

    File: sorl/thumbnail/base.py
    Function: get_thumbnail at line 61
    Total time: 2.30476 s
    
    Line #      Hits         Time  Per Hit   % Time  Line Contents
    ==============================================================
        61                                               @profile_each_line
        62                                               def get_thumbnail(self, file_, geometry_string, **options):
        63                                                   """
        64                                                   Returns thumbnail as an ImageFile instance for file with geometry and
        65                                                   options given. First it will try to get it from the key value store,
        66                                                   secondly it will create it.
        67                                                   """
        68         1            4      4.0      0.0          logger.debug(text_type('Getting thumbnail for file [%s] at [%s]'), file_,
        69         1           14     14.0      0.0                       geometry_string)
        70         1            2      2.0      0.0          if file_:
        71         1           16     16.0      0.0              source = ImageFile(file_)
        72                                                   elif settings.THUMBNAIL_DUMMY:
        73                                                       return DummyImageFile(geometry_string)
        74                                                   else:
        75                                                       return None
        76
        77                                                   #preserve image filetype
        78         1            8      8.0      0.0          if settings.THUMBNAIL_PRESERVE_FORMAT:
        79                                                       options.setdefault('format', self._get_format(file_))
        80
        81        10           16      1.6      0.0          for key, value in self.default_options.items():
        82         9           14      1.6      0.0              options.setdefault(key, value)
        83
        84
        85                                                   # For the future I think it is better to add options only if they
        86                                                   # differ from the default settings as below. This will ensure the same
        87                                                   # filenames being generated for new options at default.
        88         4            7      1.8      0.0          for key, attr in self.extra_options:
        89         3           18      6.0      0.0              value = getattr(settings, attr)
        90         3            6      2.0      0.0              if value != getattr(default_settings, attr):
        91                                                           options.setdefault(key, value)
        92         1          493    493.0      0.0          name = self._get_thumbnail_filename(source, geometry_string, options)
        93         1           20     20.0      0.0          thumbnail = ImageFile(name, default.storage)
        94         1        29609  29609.0      1.3          cached = default.kvstore.get(thumbnail)
        95         1            2      2.0      0.0          if cached:
        96                                                       return cached
        97                                                   else:
        98                                                       # We have to check exists() because the Storage backend does not
        99                                                       # overwrite in some implementations.
       100                                                       # so we make the assumption that if the thumbnail is not cached, it doesn't exist
       101         1           19     19.0      0.0              print 'No cached thumbnail'
       102         1            2      2.0      0.0              try:
       103         1      1078407 1078407.0     46.8                  source_image = default.engine.get_image(source)
       104                                                       except IOError:
       105                                                           if settings.THUMBNAIL_DUMMY:
       106                                                               return DummyImageFile(geometry_string)
       107                                                           else:
       108                                                               # if S3Storage says file doesn't exist remotely, don't try to
       109                                                               # create it and exit early.
       110                                                               # Will return working empty image type; 404'd image
       111                                                               logger.warn(text_type('Remote file [%s] at [%s] does not exist'), file_, geometry_string)
       112                                                               return thumbnail
       113
       114                                                       # We might as well set the size since we have the image in memory
       115         1           15     15.0      0.0              image_info = default.engine.get_image_info(source_image)
       116         1            2      2.0      0.0              options['image_info'] = image_info
       117         1            8      8.0      0.0              size = default.engine.get_image_size(source_image)
       118         1            7      7.0      0.0              source.set_size(size)
       119         1            2      2.0      0.0              try:
       120         1            3      3.0      0.0                  self._create_thumbnail(source_image, geometry_string, options,
       121         1       998498 998498.0     43.3                                         thumbnail)
       122         1           11     11.0      0.0                  self._create_alternative_resolutions(source_image, geometry_string,
       123         1          223    223.0      0.0                                                       options, thumbnail.name)
       124                                                       finally:
       125         1           13     13.0      0.0                  default.engine.cleanup(source_image)
       126
       127                                                   # If the thumbnail exists we don't create it, the other option is
       128                                                   # to delete and write but this could lead to race conditions so I
       129                                                   # will just leave that out for now.
       130         1         1139   1139.0      0.0          default.kvstore.get_or_set(source)
       131         1       196181 196181.0      8.5          default.kvstore.set(thumbnail, source)
       132         1            3      3.0      0.0          return thumbnail
    
    Performance 
    opened by Gwildor 14
  • Improve Cropping Behavior

    Improve Cropping Behavior

    sorl-thumbnail has been a great asset in our Django based web project however the implementation of cropping left a little to be desired (or at least the implementation didn't make a lot of sense to me) so I made some modifications.

    I modified the cropping behavior in the following ways:

    1. The crop parameter now takes x,y coordinates of the top left corner as well as width/height of the crop region.
    2. Cropping occurs before scalling.

    Feel free to merge this into the main project if you also feel that this is an improvement. If you have any additional notes I will be happy to make further modifications if this isn't exactly what you had in mind.

    new-feature needs-tests needs-docs 
    opened by sethdenner 14
  • Release a new version to PyPI - support Django 4.1 and Pillow 9.2.0.

    Release a new version to PyPI - support Django 4.1 and Pillow 9.2.0.

    Hi,

    I would like to see a new version of sorl-thumbnail on PyPI:

    • Officially support Django 4.0, 4.1 and Python 3.9, 3.10 on PyPI.
    • Remove DeprecationWarning with Pillow up to version 9.2.0 [https://github.com/jazzband/sorl-thumbnail/issues/695].

    Commit https://github.com/jazzband/sorl-thumbnail/commit/8d7bd407be95f3dafdc2ad800b51194cada3599e should be included in the new version.

    Currently, Pillow 9.0.1 is the last version supported by sorl-thumbnail without DeprecationWarning.

    opened by uri-rodberg 13
  • "Schematic view of how things are done" link in the documentation is dead

    Doc URL: https://sorl-thumbnail.readthedocs.io/en/latest/operation.html

    Targeted URL: https://docs.google.com/drawings/edit?id=1wlE4LkQpzXd2a2Nxfjt6_j5NG7889dzMyf0V-xPAJSE&hl=en

    Error:

    image

    opened by gustavi 1
  • Django 4.1 template tag 'thumbnail' conflict with easy-thumbnails

    Django 4.1 template tag 'thumbnail' conflict with easy-thumbnails

    Django 4.1 added a system check to find duplicate template tags at startup. If easy-thumbnails and sorl-thumbnails are installed in the same project, it will detect the possible clash and will exit with an error. This happens even if the tags are not used in any template.

    SystemCheckError: System check identified some issues:
    
    ERRORS:
    ?: (templates.E003) 'thumbnail' is used for multiple template tag modules: 'easy_thumbnails.templatetags.thumbnail', 'sorl.thumbnail.templatetags.thumbnail'
    

    I've added a minimal reproduction here: https://github.com/MarcoGlauser/template_tag_conflict Simply run a manage.py command like makemigrations

    Related: https://github.com/SmileyChris/easy-thumbnails/issues/609

    opened by MarcoGlauser 1
  • Setting storage class does not support deconstructors

    Setting storage class does not support deconstructors

    When setting the storage, sorl does not allow for a class instance being deconstructible, which is necessary to be able to use backends with arguments.

    sorl.thumbnails.images.py

    cls = self.storage._wrapped.__class__
    

    For a deconstructible class this can use self.storage.deconstruct (checking whether the class is deconstructible first to ensure backwards compatibility).

    deserialize could check whether the storage is a list (deconstructible) or a single value (old method)

    opened by michjnich 0
  • `FileNotFoundError` when developing locally after upgrading to `12.8.0` and django 3.

    `FileNotFoundError` when developing locally after upgrading to `12.8.0` and django 3.

    Hi,

    When developing locally without the media files available, I keep getting FileNotFoundError printed to the console. I'm calling sorl.thumbnail.get_thumbnail directly (i.e, without using the templatetags.

    backend_1   |   File "/opt/venv/lib/python3.9/site-packages/sorl/thumbnail/base.py", line 104, in get_thumbnail
    backend_1   |     source_image = default.engine.get_image(source)
    backend_1   |   File "/opt/venv/lib/python3.9/site-packages/sorl/thumbnail/engines/pil_engine.py", line 72, in get_image
    backend_1   |     buffer = BytesIO(source.read())
    backend_1   |   File "/opt/venv/lib/python3.9/site-packages/sorl/thumbnail/images.py", line 162, in read
    backend_1   |     f = self.storage.open(self.name)
    backend_1   |   File "/opt/venv/lib/python3.9/site-packages/django/core/files/storage.py", line 38, in open
    backend_1   |     return self._open(name, mode)
    backend_1   |   File "/opt/venv/lib/python3.9/site-packages/django/core/files/storage.py", line 243, in _open
    backend_1   |     return File(open(self.path(name), mode))
    backend_1   | FileNotFoundError: [Errno 2] No such file or directory: '/workspace/media/posts/image-72.png'
    

    I tried to use the DUMMY config, but the error continue.

    I believe that before when I was on django==2.2.2 and sorl-thumbnail==12.5.0 this error was getting suppressed somehow.

    Using:

             'sorl.thumbnail': {
                 'handlers': ['null'],
             },
    

    Works, but I don't want to suppress every sorl-thumbnail error.

    Looking at https://github.com/jazzband/sorl-thumbnail/blob/master/sorl/thumbnail/base.py#L106, and comparing with the 12.5.0 version, I couldn't find any difference, so it must be a new Django default that I'm missing.

    Does anyone have any ideas here? Thanks!

    opened by slig 0
  • Obsolete THUMBNAIL_KVSTORE

    Obsolete THUMBNAIL_KVSTORE

    I think that the configurable KVStore adds complexity to the project without real added value, all the more that now Django also includes a Redis cache backend in core. What about only keeping THUMBNAIL_CACHE to point to some Django-configured cache and tell users to do the cache configuration at the Django project level?

    Are there still use cases to implement/specify custom KVStores that are not possible as Django cache backends?

    @camilonova, would love to get your input on this idea.

    opened by claudep 1
Releases(12.9.0)
  • 12.9.0(Aug 29, 2022)

    What's Changed

    • Rebase thumbnail management command on BaseCommand by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/686
    • Update Python and Django version metadata by @Flimm in https://github.com/jazzband/sorl-thumbnail/pull/689
    • fix: Pillow Image.ANTIALIAS deprecation warning by @dulmandakh in https://github.com/jazzband/sorl-thumbnail/pull/696
    • Added support for Django 4.1. by @uri-rodberg in https://github.com/jazzband/sorl-thumbnail/pull/699
    • Set development status to stable by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/690
    • Dropped Python 3.6/Django 2.2 and 3.1 support. by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/702
    • Add basic pre-commit config. by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/704
    • Avoid some more recent pillow warnings by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/705
    • Updated URLs in various locations. by @claudep in https://github.com/jazzband/sorl-thumbnail/pull/706
    • sorl/thumbnail/engines/pil_engine.py - Changed code to a more readable format. by @uri-rodberg in https://github.com/jazzband/sorl-thumbnail/pull/708

    New Contributors

    • @dulmandakh made their first contribution in https://github.com/jazzband/sorl-thumbnail/pull/696

    Full Changelog: https://github.com/jazzband/sorl-thumbnail/compare/12.8.0...12.9.0

    Source code(tar.gz)
    Source code(zip)
Django URL Shortener is a Django app to to include URL Shortening feature in your Django Project

Django URL Shortener Django URL Shortener is a Django app to to include URL Shortening feature in your Django Project Install this package to your Dja

Rishav Sinha 4 Nov 18, 2021
Meta package to combine turbo-django and stimulus-django

Hotwire + Django This repository aims to help you integrate Hotwire with Django ?? Inspiration might be taken from @hotwired/hotwire-rails. We are sti

Hotwire for Django 31 Aug 9, 2022
django-reversion is an extension to the Django web framework that provides version control for model instances.

django-reversion django-reversion is an extension to the Django web framework that provides version control for model instances. Requirements Python 3

Dave Hall 2.8k Jan 2, 2023
Django-environ allows you to utilize 12factor inspired environment variables to configure your Django application.

Django-environ django-environ allows you to use Twelve-factor methodology to configure your Django application with environment variables. import envi

Daniele Faraglia 2.7k Jan 7, 2023
Rosetta is a Django application that eases the translation process of your Django projects

Rosetta Rosetta is a Django application that facilitates the translation process of your Django projects. Because it doesn't export any models, Rosett

Marco Bonetti 909 Dec 26, 2022
Cookiecutter Django is a framework for jumpstarting production-ready Django projects quickly.

Cookiecutter Django Powered by Cookiecutter, Cookiecutter Django is a framework for jumpstarting production-ready Django projects quickly. Documentati

Daniel Feldroy 10k Dec 31, 2022
Django project starter on steroids: quickly create a Django app AND generate source code for data models + REST/GraphQL APIs (the generated code is auto-linted and has 100% test coverage).

Create Django App ?? We're a Django project starter on steroids! One-line command to create a Django app with all the dependencies auto-installed AND

imagine.ai 68 Oct 19, 2022
django-quill-editor makes Quill.js easy to use on Django Forms and admin sites

django-quill-editor django-quill-editor makes Quill.js easy to use on Django Forms and admin sites No configuration required for static files! The ent

lhy 139 Dec 5, 2022
A Django chatbot that is capable of doing math and searching Chinese poet online. Developed with django, channels, celery and redis.

Django Channels Websocket Chatbot A Django chatbot that is capable of doing math and searching Chinese poet online. Developed with django, channels, c

Yunbo Shi 8 Oct 28, 2022
A handy tool for generating Django-based backend projects without coding. On the other hand, it is a code generator of the Django framework.

Django Sage Painless The django-sage-painless is a valuable package based on Django Web Framework & Django Rest Framework for high-level and rapid web

sageteam 51 Sep 15, 2022
A beginner django project and also my first Django project which involves shortening of a longer URL into a short one using a unique id.

Django-URL-Shortener A beginner django project and also my first Django project which involves shortening of a longer URL into a short one using a uni

Rohini Rao 3 Aug 8, 2021
Dockerizing Django with Postgres, Gunicorn, Nginx and Certbot. A fully Django starter project.

Dockerizing Django with Postgres, Gunicorn, Nginx and Certbot ?? Features A Django stater project with fully basic requirements for a production-ready

null 8 Jun 27, 2022
pytest-django allows you to test your Django project/applications with the pytest testing tool.

pytest-django allows you to test your Django project/applications with the pytest testing tool.

pytest-dev 1.1k Dec 14, 2022
APIs for a Chat app. Written with Django Rest framework and Django channels.

ChatAPI APIs for a Chat app. Written with Django Rest framework and Django channels. The documentation for the http end points can be found here This

Victor Aderibigbe 18 Sep 9, 2022
django-dashing is a customisable, modular dashboard application framework for Django to visualize interesting data about your project. Inspired in the dashboard framework Dashing

django-dashing django-dashing is a customisable, modular dashboard application framework for Django to visualize interesting data about your project.

talPor Solutions 703 Dec 22, 2022
Django-MySQL extends Django's built-in MySQL and MariaDB support their specific features not available on other databases.

Django-MySQL The dolphin-pony - proof that cute + cute = double cute. Django-MySQL extends Django's built-in MySQL and MariaDB support their specific

Adam Johnson 504 Jan 4, 2023
Django-Audiofield is a simple app that allows Audio files upload, management and conversion to different audio format (mp3, wav & ogg), which also makes it easy to play audio files into your Django application.

Django-Audiofield Description: Django Audio Management Tools Maintainer: Areski Contributors: list of contributors Django-Audiofield is a simple app t

Areski Belaid 167 Nov 10, 2022
django Filer is a file management application for django that makes handling of files and images a breeze.

django Filer is a file management application for django that makes handling of files and images a breeze.

django CMS Association 1.6k Jan 6, 2023
Twitter Bootstrap for Django Form - A simple Django template tag to work with Bootstrap

Twitter Bootstrap for Django Form - A simple Django template tag to work with Bootstrap

tzangms 557 Oct 19, 2022