-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow configuring caching upon request #534
Comments
That is a great idea! And at the right time, too; I am currently pondering a lot of ideas related to caching, none as good. What should we name the parameter? I would imagine it to directly be how long a Cache-Control max-age should be set to, for browsers to remember. It would then be a number of seconds. |
What about properly using ETags? A simple checksum of the input parameters would suffice, I'd think. |
ETags have no say on cache invalidation. The only way for shields.io to know if the ETag has changed is to call the vendor and perform the computation, which is what takes time. The image download in itself is tiny. |
Note that what I had in mind wasn't for shields.io to cache anything, via etags or otherwise. It's to have an option for it to return caching headers that would make client browsers cache badges for a configurable amount of time. The goal is simply to avoid going to shields.io on every page which contains the badges. I, as the maintainer of a site which uses shields.io, could decide to ask shields.io to add HTTP response headers that would make client browsers cache for, say, 2 minutes or whatever. |
@roji I think we're on the same page. Would setting a Cache-Control max-age be suitable? Maybe via |
@espadrine, I think setting Cache-Control's max-age would be the perfect solution here, I think it's definitely well-defined - it allows browsers to cache for the number of seconds without checking anything with the servers. As you mentioned above, ETags would be useless here because the idea is to eliminate the server request entirely, whereas ETags allow the elimination of the response payload once the cache expires (via max-age). However, since in the shields.io case the payload is negligible this doesn't make much sense. To make things generic I'd make shields.io accept a |
@roji Thanks for your suggestion! It should be live now. |
Thanks @espadrine, but something a bit odd is going on: no matter what I specify in the maxAge URL parameter I always get max-age=7200 in the response headers (https://img.shields.io/teamcity/http/build.npgsql.org/s/npgsql.svg?label=TeamCity&style=plastic&maxAge=50). Also don't forget to update the docs at the bottom of shields.io. Thanks for giving this your attention! |
@espadrine, any response on this bug? Whatever I specify maxAge to be, I always get headers specifying 2 hours... |
It seems like a CloudFlare bug. You can set it to be higher than 2 hours; just not lower. On the plus side, it's just browser caching, so Ctrl+Shift+R forces an update. |
OK, thanks for looking into it! |
Sent to CloudFlare's support:
|
Initially motivated by a CloudFlare cache error (#534).
Hi, Thank you for contacting CloudFlare support. What do you currently have set at your origin server for .svg Cache-Control headers? Let me know and we can investigate this behavior together. Thank you. Hi!
It depends on the parameter ?maxAge (it is set here: Line 174 in 38f9625
You can detect that the parameter returns the correct value by curl -vk 'https://51.254.114.150/gitter/room/nwjs/nw.js.svg?maxAge=50' 2>&1 | grep 'Cache-Control' (Note that I fixed a small issue that was present in the past few days This command bypasses CloudFlare by addressing the IP directly. You The following command goes through CloudFlare: curl -vk 'https://img.shields.io/gitter/room/nwjs/nw.js.svg?maxAge=50' 2>&1 | grep 'Cache-Control' The Cache-Control header, which should be set to the maxAge parameter, Thanks for looking into it! Hi there, That's odd! We should respect any cache-control header that is sent to us. I notice that without the query string maxAge=50 in the URL, the max-age=50 isn't set. Is it possible for you to set that within the headers for the asset as a whole? I would be interested to see if that helps at all.
That is by design, yes. Instead, it sends the following header: Cache-Control: no-cache, no-store, must-revalidate
I find what you ask of me unclear. Upon the reception of a request by Unfortunately, GitHub (where a lot of users put their badges) caches It is not an issue that we currently have with the gitter image, as it curl -vk 'https://51.254.114.150/gitter/room/nwjs/nw.js.svg' 2>&1 | grep 'Cache-Control'
#> < Cache-Control: max-age=50
curl -vk 'https://51.254.114.150/gitter/room/nwjs/nw.js.svg?maxAge=70' 2>&1 | grep 'Cache-Control'
#> < Cache-Control: max-age=50 Hello there, Thanks for that information. I have checked again though, and I see that the Expires header doesn't also respect the extra time here, so the Expires header is the same as the current time. Here's a test I did that shows this- curl -vso /dev/null 'https://51.254.114.150/gitter/room/nwjs/nw.js.svg?maxAge=70' -k ; date
Hi! Thanks a lot for your answer.
My understanding of HTTP headers leads me to believe that this
https://tools.ietf.org/html/rfc7234#section-4.2.1 Is my understanding inaccurate? For the purpose of debugging, I followed your advice by creating a # Direct access
curl -vk 'https://51.254.114.150/flip.svg' 2>&1 | grep 'Expires\|Date\|Cache-Control'
# < Cache-Control: max-age=60
# < Expires: Sat, 14 May 2016 13:25:00 GMT
# < Date: Sat, 14 May 2016 13:24:00 GMT
# CloudFlare access
curl -vk 'https://img.shields.io/flip.svg' 2>&1 | grep 'Expires\|Date\|Cache-Control'
# < Date: Sat, 14 May 2016 13:24:00 GMT
# < Cache-Control: public, max-age=7200
# < Expires: Sat, 14 May 2016 15:24:00 GMT As you can tell, CloudFlare still returns incorrect results, 2 hours That being said, I noticed that the image, which I coded to flip If you'd like me to remove the wildcard to let you perform further |
Hello there, That is very odd! I will check what you mention about the order of precedence of caching headers. We should just use the standard nginx behaviour I believe. If you could disable the page rule you have there, that would be great. If there's another page that you would prefer we use for testing, that's good as well! Hello there, I suspect there's some confusion here. Your settings have a Browser cache expiry of 2 hours (7200s), so it's normal that we present this value to customers. That's the value you see when you cURL the domain. Anything that I'm missing? Or were you trying to assess how often we refresh our cache? Hi!
Clearly, CloudFlare follows the HTTP rules for caching most of the curl -vk 'https://img.shields.io/gitter/room/nwjs/nw.js.svg?maxAge=8000' 2>&1 | grep Cache-Control
# < Cache-Control: public, max-age=8000
# (8000, not 7200, as per the HTTP spec.) When the Cache-Control HTTP header that my server yields has a max-age curl -vk 'https://img.shields.io/gitter/room/nwjs/nw.js.svg?maxAge=60' 2>&1 | grep Cache-Control
# < Cache-Control: public, max-age=7200 HTTP asks of caching proxies to respect the Cache-Control header. Relying on the CloudFlare browser cache expiration setting for Hello there, Let me follow-up on your previous answer:
It's not a bug, this is how the system is designed:
I hope this clarifies the situation, but we're happy to answer your questions further, should you have any. |
It seems that shields.io configures caching headers to cache for very little time, if at all. The result is that if a site has shields on multiple pages, navigating between them provides a poor experience as shields are downloaded again and again.
How about allowing websites to configure how long badges should be cached via a parameter (like
link
,logoWidth
...)?The text was updated successfully, but these errors were encountered: