Caching effect on CORS: No 'Access-Control-Allow-Origin' header is present on the requested resource

后端 未结 6 1189
故里飘歌
故里飘歌 2020-12-02 09:05

The short version of this issue is we are seeing the typical CORS error (x has been blocked by CORS policy: No \'Access-Control-Allow-Origin\' header is present on the

相关标签:
6条回答
  • 2020-12-02 09:30

    I was having same problem here is how I solved it. Added Corsrule for wildcard domain(you can choose you origin domain)

    <CORSRule>
        <AllowedOrigin>*</AllowedOrigin>
        <AllowedMethod>GET</AllowedMethod>
        <AllowedMethod>HEAD</AllowedMethod>
        <MaxAgeSeconds>3000</MaxAgeSeconds>
        <AllowedHeader>*</AllowedHeader>
    </CORSRule>
    

    Then go to

    CloudFront Distribution > Origin and Origin Groups > Edit Origin
    

    In your "Origin Custom Headers" fill "Header Name" value "origin" and "Value" to "https://www.yourorigindomain.com"

    When you click on info icon in the right of Origin Custom Headers you will see the message:

    All custom header keys and values you specify here will be included in every >request to this origin. If a header was already supplied in the client request, it is overridden.

    So cloudfront add origin header in every request it made to s3 bucket, wheather you pass it from client or not and cache response the headers.

    You can check access-control-allow-origin: * in response header using

    `curl -i https://cloufrontdistributiondomain.com/example.png`
    

    i.e without passing the host.

    0 讨论(0)
  • 2020-12-02 09:42

    I want to share that we were having the same issue, but in this case, specifically preloading some fonts. We noticed that the combination of S3, CloudFront, and Safari was killing us, so we decided to remove preload and crossorigin="anonymous".

    We were trying to do this:

    <link rel="preload" href="<zzz.cloudfrontUrl.com>" as="font" crossOrigin="anonymous" />

    But safari somehow corrupted the cache and it was giving not allowed access-control-allow-origin but only sometimes.

    Our assumption there is that maybe there is a problem between safari and preload fonts from maybe any CDN and the crossOrigin="anonymous" (which is required).

    Regards.

    0 讨论(0)
  • 2020-12-02 09:51

    https://assets-frontend.kalohq.ink/style.allapps.add899080acbbeed5bb6a7301d234b65.css only returns CORS headers when an "Origin" header is present (which is sent with a CORS request, but not regular requests).

    Here's what happens:

    1. User fetches CSS as part of a no-CORS request (eg, <link rel="stylesheet">). This caches due to the Cache-Control header.
    2. User fetches CSS as part of a CORS request. The response comes from the cache.
    3. CORS check fails, no Access-Control-Allow-Origin header.

    The server is at fault here, it should use the Vary header to indicate its response changes depending on the Origin header (and others). It sends this header in response to CORS requests, but it should send it in response to non-CORS requests too.

    Chrome is somewhat at fault here, as it should use the credentials mode of the request as part of the caching key, so a non-credentialed request (such as those sent by fetch()) shouldn't match items in the cache that were requested with credentials. I think there are other browsers that behave like Chrome here, but Firefox doesn't.

    However, since you're using a CDN, you can't rely on browsers to get this right, as the caching may still happen at the CDN. Adding the correct Vary header is the right fix.

    tl;dr: Add the following header to all of your responses that support CORS:

    Vary: Origin, Access-Control-Request-Headers, Access-Control-Request-Method
    
    0 讨论(0)
  • 2020-12-02 09:51

    We experienced the same problem when migrating our JS to Webpack.

    Our setup is similar:

    • assets are uploaded to an S3 bucket during deployment
    • the bucket is set as the Cloudfront origin

    When migrating to Webpack, we wanted to take advantage of JS sourcemaps for better error reporting to Airbrake. To allow errors to be catched properly, the crossorigin="anonymous" attribute had to be set on the script tags. The reason why is explained here: https://blog.sentry.io/2016/05/17/what-is-script-error.html

    Part of the problem was that CORS response headers were sometimes returned, sometimes not, triggering a CORS errror in the browser. Cloudfront servers were caching the response with OR without the CORS headers, depending on the first client request making a Miss request.

    So two possible outcomes:

    1. First client does not send the Origin request header => Cloudfront server caches the response without CORS headers.
    2. First client sends the Origin request header => Cloudfront server caches the response without CORS headers.

    This made the problem look like it was random, but it was just a matter of race condition (how the first client made the request) and different headers cached on different Cloudfront servers: timing and location dependent. Add to that the fact that browsers might cache these wrong headers...

    So you need to properly configure Cloudront's distribution behavior to:

    • allow and cache preflight (OPTIONS) requests
    • base the cache on CORS request headers (Origin, Access-Control-Request-Headers, Access-Control-Request-Method)

    Here is the configuration that solved our problem.

    S3 bucket / Permissions / CORS configuration:

    <?xml version="1.0" encoding="UTF-8"?>
    <CORSConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/">
    <CORSRule>
        <AllowedOrigin>*</AllowedOrigin>
        <AllowedMethod>GET</AllowedMethod>
        <AllowedMethod>HEAD</AllowedMethod>
        <MaxAgeSeconds>300</MaxAgeSeconds>
        <AllowedHeader>*</AllowedHeader>
    </CORSRule>
    </CORSConfiguration>
    

    Cloudfront distribution / Edit Behavior:


    We now experience a problem similar to yours, as we just migrated our CSS to Webpack. We are experiencing even more sporadic CORS errors for CSS files. We are trying to remove the crossorigin="anonymous" attribute on <link rel="stylesheet" /> tags since we don't need error tracking for CSS files.

    0 讨论(0)
  • 2020-12-02 09:51

    I can shed a little light to how it happened with us. Azure CDN (which we use) does not support Vary: headers right now. So far so bad. But now we use the script crossorigin attribute which - and thats the interesting thing - is not supported by some browsers.

    If now such browser comes to our site, it does not send origin: because it does not understand the "crossorigin" attribute. If later another one comes who understands it, it will send origin: -> CORS Error because first response is cached.

    Ugly.

    0 讨论(0)
  • 2020-12-02 09:56

    Assuming that the CROS configuration has been set in the S3 already, these two points below can make sure that the video will be always loaded on the browser.

    1. Add crossorigin=”anonymous” on the tag
    2. Add the "?q=#{Time.now.to_i}" at the end of the S3 URLs

    HAML + Ruby code will look something like this.

        %video{controls: "", controlslist: "nodownload", crossorigin: 'anonymous'}
         %source{src: "#{s3_url}?q=#{Time.now.to_i}", type: "video/mp4"}
    
    0 讨论(0)
提交回复
热议问题