diff --git a/website/src/components/DownloadButtons.astro b/website/src/components/DownloadButtons.astro
index 4f16c21..edbfd08 100644
--- a/website/src/components/DownloadButtons.astro
+++ b/website/src/components/DownloadButtons.astro
@@ -1,10 +1,12 @@
---
import { site, platforms } from "../data/site";
+import { getRelease } from "../data/release";
interface Props {
large?: boolean;
}
const { large = false } = Astro.props;
+const release = await getRelease();
---
-
-
- v0.1.2 · Works offline · No account
-
+
@@ -75,62 +57,9 @@ import { site, platforms } from "../data/site";
margin-top: clamp(24px, 3vw, 32px);
scroll-margin-top: 96px;
}
- .hero__buttons {
- display: flex;
- flex-wrap: wrap;
- justify-content: center;
- gap: 12px;
- }
- .osbtn {
- display: inline-flex;
- align-items: center;
- gap: 10px;
- padding: 0.82em 1.35em;
- background: #ffffff;
- border: 1px solid var(--line-strong);
- border-radius: 999px;
- color: #23201b;
- font-family: var(--font-ui);
- font-size: 1rem;
- font-weight: 600;
- box-shadow: var(--shadow-page);
- transition:
- transform 0.18s var(--ease),
- box-shadow 0.18s var(--ease),
- border-color 0.18s var(--ease);
- }
- .osbtn:hover {
- transform: translateY(-1px);
- box-shadow: var(--shadow-pop);
- }
- .osbtn.is-detected {
- border-color: var(--ink);
- }
- .osbtn__icon {
- width: 18px;
- height: 18px;
- flex: none;
- object-fit: contain;
- }
- .hero__meta {
- margin: 16px 0 0;
- font-family: ui-monospace, SFMono-Regular, "SF Mono", Menlo, Consolas, monospace;
- font-size: 0.8rem;
- color: var(--ink-faint);
- text-align: center;
- }
.hero__offer {
display: flex;
justify-content: center;
margin-top: 22px;
}
- @media (max-width: 480px) {
- .hero__buttons {
- flex-direction: column;
- align-items: stretch;
- }
- .osbtn {
- justify-content: center;
- }
- }
diff --git a/website/src/data/release.ts b/website/src/data/release.ts
new file mode 100644
index 0000000..f3e1b13
--- /dev/null
+++ b/website/src/data/release.ts
@@ -0,0 +1,52 @@
+// Resolves the latest GitHub release to a direct download URL per OS, at build
+// time. The picked file follows each platform's `match` order in site.ts.
+// Falls back to the releases page if the release can't be read.
+
+import { site, platforms } from "./site";
+
+type Asset = { name: string; browser_download_url: string };
+
+export type Release = {
+ version: string;
+ urls: Record
;
+};
+
+function pickAsset(assets: Asset[], match: string[]): string | null {
+ for (const sfx of match) {
+ const hit = assets.find((a) => a.name.toLowerCase().endsWith(sfx.toLowerCase()));
+ if (hit) return hit.browser_download_url;
+ }
+ return null;
+}
+
+function fallback(): Release {
+ return {
+ version: "",
+ urls: Object.fromEntries(platforms.map((p) => [p.id, site.releasesUrl])),
+ };
+}
+
+async function fetchRelease(): Promise {
+ try {
+ const res = await fetch(`https://api.github.com/repos/${site.repo}/releases/latest`, {
+ headers: { Accept: "application/vnd.github+json" },
+ signal: AbortSignal.timeout(8000),
+ });
+ if (!res.ok) return fallback();
+ const data = await res.json();
+ const assets: Asset[] = data.assets || [];
+ const urls = Object.fromEntries(
+ platforms.map((p) => [p.id, pickAsset(assets, p.match) ?? site.releasesUrl]),
+ );
+ return { version: data.tag_name ?? "", urls };
+ } catch {
+ return fallback();
+ }
+}
+
+let cached: Promise | null = null;
+
+export function getRelease(): Promise {
+ cached ??= fetchRelease();
+ return cached;
+}
diff --git a/website/src/data/site.ts b/website/src/data/site.ts
index c33b12c..c73776a 100644
--- a/website/src/data/site.ts
+++ b/website/src/data/site.ts
@@ -39,8 +39,8 @@ export type Platform = {
export const platforms: Platform[] = [
{ id: "mac", label: "macOS", logo: "macos.svg", match: [".dmg"] },
- { id: "windows", label: "Windows", logo: "windows.svg", match: [".msi", ".exe"] },
- { id: "linux", label: "Linux", logo: "linux.svg", match: [".AppImage", ".deb", ".rpm"] },
+ { id: "windows", label: "Windows", logo: "windows.svg", match: [".exe", ".msi"] },
+ { id: "linux", label: "Linux", logo: "linux.svg", match: [".deb", ".AppImage", ".rpm"] },
];
// Full-color store logos, served from /public/logos. Shown on white tiles so