serve 88x31 buttons from cache URLs instead of base64, preload the art font
Deploy / deploy (push) Successful in 3s

This commit is contained in:
2026-10-03 15:27:54 +02:00
parent 2e80e535b3
commit 2201006b24
3 changed files with 39 additions and 16 deletions
+22
View File
@@ -0,0 +1,22 @@
<?php
// Serves an 88x31 button from the local cache (see inc/buttons.php).
require_once __DIR__ . '/config.php';
$h = $_GET['h'] ?? '';
$file = DATA_DIR . '/buttons/' . $h;
if (!preg_match('/^[0-9a-f]{32}$/', $h) || !is_file($file)) {
http_response_code(404);
exit;
}
$raw = (string) file_get_contents($file);
$nl = strpos($raw, "\n");
$type = $nl !== false ? substr($raw, 0, $nl) : '';
if (!preg_match('#^image/[\w.+-]+$#', $type)) {
http_response_code(404);
exit;
}
header('Content-Type: ' . $type);
header('Cache-Control: public, max-age=31536000, immutable'); // URL carries ?v=<mtime>
echo substr($raw, $nl + 1);
+15 -15
View File
@@ -20,10 +20,10 @@ const BUTTONS_88x31 = [
const BUTTON_CACHE_TTL = 7 * 86400; // re-fetch each button at most once a week
/**
* Fetch a remote image, cache it locally, and return it as a base64 data: URI.
* Returns null on failure so the caller can fall back to hotlinking.
* Fetch a remote image into the local cache (at most once a week) and return
* the cache file's path, or null if it couldn't be fetched.
*/
function button_data_uri(string $url): ?string
function button_cache(string $url): ?string
{
$dir = DATA_DIR . '/buttons';
@mkdir($dir, 0775, true);
@@ -47,19 +47,19 @@ function button_data_uri(string $url): ?string
}
}
if (!is_file($file)) {
return null;
return is_file($file) ? $file : null;
}
$raw = (string) file_get_contents($file);
$nl = strpos($raw, "\n");
if ($nl === false) {
return null;
}
$type = substr($raw, 0, $nl);
$data = substr($raw, $nl + 1);
return 'data:' . $type . ';base64,' . base64_encode($data);
/**
* Where the page should load a button from: our own copy (button.php serves
* it, versioned by the cache file's mtime so browsers can keep it), or the
* original if fetching failed. Was inlined as base64 before, which made every
* page ~260 KB heavier.
*/
function button_src(string $url): string
{
$file = button_cache($url);
return $file ? '/button.php?h=' . basename($file) . '&v=' . filemtime($file) : $url;
}
/** Render the whole 88x31 button row as HTML. */
@@ -67,7 +67,7 @@ function render_buttons_88x31(): string
{
$html = '';
foreach (BUTTONS_88x31 as $b) {
$uri = button_data_uri($b['src']) ?? $b['src']; // fall back to hotlink if fetch failed
$uri = button_src($b['src']);
$img = '<img src="' . htmlspecialchars($uri) . '" alt="' . htmlspecialchars($b['alt']) . '" width="88" height="31">';
$href = $b['href'] ?? '';
if ($href !== '') {
+1
View File
@@ -9,6 +9,7 @@ require_once __DIR__ . '/../config.php';
<title><?= htmlspecialchars($page_title ?? SITE_TITLE) ?></title>
<link rel="icon" href="/img/favicon.ico" sizes="any">
<link rel="stylesheet" href="/css/style.css?v=<?= filemtime(__DIR__ . '/../css/style.css') ?>">
<link rel="preload" href="/css/sideart.woff2" as="font" type="font/woff2" crossorigin>
<script src="/js/htmx.min.js" defer></script>
<script src="/js/idiomorph-ext.min.js" defer></script>
</head>