Letter avatars are our 4th most expensive route globally.
This route is responsible for retrieving and generating unique letter avatars.
For scale of the enormity of the current cost, in the last 24 hours we spent 30 minutes of CPU time in the last 24 hours on meta alone, generating these avatars. At our hosting scale it’s as though we have single CPU dedicated permanently for letter avatar generation.
CPU alone is not the issue, we also have all these pesky web requests to deliver these little images to users.
Instead we would like to investigate another approach here that is more efficient.
Option 1: ship a font and use CSS
The simplest and probably most efficient way would be to pick a pretty font from: Google Fonts and use CSS to render this stuff.
If we were to do this with “font + CSS” we must use a consistent font, otherwise positioning will be hellish and the UX. Centering the letter is not going to be super easy but probably doable.
- Simple to build
- Will be very fast regardless of avatar count on screen
- Embed freindly
- Centering in CSS is hard
- We need to ship an extra icon font
- CSS for this will be quite long
- Not RSS friendly (unlikely to be even doable in a sane way)
- Not Email friendly (will require a fair amount of work to get it to work in email)
<div width='100' height='100' class='letter-avatar letter-color-1 background-color-76'>A</div>
Option 2: use a font and Canvas
A slightly more complex option would be to use a font + canvas api to generate an image. This will make it slightly easier to center the letter. It may be slightly easier to integrate as well.
- Centering in canvas is easy
- We need to ship an icon font
- We need to run a “post processor” in JS on all letter avatars
- Impossible to do in Email
Option 3: use SVG
We could consider using a 100% SVG solution, ship all the glyphs in SVG. If we were to follow this we would have to have to ship an extra asset, cause I would not want to bloat vendor.js or application.js
- Can be extremely easy on embedding if all SVG is inlined
- Requires and extra asset
- Very complicated to build
- Will bloat cooked Markdown for quotes if we inline SVG
- Unlikely to be doable in Email
Option 4: Free letter avatar service
Have Discourse host a single, “free”, letter avatar service that any Discourse customer can use, wire it in as default.
- Simple to integrate into Discourse
- Can be default on with a simple off switch
- Allows us to provide custom “default” avatar styles
- Can run on Digital Ocean + Cloudflare and have very low running cost.
- Simple to build
- We can upgrade the avatar algorithm at will
- Everyone gets to use 1 cache
- Can reuse existing code
- We need to run yet another service
- We still got to maintain the fallback
- If cloudflare has issues, no letter avatars (need to check on great firewall of China)
- Some people may have privacy concerns (but they still have an off switch)
Options 1, super private
Guid is generated using username + random hidden site setting hash
Option 2, high letter avatar reuse and cache use
Option 3, super high cache reuse, good privacy
(100, 150, 10 are the colors being used)
(I lean toward option 3 here)
The one thing that is clear is that something needs to be done.
After thinking this through I think #4 are the best approach we can take, it leaves people a safety valve and is the least intrusive change code wise.
Also going forward it allows us to provide more “default avatar” styles that people can choose from which can be handy.
#3 route cost wise is the standard user avatar route, this happens because we are resizing images on demand (we do keep a cache, but still). We must investigate if there is a more efficient way to size down these images, if the original avatar is already optimized, we may be able to skip the optimization stage altogether. We may also consider adding rmagick so we do not spawn a process each time we resize an avatar.