def get_rendition_or_not_found_patch(image, filter):
    """
    This function is a monkey patch of wagtail.images.shortcuts.get_rendition_or_not_found (v2.1).
    Here, we try to find the requested rendition in Python before calling the original function.

    Wagtail's (v2.1) 'get_rendition_or_not_found' uses the ORM's 'get' method to lookup every image rendition,
    which causes a database request for every image we render. This implementation is really slow.

    Even worse, this method does not respect prefetch_related('renditions') so we cannot optimize this tag using
    ORM wizardry alone.

    This fix will allow you to use prefetch_related on renditions and grab all your renditions in one query.
    If you do not use prefetch related, then this function performs roughly as bad as it did before.
    """
    if type(filter) is str:
        filter = Filter(spec=filter)

    filter_spec = filter.spec
    focal_point_key = filter.get_cache_key(image)

    # This loop assumes that you've prefetched your image's renditions
    rendition = None
    for rend in image.renditions.all():
        if rend.filter_spec == filter_spec and rend.focal_point_key == focal_point_key:
            rendition = rend

    if not rendition:
        rendition = get_rendition_or_not_found(image, filter)

    return rendition
Beispiel #2
0
    def test_cache_key_fill_filter_with_focal_point(self):
        image = Image(
            width=1000,
            height=1000,
            focal_point_width=100,
            focal_point_height=100,
            focal_point_x=500,
            focal_point_y=500,
        )
        fil = Filter(spec='fill-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '0bbe3b2f')
    def test_cache_key_fill_filter_with_focal_point(self):
        image = Image(
            width=1000,
            height=1000,
            focal_point_width=100,
            focal_point_height=100,
            focal_point_x=500,
            focal_point_y=500,
        )
        fil = Filter(spec='fill-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '0bbe3b2f')
Beispiel #4
0
    def test_cache_key_fill_filter(self):
        image = Image(width=1000, height=1000)
        fil = Filter(spec='fill-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '2e16d0ba')
Beispiel #5
0
    def test_cache_key(self):
        image = Image(width=1000, height=1000)
        fil = Filter(spec='max-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '')
    def test_cache_key_fill_filter(self):
        image = Image(width=1000, height=1000)
        fil = Filter(spec='fill-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '2e16d0ba')
    def test_cache_key(self):
        image = Image(width=1000, height=1000)
        fil = Filter(spec='max-100x100')
        cache_key = fil.get_cache_key(image)

        self.assertEqual(cache_key, '')
Beispiel #8
0
    def _import_metadata_images(self):
        has_changed = False

        if self.publisher_logo_src_original and not self.publisher_logo:
            try:
                self.publisher_logo, created = self._image_from_url(
                    urljoin(self.original_url,
                            self.publisher_logo_src_original),
                    title="%s logo" % self.publisher,
                )
                has_changed = True
            except requests.exceptions.RequestException:
                pass

        if self.poster_portrait_src_original and not self.poster_image:
            try:
                portrait_image_file = self._image_file_from_url(
                    urljoin(self.original_url,
                            self.poster_portrait_src_original))
                self.poster_image, created = self._image_from_image_file(
                    portrait_image_file, title=self.title)
                has_changed = True
            except requests.exceptions.RequestException:
                created = False

            if created:
                # Pre-generate renditions for whichever of portrait, square and landscape poster images
                # have been supplied, indexed under PORTRAIT_IMAGE_FILTER, SQUARE_IMAGE_FILTER
                # and LANDSCAPE_IMAGE_FILTER respectively so that when we look those up again we get
                # the original appropriately-cropped version
                portrait_filter = Filter(self.PORTRAIT_IMAGE_FILTER)
                self.poster_image.renditions.create(
                    filter_spec=self.PORTRAIT_IMAGE_FILTER,
                    file=portrait_image_file,
                    focal_point_key=portrait_filter.get_cache_key(
                        self.poster_image))

                if self.poster_square_src_original:
                    square_filter = Filter(self.SQUARE_IMAGE_FILTER)
                    try:
                        self.poster_image.renditions.create(
                            filter_spec=self.SQUARE_IMAGE_FILTER,
                            file=self._image_file_from_url(
                                urljoin(self.original_url,
                                        self.poster_square_src_original)),
                            focal_point_key=square_filter.get_cache_key(
                                self.poster_image))
                    except requests.exceptions.RequestException:
                        pass

                if self.poster_landscape_src_original:
                    landscape_filter = Filter(self.LANDSCAPE_IMAGE_FILTER)
                    try:
                        self.poster_image.renditions.create(
                            filter_spec=self.LANDSCAPE_IMAGE_FILTER,
                            file=self._image_file_from_url(
                                urljoin(self.original_url,
                                        self.poster_landscape_src_original)),
                            focal_point_key=landscape_filter.get_cache_key(
                                self.poster_image))
                    except requests.exceptions.RequestException:
                        pass

        return has_changed