This commit is contained in:
2026-10-23 10:23:03 -04:00
parent 84b363b863
commit c4d9d1b86c
10 changed files with 625 additions and 22 deletions
+44 -2
View File
@@ -3,9 +3,18 @@
const TOKEN_KEY = "thebutton-token";
const $ = (id) => document.getElementById(id);
const callbackParams = new URLSearchParams(window.location.hash.slice(1));
const callbackError = callbackParams.get("oidc_error");
if (callbackError) {
history.replaceState(null, "", window.location.pathname + window.location.search);
}
let game = null; // latest /api/state payload
let clockOffset = 0; // serverTime - clientTime
let token = localStorage.getItem(TOKEN_KEY);
let oidcMode = false;
let oidcLoginUrl = "";
let oidcRegisterUrl = "";
let statsLoaded = false;
let subscribed = false;
let currentShareText = "";
@@ -238,12 +247,19 @@ function renderSections() {
const id = button.dataset.section;
button.hidden = !available[id];
button.setAttribute("aria-expanded", String(selectedSection === id));
if (id === "account-section") button.textContent = token ? "Your score" : "Log in / Join";
if (id === "account-section") button.textContent = token ? "Your score" : oidcMode ? "Sign in" : "Log in / Join";
});
document.querySelectorAll("[data-panel]").forEach((panel) => {
panel.hidden = panel.id !== selectedSection;
});
$("mailing-list").hidden = !token || subscribed;
$("register-section").hidden = !!token || oidcMode;
$("oidc-login-section").hidden = !!token || !oidcMode;
if (oidcMode) {
$("oidc-login-link").href = oidcLoginUrl;
$("oidc-register-link").href = oidcRegisterUrl || "#";
$("oidc-register-link").hidden = !oidcRegisterUrl;
}
$("chat-form").hidden = !token;
$("chat-login").hidden = !!token;
$("section-hint").hidden = selectedSection !== null;
@@ -434,7 +450,6 @@ async function refreshState() {
function updateButton() {
$("the-button").disabled = !token || !game || game.ended;
$("register-section").hidden = !!token;
$("me-section").hidden = !token;
$("my-subscribed").hidden = !token || !subscribed;
renderSections();
@@ -936,6 +951,32 @@ $("the-button").addEventListener("click", async () => {
$("mastodon-instance").addEventListener("input", updateShareLinks);
async function loadAuthConfig() {
try {
const response = await fetch("/api/config", { cache: "no-store" });
if (!response.ok) return;
const config = await response.json();
oidcMode = config.auth_mode === "oidc";
if (oidcMode) {
token = null;
localStorage.removeItem(TOKEN_KEY);
}
oidcLoginUrl = config.login_url || "";
oidcRegisterUrl = config.register_url || "";
renderSections();
if (callbackError) {
const errorMessage = callbackError === "access_denied"
? "This account is not authorized to play The Button."
: callbackError === "account_link_required"
? "A game account with this name already exists. Ask a moderator to link your eom.dev identity so your scores are preserved."
: "Sign-in didn't complete. Please try again.";
$("oidc-error").textContent = errorMessage;
}
} catch {
// Keep the local login UI available if the server has no OIDC config endpoint.
}
}
$("register-form").addEventListener("submit", async (ev) => {
ev.preventDefault();
$("register-error").textContent = "";
@@ -991,6 +1032,7 @@ $("subscribe-form").addEventListener("submit", async (ev) => {
});
(async function init() {
await loadAuthConfig();
await refreshState();
await loadMe();
requestAnimationFrame(tick);