Add changelog viewer to runtime info
This commit is contained in:
@@ -223,6 +223,9 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
display: grid;
|
||||
gap: 10px;
|
||||
}
|
||||
.wide-button {
|
||||
width: 100%;
|
||||
}
|
||||
.chips {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
@@ -388,6 +391,39 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
.browser-entry-name {
|
||||
overflow-wrap: anywhere;
|
||||
}
|
||||
.changelog-modal {
|
||||
width: min(100%, 900px);
|
||||
max-height: min(84vh, 820px);
|
||||
overflow: hidden;
|
||||
border: 1px solid var(--line);
|
||||
border-radius: 22px;
|
||||
background: linear-gradient(180deg, rgba(29, 22, 47, 0.96), rgba(17, 13, 29, 0.98));
|
||||
box-shadow: var(--shadow);
|
||||
display: grid;
|
||||
grid-template-rows: auto 1fr;
|
||||
gap: 12px;
|
||||
padding: 18px;
|
||||
}
|
||||
.changelog-header {
|
||||
display: flex;
|
||||
gap: 10px;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
}
|
||||
.changelog-content {
|
||||
overflow: auto;
|
||||
border: 1px solid var(--line);
|
||||
border-radius: 18px;
|
||||
background: rgba(255, 255, 255, 0.03);
|
||||
padding: 16px;
|
||||
}
|
||||
.changelog-content pre {
|
||||
margin: 0;
|
||||
white-space: pre-wrap;
|
||||
overflow-wrap: anywhere;
|
||||
color: var(--text);
|
||||
font: 13px/1.55 "Cascadia Code", "Fira Code", Consolas, monospace;
|
||||
}
|
||||
@media (max-width: 900px) {
|
||||
.app { grid-template-columns: 1fr; }
|
||||
aside { border-right: 0; border-bottom: 1px solid var(--line); }
|
||||
@@ -427,6 +463,7 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
<p id="aniCliVersionLine">Detecting ani-cli version...</p>
|
||||
<p>Saved settings live in `.ani-cli-web/config.json` inside this project.</p>
|
||||
</div>
|
||||
<button class="ghost wide-button" id="openChangelogBtn" type="button">Changelog</button>
|
||||
</section>
|
||||
</aside>
|
||||
|
||||
@@ -607,6 +644,21 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="overlay" id="changelogOverlay" hidden>
|
||||
<div class="changelog-modal" role="dialog" aria-modal="true" aria-labelledby="changelogTitle">
|
||||
<div class="changelog-header">
|
||||
<div>
|
||||
<h2 id="changelogTitle">Changelog</h2>
|
||||
<p class="muted">Recent release notes loaded from the project's `CHANGELOG.md` file.</p>
|
||||
</div>
|
||||
<button class="ghost" id="closeChangelogBtn" type="button" aria-label="Close changelog">×</button>
|
||||
</div>
|
||||
<div class="changelog-content">
|
||||
<pre id="changelogContent">Loading changelog...</pre>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
const state = {
|
||||
config: {
|
||||
@@ -641,6 +693,8 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
const pathBrowserCurrentPath = $("pathBrowserCurrentPath");
|
||||
const pathBrowserList = $("pathBrowserList");
|
||||
const pathBrowserStatus = $("pathBrowserStatus");
|
||||
const changelogOverlay = $("changelogOverlay");
|
||||
const changelogContent = $("changelogContent");
|
||||
|
||||
function setNotice(text) {
|
||||
$("notice").textContent = text || "";
|
||||
@@ -744,6 +798,10 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
pathBrowserStatus.textContent = "";
|
||||
}
|
||||
|
||||
function closeChangelog() {
|
||||
changelogOverlay.hidden = true;
|
||||
}
|
||||
|
||||
function renderPathBrowser(data) {
|
||||
state.pathBrowser = {
|
||||
...state.pathBrowser,
|
||||
@@ -856,9 +914,22 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
$("aniCliVersionLine").textContent = `ani-cli ${data.ani_cli_version || "Unavailable"}`;
|
||||
}
|
||||
|
||||
async function openChangelog() {
|
||||
try {
|
||||
changelogContent.textContent = "Loading changelog...";
|
||||
changelogOverlay.hidden = false;
|
||||
const data = await api("/api/changelog");
|
||||
changelogContent.textContent = data.content || "Changelog unavailable.";
|
||||
} catch (error) {
|
||||
changelogContent.textContent = error.message || "Changelog unavailable.";
|
||||
}
|
||||
}
|
||||
|
||||
$("saveConfigBtn").addEventListener("click", saveConfig);
|
||||
$("testWebhookBtn").addEventListener("click", testWebhook);
|
||||
$("runJellyfinSyncBtn").addEventListener("click", runJellyfinSync);
|
||||
$("openChangelogBtn").addEventListener("click", openChangelog);
|
||||
$("closeChangelogBtn").addEventListener("click", closeChangelog);
|
||||
$("pathBrowserCloseBtn").addEventListener("click", closePathBrowser);
|
||||
$("pathBrowserCancelBtn").addEventListener("click", closePathBrowser);
|
||||
$("pathBrowserSelectBtn").addEventListener("click", selectCurrentBrowserPath);
|
||||
@@ -870,10 +941,18 @@ CONFIG_HTML = r"""<!doctype html>
|
||||
closePathBrowser();
|
||||
}
|
||||
});
|
||||
changelogOverlay.addEventListener("click", (event) => {
|
||||
if (event.target === changelogOverlay) {
|
||||
closeChangelog();
|
||||
}
|
||||
});
|
||||
window.addEventListener("keydown", (event) => {
|
||||
if (event.key === "Escape" && !pathBrowserOverlay.hidden) {
|
||||
closePathBrowser();
|
||||
}
|
||||
if (event.key === "Escape" && !changelogOverlay.hidden) {
|
||||
closeChangelog();
|
||||
}
|
||||
});
|
||||
for (const button of document.querySelectorAll(".browse-path-btn")) {
|
||||
button.addEventListener("click", () => openPathBrowser(button.dataset.target || "", button.dataset.mode || "dir"));
|
||||
|
||||
Reference in New Issue
Block a user