I am working on setting up amazon cloud front and have been playing around with the cache-control settings. It is explicitly stated here, that amazon-cloudfront will not follow a 301 and 307.
I am wondering if there is documentation on if the redirect will be followed if the origin returns a 308?
It seems a little strange that 302 and 308 are not mentioned, here, but CloudFront does not follow redirects. They are stored in the cache and returned to the browser.
You can intercept redirects with a Lambda#Edge response trigger, but the typical application for this is to rewrite the Location header and send the browser somewhere other than where it would otherwise have gone.
For small responses, it's possible to actually follow the redirect using an Origin Response trigger that makes a request using the Node HTTP client, but this only suports responses up to 1 MB in total size, and would probably not perform as well as simply letting the browser follow the redirect.
There is some additional documentation here of handling redirects:
If you change the location of an object on the origin server, you can
configure your web server to redirect requests to the new location.
After you configure the redirect, the first time a viewer submits a
request for the object, CloudFront Front sends the request to the
origin, and the origin responds with a redirect (for example, 302
Moved Temporarily). CloudFront caches the redirect and returns it to
the viewer. CloudFront does not follow the redirect.
You can configure your web server to redirect requests to one of the
following locations:
The new URL of the object on the origin server. When the viewer follows the redirect to the new URL, the viewer bypasses CloudFront
and goes straight to the origin. As a result, we recommend that you
not redirect requests to the new URL of the object on the origin.
The new CloudFront URL for the object. When the viewer submits the request that contains the new CloudFront URL, CloudFront gets the
object from the new location on your origin, caches it at the edge
location, and returns the object to the viewer. Subsequent requests
for the object will be served by the edge location. This avoids the
latency and load associated with viewers requesting the object from
the origin. However, every new request for the object will incur
charges for two requests to CloudFront.
But because 301 and 308 only difference is that 308
does not allow changing the request method from POST to GET
i would guess that it is handled like 301.
The documentation has since original post been updated to include info on 301, 302, 304, 307 and 308.
Related
Note: My site is in production mode, not testing. It is pending verification due to me adding an icon. This issue persisted before the verification was started.
Whenever my browser makes a request to Google for the one-tap widget or the pill, both requests return 400 Bad Request with an empty HTML page and the console is sent a message stating "The given origin is not allowed for the given client ID." I've gone onto the Google Cloud Console and checked my origins. I have only one listed, and it's the exact site I'm sending requests from my browser. My site also has its traffic proxied through Cloudflare if that makes a difference. In addition, I am using JavaScript callbacks (which work when used in PI#1).
Potential issue #1: The URLs are typed in wrong
When I insert localhost (I add https and http because I test with a HTTPS webserver locally using a Cloudflare origin certificate), the requests go through perfectly. However, the moment the requests are from my browser when it's not localhost, the requests fail. I've copied and pasted straight from the URL bar just to make sure that there's no typos or anything but the same results return.
Potential issue #2: The widget is making bad requests
I do open the URLs in other tabs (Which yield the same results from PI#1) and insert bogus URLs like example.com and thisisnotaurl.com to ensure it's not just dropping every request. Those requests return 403 Forbidden instead of 400 Bad Request.
Potential issue #3: The issue is browser specific
I've checked this issue on both Firefox and Microsoft Edge, both on the stable branches and completely up to date. I've disabled my ad block (UBlock Origin & Firefox built-in protection) to ensure they aren't messing with requests but everything except the crucial requests fail with 400 Bad Request. I have yet to test other browsers as I do not have them installed but I assume the same results come from them.
An example of the code can be found here: https://gist.github.com/Coder-Tavi/772ea25b16f3fa0b6b0e04739a1689dd.
The origins shown below are the exact website I am accessing. In addition, I've verified the client IDs are exactly the same as the ones I have added
Referrer Policy is improperly configured
The HTTP header Referrer-Policy controls the exact amount of data sent to servers regarding the origin of the request. In most cases, this is set to same-origin which means that the Referer header will send the origin to servers with the same origin.
Consider you have a webserver at example.com and another at web.example.com with a Referrer-Policy of same-origin. When example.com sends a request to web.example.com, the Referer header will contain the origin of the request, since it is the same origin. However, if example.com sends a request to google.com, the Referer header will not send any origin data, as google.com and example.com are not the same origin.
If we look at the requests, this directive is what we see
As such, we need to update the directive to allow the browser to send the origin in the Referer header. This can be done by inserting the following into the HTML of the current page.
<meta name="referrer" content="origin">
This meta tag will allow the browser to send the origin only to other webservers, and as such, Google will see the origin.
Consider the example above again. This time, when example.com sends a request to google.com, the request will contain a Referer header with the origin, as the directive allows for sharing of the origin. However, with this current policy, only the origin is sent, not the query parameters and other parts of the URL. With the following URL: https://example.com/test/123, google.com will only see https://example.com. The MDN Web Docs contain all the possible values and their effects.
AWS Cloudfront document says:
If you set the TTL for a particular origin to 0, CloudFront will still
cache the content from that origin. It will then make a GET request
with an If-Modified-Since header, thereby giving the origin a chance
to signal that CloudFront can continue to use the cached content if it
hasn't changed at the origin
I need to configure my Dynamic Content. I have already set TTL to 0.. I want every request to go to Origin always. Is there a way I avoid this additional GET request with an If-Modified-Since header ! Why this extra request everytime !
Is there a way I avoid this additional GET request
It sounds as if you are misinterpreting the what you are reading. Unfortunately, you didn't cite the source, so it's difficult to go back and pick up more context; however, this is not referring to an "extra" request.
It will then make a GET request with an If-Modified-Since header
This refers to each time the object is subsequently requested by a browser. CloudFront sends the next request with If-Modified-Since: so that your origin server has the option of returning a 304 Not Modified response... it doesn't send two requests to the origin in response to one request from a browser.
If your content is always dynamic, return Cache-Control: private, no-cache, no-store and set Minimum TTL to 0.
http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/Expiration.html#ExpirationDownloadDist
This is the answer I got from AWS:
However, if you forward all headers for that particular origin, the
request will go to the origin every time without the If-Modified-Since
header mentioned [1]. Please view the excerpt from the link below for
further detail:
“Forward all headers to your origin Important If you configure
CloudFront to forward all headers to your origin, CloudFront doesn't
cache the objects associated with this cache behavior. Instead, it
sends every request to the origin.”
I have a webstack that is currently serving both dynamic and static content. I want start serving the static content from AWS CloudFront without having to change all of the urls.
So I set up CloudFront to serve the static content from AWS S3 and the dynamic content from a custom url (current webstack). This worked however CloudFront was making the request to our webstack via a rewrite rule.
Is it possible for CloudFront to return a 302 redirect so that the request to my webstack would come from the users browser?
Unfortunately this is critical for our application to work properly.
I don't think it's possible, because CloudFront should follow 302 redirects and cache the result, rather than return the 302 redirect to the client.
Hi I have a dynamic application that has a search form. I'm trying to use CloudFront with a load balancer. When you do a search the application creates some URL parameters and reloads the page. For some reason cloudfront is doing a 302 redirect back to the origin. Does anybody know how to fix this?
I have the following configuration.
It's clear that you're going to want to turn on Forward Query Strings. Without it, cloudfront will treat the following urls as the same:
http://www.example.com
http://www.example.com?q=search_term
http://www.example.com?q=search_term&option=true
It's however not clear to me that this would result in 302 to the original url (btw. origin means something very specific when dealing with cloudfront/other cdns - it's often short for origin server which is the source behind the cdn)
The 302 redirect is much more likely to your Viewer Protocol Policy, which you have set http requests to redirect to http. You should double check that your application isn't reloading the http version of the page.
I'm trying to make Cloudfront work on my solution. I'm using Route 53 + CloudFront + ELB.
Consider the following:
1. Route 53 is pointing to CloudFront through a record set alias.
2. CloudFront is pointing to the ELB through a origin domain name.
3. CloudFront has an Alternate Domain Name set to my custom domain (mysite.com)
If I make a request using the CloudFront domain name (d1ngxxxx.cloudfront.net) or the custom domain (mysite.com), the initial request goes to CloudFront which responds with a HTTP 302. All the subsequent requests (for resources like images, css, js..) are made directly to the ELB domain name bypassing CloudFront.
What should I do to make all requests go throuhg CloudFront?
Thanks is advance!
I can't come up with a circumstance where Cloudfront would issue these redirects.
It seems likely that what's happening is that your server itself is issuing the 302 redirect, because it doesn't like the Host: header it's getting from Cloudfront.
Host: CloudFront sets the value to the domain name of the origin that is associated with the requested object.
— http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/RequestAndResponseBehaviorCustomOrigin.html
Cloudfront is then returning the redirect to the browser.
Cloudfront can also cache such a redirect, so be mindful of that as you're troubleshooting. The response headers should indicate whether cloudfront went to the origin for the particular reponse:
X-Cache: Miss from cloudfront
...or whether cloudfront served the request from cache.
X-Cache: Hit from cloudfront
Two possible approaches to resolve this:
If your legacy code is reacting to the Host: header in a negative way, you might be able to reconfigure the web server to modify that value before the code is able to see it, so the redirection wouldn't occur.
Alternately, you could use something outboard, a reverse-proxying engine like Varnish or HAProxy (of which I have touched on elsewhere). In HAProxy, for a simple example:
reqirep ^Host:\ .* Host:\ expected-domain.example.com if { hdr(host) -i unexpected-domain.example.com }
A rule in form similar to this would replace the Host: unexpected-domain.example.com header with Host: expected-domain.example.com in all incoming requests where that header was present, which should keep your legacy code happy and avoid the redirects. Running HAProxy in front of your legacy system doesn't impose a significant load, since the code is very tight. All of my legacy web systems are now fronted with these systems, to give me the ability to manipulate and modify behavior much more easily than might otherwise be possible.