How to make cloudfront not cache any html file - amazon-s3

I have a React application served on S3, with CloudFront. I know it's a common question on how to not cache the index.html file. I could make it work changing the Behavior of CloudFront distribution, but the issue I am facing is different.
Basically, on a SPA all URL are redirected to /, so React knows how to serve each one. My issue is that when I try to access https://mywebsite.com/login, a login.html is served from CloudFront (even if I don't have this file). This file is actually index.html. My issue is that the Behavior of CloudFront distribution doesn't work for this path, and a cached index.html file is served.
I tried to change the Path Pattern to be /*.html, but this is not a valid config in CloudFront.
My question is: what's the best way to tell CloudFront that I don't want to cache any html files, and that I want to hit S3 on every request of a html file?
Thank you!

Related

Cloudfront behavior path redirect to root of S3 bucket

I want to create a behavior in my Cloudfront distribution that will redirect to S3. I want all requests to /site to get redirected to S3. The problem is that as I understand there should be a folder in S3 with /site name, the problem with that is it breaks the paths for the resources requested in my html.
If I create a /site folder and add my index.html and the relative js/css files, that are references from inside html without the /site prefix then the styling/js is not working. I don't have the ability to change the path in the html files as they are generated automatically by a tool.
Is there a way to do a redirect but point to the root of the S3 instead of creating a folder there?

ListBucketResult xml trying to show home page of site in S3 thorugh CloudFront

I created a bucket where I´m hosting my static website.
I set the properties to use it as static website hosting (which index document value index.html)
The URL was: http://mywebsitelearningcurve.s3-website-us-east-1.amazonaws.com (not currently up, just to explain)
I exposed it as public (permission).
Overview of my bucket
/images
/static
/asset-manifest.json
/favicon.ico
/index.html
/manifest.json
/service-worker.js
Using http://mywebsitelearningcurve.s3-website-us-east-1.amazonaws.com I could access to my site. However I decided to use CloudFront in front of my bucket.
I created a new distribution for WEB.
On Origin Domain Name I used mywebsitelearningcurve.s3.amazonaws.com
Origin ID: S3-mywebsitelearningcurve
In Viewer Protocol Policy I selected: Redirect HTTP to HTTPS.
Once it finished and I waited for a prudential time to propagate, I had the url https://d2qf2r44tssakh.cloudfront.net/ (not currently up, just to explain).
The issue:
When I tried to use https://d2qf2r44tssakh.cloudfront.net/ it showed me a xml
<ListBucketResult xmlns="http://s3.amazonaws.com/doc/2006-03-01/"><Name>mywebsitelearningcurve</Name>
...
...
...
</ListBucketResult>
However, when I tried https://d2qf2r44tssakh.cloudfront.net/index.html it works properly.
I go through several tutos and post but I can´t still make it work. Anyone can provide help?
Thanks
I had the same problem today and was able to fix it by adding index.html to the Default Root Object in the distribution settings:
Optional. The object that you want CloudFront to return (for example,
index.html) when a viewer request points to your root URL
(http://www.example.com) instead of to a specific object in your
distribution (http://www.example.com/index.html).
i had 5 years prod experience on AWS with 5 certifications in place.
When it comes to s3 + cloudfront, i got always in troubles
I tried to automate that using Cloudformation, but Cloudformation does not support everything needed (.i.e. custom origin in cloudfront).
At the end, i relies only on terraform to automate this part:
https://github.com/riboseinc/terraform-aws-s3-cloudfront-website/blob/master/sample-site/main.tf
If you don't mind to use terraform, i highly recommend to jump there.

Resolve S3 static page from custom path with CloudFront

I've got an S3 bucket configured to host a static website, and if I browse to the bucket URL it shows the index.html file. I also have a CloudFront distribution to show another S3 bucket under a custom domain. Is there any chance I could configure CloudFront to serve one bucket from the root and another from a custom path? So:
mydomain.com -> bucket1/index.html
mydomain.come/some-path -> bucket2/index.html
I already created an origin for the bucket and set up a path pattern for it and some-path, but I'm getting 403 Forbidden, even though if I browse to the origin directly I can see the webpage.
This configuration works fine, but it requires that the object in bucket2 be located at some-path/index.html inside bucket2.
The path pattern you configured in the cache behavior is still part of the request path, so it is forwarded to the origin.
CloudFront does not support removing part of the request path before forwarding the request to the origin.

Access js and css files from API gateway and lambda

I have an API Gateway in AWS that calls a a lambda function that returns some html. That html is then properly rendered on the screen but without any styles or js files included. How do I get those to the client as well? Is there a better method than creating /js and /css GET endpoints on the API Gateway to go get those files? I was hoping I could just store them in S3 and they'd get autoloaded from there.
Store them on S3, and enable S3 static website hosting. Then include the correct URL to those assets in the HTML.
I put in the exact address of each js/css file I wanted to include in my html. You need to use https address, not the http address of the bucket. Each file has it's own https address which can be found by following Mark B's instructions above. Notably, going through the AWS admin console, navigate to the file in the S3 bucket, click the "Properties" button in the upper right, copy the "Link" field, and post that into the html file (which was also hosted in S3 in my case). Html looks like this:
<link href="https://s3-us-west-2.amazonaws.com/my-bucket-name/css/bootstrap.min.css" rel="stylesheet">
I don't have static website hosting enabled on the bucket. I don't have any CORS permissions allowing reading from a certain host.

Serving Angular JS HTML templates from S3 and CloudFront - CORS problems

I'm having a doozy of a time trying to serve static HTML templates from Amazon CloudFront.
I can perform a jQuery.get on Firefox for my HTML hosted on S3 just fine. The same thing for CloudFront returns an OPTIONS 403 Forbidden. And I can't perform an ajax get for either S3 or CloudFront files on Chrome. I assume that Angular is having the same problem.
I don't know how it fetches remote templates, but it's returning the same error as a jQuery.get. My CORS config is fine according to Amazon tech support and as I said I can get the files directly from S3 on Firefox so it works in one case.
My question is, how do I get it working in all browsers and with CloudFront and with an Angular templateUrl?
For people coming from google, a bit more
Turns out Amazon actually does support CORS via SSL when the CORS settings are on an S3 bucket. The bad part comes in when cloudfront caches the headers for the CORS response. If you're fetching from an origin that could be mixed http & https you'll run into the case where the allowed origin from CloudFront will say http but you want https. That of course causes the browser to blow up. To make matters worse, CloudFront will cache slightly differing versions if you accept compressed content. Thus if you try to debug this with curl, you'll think all is well then find it isn't in the browser (try passing --compressed to curl).
One, admittedly frustrating, solution is just ditch the entire CloudFront thing and serve directly from the S3 bucket.
It looks like Amazon does not currently support SSL and CORS on CloudFront or S3, which is the crux of the problem. Other CDNs like Limelight or Akamai allow you to add your SSL cert to a CNAME which circumvents the problem, but Amazon does not allow that either and other CDNs are cost prohibitive. The best alternative seems to be serving the html from your own server on your domain. Here is a solution for Angular and Rails: https://stackoverflow.com/a/12180837/256066