我在提供 CORS 请求之间遇到了延迟,但可以正常处理直接请求。我正在使用它通过 HTTP 分发媒体流,因此减少启动延迟非常重要。
从通过 CloudFront 分配(通过来自浏览器或 curl 的直接请求)提供媒体清单到我们网站上的播放器发出的 CORS 请求返回成功之间大约有 90-180 秒。我已经在 CloudFront 分配中启用了 OPTIONS 请求转发,并且也包含了 OPTIONS 请求的结果。我在下面的 Chrome 开发工具中包含了 curl 请求的结果和网络选项卡的相应结果。请注意,这些请求是在 15 秒内从同一客户端发出的(首先发送 curl 请求)。
=== CURL 请求 ===
* Trying 54.192.135.101...
* Connected to <exampleDistributionID>.cloudfront.net (1.1.1.1) port 443 (#0)
* ALPN, offering http/1.1
* Cipher selection: ALL:!EXPORT:!EXPORT40:!EXPORT56:!aNULL:!LOW:!RC4:@STRENGTH
* successfully set certificate verify locations:
* CAfile: /opt/local/share/curl/curl-ca-bundle.crt
CApath: none
* TLSv1.2 (OUT), TLS header, Certificate Status (22):
* TLSv1.2 (OUT), TLS handshake, Client hello (1):
* TLSv1.2 (IN), TLS handshake, Server hello (2):
* TLSv1.2 (IN), TLS handshake, Certificate (11):
* TLSv1.2 (IN), TLS handshake, Server key exchange (12):
* TLSv1.2 (IN), TLS handshake, Server finished (14):
* TLSv1.2 (OUT), TLS handshake, Client key exchange (16):
* TLSv1.2 (OUT), TLS change cipher, Client hello (1):
* TLSv1.2 (OUT), TLS handshake, Finished (20):
* TLSv1.2 (IN), TLS change cipher, Client hello (1):
* TLSv1.2 (IN), TLS handshake, Finished (20):
* SSL connection using TLSv1.2 / ECDHE-RSA-AES128-GCM-SHA256
* ALPN, server accepted to use http/1.1
* Server certificate:
* subject: C=US; ST=Washington; L=Seattle; O=Amazon.com, Inc.; CN=*.cloudfront.net
* start date: Sep 17 00:00:00 2015 GMT
* expire date: Dec 15 23:59:59 2016 GMT
* subjectAltName: <exampleDistributionID>.cloudfront.net matched
* issuer: C=US; O=Symantec Corporation; OU=Symantec Trust Network; CN=Symantec Class 3 Secure Server CA - G4
* SSL certificate verify ok.
> GET /path/to/manifest/stream.m3u8 HTTP/1.1
> Host: <exampleDistributionID>.cloudfront.net
> User-Agent: curl/7.47.1
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: application/vnd.apple.mpegurl
< Content-Length: 1435
< Connection: keep-alive
< Server: nginx/1.9.10
< Date: Sun, 17 Apr 2016 00:26:06 GMT
< Last-Modified: Sun, 17 Apr 2016 00:26:05 GMT
< ETag: "5712d81d-59b"
< Cache-Control: no-cache
< Access-Control-Allow-Origin: *
< Accept-Ranges: bytes
< X-Cache: Miss from cloudfront
< Via: 1.1 f687c6e8ce478528ab87681ac35779ab.cloudfront.net (CloudFront)
< X-Amz-Cf-Id: P01_dDWZRWZ0lzAqROqOMnaipstK484vPWnicw3F0kcG_7elxBGNkQ==
<...Content of stream.m3u8...>
===Chrome 请求===
显示收到的 404 错误的 Chrome 开发工具网络选项卡的屏幕截图
===选项请求===
* Trying 1.1.1.1...
* Connected to <exampleDistributionID>.cloudfront.net (1.1.1.1) port 443 (#0)
* ALPN, offering http/1.1
* Cipher selection: ALL:!EXPORT:!EXPORT40:!EXPORT56:!aNULL:!LOW:!RC4:@STRENGTH
* successfully set certificate verify locations:
* CAfile: /opt/local/share/curl/curl-ca-bundle.crt
CApath: none
* TLSv1.2 (OUT), TLS header, Certificate Status (22):
* TLSv1.2 (OUT), TLS handshake, Client hello (1):
* TLSv1.2 (IN), TLS handshake, Server hello (2):
* TLSv1.2 (IN), TLS handshake, Certificate (11):
* TLSv1.2 (IN), TLS handshake, Server key exchange (12):
* TLSv1.2 (IN), TLS handshake, Server finished (14):
* TLSv1.2 (OUT), TLS handshake, Client key exchange (16):
* TLSv1.2 (OUT), TLS change cipher, Client hello (1):
* TLSv1.2 (OUT), TLS handshake, Finished (20):
* TLSv1.2 (IN), TLS change cipher, Client hello (1):
* TLSv1.2 (IN), TLS handshake, Finished (20):
* SSL connection using TLSv1.2 / ECDHE-RSA-AES128-GCM-SHA256
* ALPN, server accepted to use http/1.1
* Server certificate:
* subject: C=US; ST=Washington; L=Seattle; O=Amazon.com, Inc.; CN=*.cloudfront.net
* start date: Sep 17 00:00:00 2015 GMT
* expire date: Dec 15 23:59:59 2016 GMT
* subjectAltName: <exampleDistributionID>.cloudfront.net matched
* issuer: C=US; O=Symantec Corporation; OU=Symantec Trust Network; CN=Symantec Class 3 Secure Server CA - G4
* SSL certificate verify ok.
> OPTIONS /path/to/manifest/stream.m3u8 HTTP/1.1
> Host: <exampleDistributionID>.cloudfront.net
> User-Agent: curl/7.47.1
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: text/plain
< Content-Length: 0
< Connection: keep-alive
< Server: nginx/1.9.10
< Date: Sun, 17 Apr 2016 22:05:15 GMT
< Access-Control-Allow-Origin: http://my.origin.com
< Access-Control-Allow-Methods: GET, OPTIONS
< Access-Control-Allow-Headers: Authorization
< Access-Control-Allow-Credentials: true
< X-Cache: Miss from cloudfront
< Via: 1.1 ed2825b48bb51b4febd93a82e71f7ed9.cloudfront.net (CloudFront)
< X-Amz-Cf-Id: WY-KPfTlNTenTjWyYF9GS4ikyrGMQONAm4mXpbuKpHzfBk_xKfxG2w==
<
* Connection #0 to host <exampleDistributionID>.cloudfront.net left intact
不知所措地看到我的配置中的错误,任何帮助将不胜感激。
默认情况下,CloudFront 通过将错误响应缓存 5 分钟来尝试保护源服务器免受对不可用对象的不必要请求。
从这个问题中可以明显看出,最可能的解释是对象在它实际存在之前被请求(无论出于何种原因),并且错误响应被缓存了几分钟,导致似乎是“延迟“在对象的可用性中。但是 CloudFront 没有传播延迟,因为 CloudFront 是一个直通式缓存——没有什么可以传播的。
您的
curl
测试似乎成功,但实际上未能证明任何事情,显然是因为(以及其他潜在原因)您没有Origin:
在curl
请求中包含标头。这使得curl
请求在语义上与浏览器发送的请求不同。在评估是否可以从缓存中提供对象时,CloudFront 不仅仅考虑路径。大多数转发到源服务器的标头也会进行比较,如果要与此请求一起转发的标头与先前请求发送的标头与可用的缓存响应不匹配,则不会使用缓存的响应, 而一个请求将被发送到源。它的响应将与发送的标头一起缓存。
因此,以下两个请求:
和
...是(假设
Origin:
标头被转发到源服务器,因为它需要用于 CORS)被视为两个不同的、本质上不相关的请求,这是必要的——CloudFront 不知道源服务器是否可能会修改其基于发送的请求标头的响应。对这两个请求的响应将被分别缓存,并且它们中的每一个都只会在响应未来的匹配请求时提供服务。如果分发被配置为转发 cookie 或查询字符串,这些也会与缓存的响应一起存储,这些响应只会在响应与生成缓存响应的原始请求完全匹配的请求时提供 - 基于所有转发参数。(这就是为什么不必要地转发你的源服务器不需要的信息会损害你的缓存率。)
将分发的404 错误的错误缓存最小 TTL设置为 0 可以通过阻止缓存 404 响应来解决此问题。