Shields has changed the way it presents raster badges – i.e. badges in PNG, GIF, and JPG format.
https://img.shields.io/v/npm/express.png
↪️https://raster.shields.io/v/npm/express.png
What has changed?
img.shields.io renders only SVG and JSON badges.raster.shields.ioraster.shields.ioNote: The legacy raster static badge route, https://img.shields.io/label/message.png has been discontinued. (#3659) URLs of that form should be updated to use one of the modern routes:
Why was this changed?
Shields has always been about SVG badges first, because they look better and perform better.
PNG badges are a fringe but meaningful use case for badges in emails, and services like Slack which don’t support SVG.
Moving rasterization off-board simplifies the responsibilities of the badge server and hardens the server, as it prevents someone from overloading the server with raster requests. (Each raster request used a subprocess, making them much more expensive than SVG badges.)
GIF and JPG were removed because, on a monthly basis, these were barely touched.
Read more: #3112
How does it work?
Notes
.svg with .png in the URL (e.g. https://raster.shields.io/v/npm/express.svg)Acknowledgements
Thanks to the Shields maintainer team, to @styfle whose post about Serverless Chrome on Now 2.0 helped me get this off the ground, and to @neocotic for convert-svg.
Feedback
Your feedback on the new feature is much appreciated! Feel free to comment in this issue with feedback or questions, or in the #support room in Discord.
Related issues
Thanks for taking on this piece of work Paul, it's nice to have separated raster functionality out!
Thanks for the acknowledgement! Great to see my little tool being used. I realised that I haven't touched it in a little while so might go back and see how it's faring. As a user and fan of shields.io, I was wondering if there's anything that you'd like to see specifically.
Thanks for asking @neocotic!
I guess there are two things that might be useful:
@neocotic To add a little more context about why puppeteer-core would be useful: I'd like to publish the web function on npm, and make the app a tiny page that includes just the web function. I've had trouble doing that, in part because I can't just declare the dependencies I want. The env var, for example, must be set when npm install runs. If I could just declare the dependencies, I'd make it easier for people to host their own svg-to-image-proxy without needing to create their own fork.
I noticed that the raster example, badge/label-message-color, sets a header cache-control: max-age=86400 but this does not take advantage of the CDN Edge.
Consider adding s-maxage like the caching docs mention:
cache-control: max-age=86400, s-maxage=86400, public
You could even add immutable for static badges that you know will never change.
Thanks so much! That could help a lot here! We've tried to avoid immutable because of changes in the template and server bugs, but setting fairly long timeouts should have a pretty similar effect.
No problem!
Also note that deploying will purge the CDN Edge cache https://vercel.com/docs/v2/edge-network/caching#cache-invalidation
@paulmelnikow - do you have a handle on how the headers are set/forwarded with the raster proxy? I know @calebcartwright is following up on https://github.com/badges/shields/issues/3647#issuecomment-621582157 but if we can cut our costs in the meantime with a header, that seems like its worth following up.
There's a short list of headers that are copied from the upstream svg response: https://github.com/badges/svg-to-image-proxy/blob/aa3486603f6e67295d1857351a1de8b47732257e/index.js#L20-L25
So the place to make this change is probably in Shields:
I'm not 100% sure we want public in there. We should think about whether that's a problem for self-hosting.
Most helpful comment
Thanks for the acknowledgement! Great to see my little tool being used. I realised that I haven't touched it in a little while so might go back and see how it's faring. As a user and fan of shields.io, I was wondering if there's anything that you'd like to see specifically.