title: Resize images on the fly in CloudFront and get them in the same URL instantly: AWS CloudFront -> S3 -> Lambda -> CloudFront
body: <p><strong>TLDR:</strong> We have to trick CloudFront 307 redirect caching by creating new cache behavior for responses coming from our Lambda function.</p>
  <p>You will not believe how close we are to achieve this. We have stucked so badly in the last step.</p>
  <p>Business case:</p>
  <p>Our application stores images in S3 and serves them with CloudFront in order to avoid any geographic slow downs around the globe.
  Now, we want to be really flexible with the design and to be able to request new image dimentions directly in the CouldFront URL!
  Each new image size will be created on demand and then stored in S3, so the second time it is requested it will be
  served really quickly as it will exist in S3 and also will be cached in CloudFront.</p>
  <p>Lets say the user had uploaded the image chucknorris.jpg.
  Only the original image will be stored in S3 and wil be served on our page like this:</p>
  <p>//xxxxx.cloudfront.net/chucknorris.jpg</p>
  <p>We have calculated that we now need to display a thumbnail of 200x200 pixels.
  Therefore we put the image src to be in our template:</p>
  <p>//xxxxx.cloudfront.net/chucknorris-200x200.jpg</p>
  <p>When this new size is requested, the amazon web services have to provide it on the fly in the same bucket and with the requested key.
  This way the image will be directly loaded in the same URL of CloudFront.</p>
  <p>I made an ugly drawing with the architecture overview and the workflow on how we are doing this in AWS:</p>
  <p><a href="https://i.stack.imgur.com/rJuh1.png" rel="noreferrer"><img src="https://i.stack.imgur.com/rJuh1.png" alt="enter image description here" /></a></p>
  <p>Here is how Python Lambda ends:</p>
  <pre><code>return {
      'statusCode': '301',
      'headers': {'location': redirect_url},
      'body': ''
  }
  </code></pre>
  <p>The problem:</p>
  <p>If we make the Lambda function redirect to S3, it works like a charm.
  If we redirect to CloudFront, it goes into redirect loop because CloudFront caches 307 (as well as 301, 302 and 303).
  As soon as our Lambda function redirects to CloudFront, CloudFront calls the API Getaway URL instead of fetching the image from S3:</p>
  <p><a href="https://i.stack.imgur.com/4ofTY.png" rel="noreferrer"><img src="https://i.stack.imgur.com/4ofTY.png" alt="enter image description here" /></a></p>
  <p>I would like to create new cache behavior in CloudFront's <code>Behaviors</code> settings tab.
  This behavior should not cache responses from Lambda or S3 (don't know what exactly is happening internally there), but should still cache any followed requests to this very same resized image.
  I am trying to set path pattern <code>-\d+x\d+\..+$</code>, add the ARN of the Lambda function in add &quot;Lambda Function Association&quot;
  and set Event Type <code>Origin Response</code>.
  Next to that, I am setting the &quot;Default TTL&quot; to <code>0</code>.</p>
  <p>But I cannot save the behavior due to some error:</p>
  <p><a href="https://i.stack.imgur.com/vs89F.png" rel="noreferrer"><img src="https://i.stack.imgur.com/vs89F.png" alt="enter image description here" /></a></p>
  <p>Are we on the right way, or is the idea of this &quot;Lambda Function Association&quot; totally different?</p>