fix: load system fonts for OG image text rendering

usvg's default Options creates an empty fontdb, so no fonts are found
for text rendering regardless of what's installed. Load system fonts
into a fontdb::Database and set the default font family to Noto Sans.

Also picks up a formatting change to index.html from a linter.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-05-11 16:17:17 +03:00
parent d539892b70
commit 1f2fea3427
4 changed files with 67 additions and 23 deletions

View File

@@ -31,6 +31,7 @@ reqwest = { version = "0.12", default-features = false, features = ["rustls-tls"
figment = { version = "0.10", features = ["toml", "env"] }
clap = { version = "4", features = ["derive", "env"] }
resvg = "0.45"
fontdb = "0.23"
# internal
moments-entities = { path = "crates/moments-entities", version = "=0.1.0" }

View File

@@ -22,3 +22,4 @@ chrono.workspace = true
clap.workspace = true
reqwest.workspace = true
resvg.workspace = true
fontdb.workspace = true

View File

@@ -360,7 +360,12 @@ fn render_contributions_png(
svg.push_str("</svg>");
// Rasterize at 1200x630
let tree = resvg::usvg::Tree::from_str(&svg, &resvg::usvg::Options::default())
let mut fontdb = fontdb::Database::new();
fontdb.load_system_fonts();
let mut opts = resvg::usvg::Options::default();
opts.fontdb = std::sync::Arc::new(fontdb);
opts.font_family = "Noto Sans".to_owned();
let tree = resvg::usvg::Tree::from_str(&svg, &opts)
.map_err(|e| format!("svg parse: {e}"))?;
let mut pixmap =

View File

@@ -4,19 +4,56 @@
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>rob.tn</title>
<meta property="og:title" content="rob thijssen — developer activity and contribution history" />
<meta property="og:description" content="a timeline of open source contributions across github, gitea, and mozilla hg — ranked projects, language trends, and commit activity since 2012." />
<meta property="og:image" content="https://rob.tn/api/v1/og/contributions.png" />
<meta
property="og:title"
content="rob thijssen: developer activity and contribution history"
/>
<meta
property="og:description"
content="a timeline of open source contributions across github, gitea, and mozilla hg — ranked projects, language trends, and commit activity since 2012."
/>
<meta
property="og:image"
content="https://rob.tn/api/v1/og/contributions.png"
/>
<meta property="og:type" content="website" />
<meta name="twitter:card" content="summary_large_image" />
<meta name="twitter:image" content="https://rob.tn/api/v1/og/contributions.png" />
<meta
name="twitter:image"
content="https://rob.tn/api/v1/og/contributions.png"
/>
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
<link rel="icon" type="image/png" sizes="16x16" href="/favicon-16.png" />
<link rel="icon" type="image/png" sizes="32x32" href="/favicon-32.png" />
<link rel="icon" type="image/png" sizes="48x48" href="/favicon-48.png" />
<link
rel="icon"
type="image/png"
sizes="16x16"
href="/favicon-16.png"
/>
<link
rel="icon"
type="image/png"
sizes="32x32"
href="/favicon-32.png"
/>
<link
rel="icon"
type="image/png"
sizes="48x48"
href="/favicon-48.png"
/>
<link rel="apple-touch-icon" href="/apple-touch-icon.png" />
<link rel="icon" type="image/png" sizes="192x192" href="/icon-192.png" />
<link rel="icon" type="image/png" sizes="512x512" href="/icon-512.png" />
<link
rel="icon"
type="image/png"
sizes="192x192"
href="/icon-192.png"
/>
<link
rel="icon"
type="image/png"
sizes="512x512"
href="/icon-512.png"
/>
</head>
<body>
<div id="root"></div>