client: bugfix new code

We now have a sidebar!
This commit is contained in:
Starbeamrainbowlabs 2022-03-10 23:58:12 +00:00
parent a24ba21ba8
commit 21d193a424
Signed by: sbrl
GPG key ID: 1BE5172E637709C2
8 changed files with 74 additions and 40 deletions

View file

@ -5,7 +5,8 @@
"main": "src/index.mjs", "main": "src/index.mjs",
"scripts": { "scripts": {
"test": "echo \"No tests have been implemented yet\"", "test": "echo \"No tests have been implemented yet\"",
"build": "node src/static/esbuild.mjs" "build": "node src/static/esbuild.mjs",
"watch": "ESBUILD_WATCH=yes node src/static/esbuild.mjs"
}, },
"repository": { "repository": {
"type": "git", "type": "git",

View file

@ -89,14 +89,18 @@ nav {
padding: 0.5em 0.75em; padding: 0.5em 0.75em;
} }
.nav-items a { .nav-items a {
display: block; display: flex;
align-items: center;
gap: 0 0.5em;
color: inherit; color: inherit;
text-decoration: none; text-decoration: none;
} }
.nav-items .fa { .nav-items span:last-child { flex: 1; }
margin: 0.1em 0.25em 0.1em 0.1em; .nav-items .fa:not(.fa-stack):not(.fa-stack-1x):not(.fa-stack-2x):not(.fa-stack-3x) {
font-size: 200%; font-size: 200%;
vertical-align: middle; width: 1em;
height: 1em;
} }

View file

@ -7,7 +7,6 @@ import GlobalUI from './js/ui/GlobalUI.mjs';
import TableView from './js/ui/TableView.mjs'; import TableView from './js/ui/TableView.mjs';
window.addEventListener("load", async (_event) => { window.addEventListener("load", async (_event) => {
const el_version = document.querySelector(".version");
const el_table = document.querySelector("main"); const el_table = document.querySelector("main");
globalThis.sysquery = new SystemQueryClient(); globalThis.sysquery = new SystemQueryClient();
@ -17,7 +16,7 @@ window.addEventListener("load", async (_event) => {
tableview: new TableView(el_table), tableview: new TableView(el_table),
} }
await ui.init(); await globalThis.sysui.ui.init();
globalThis.sysquery_router.navigate_current_hash(); globalThis.sysquery_router.navigate_current_hash();

View file

@ -7,8 +7,12 @@ import crypto from 'crypto';
import esbuild from 'esbuild'; import esbuild from 'esbuild';
import log from '../lib/io/NamespacedLog.mjs'; const l = log("esbuild");
const __dirname = import.meta.url.slice(7, import.meta.url.lastIndexOf("/")); const __dirname = import.meta.url.slice(7, import.meta.url.lastIndexOf("/"));
const outdir = path.resolve(__dirname, "../static-dist");
/** /**
* Hashes the contents of a file. * Hashes the contents of a file.
* @ref https://stackoverflow.com/a/44643479/1460422 * @ref https://stackoverflow.com/a/44643479/1460422
@ -29,33 +33,7 @@ function hash_file(hashName, path) {
}); });
} }
(async () => { async function do_html() {
"use strict";
const outdir = path.resolve(__dirname, "../static-dist");
const result = await esbuild.build({
entryPoints: [
"./app.mjs",
"./app.css"
].map(filepath => path.resolve(__dirname, filepath)),
outdir,
bundle: true,
minify: true,
sourcemap: true,
treeShaking: true,
loader: {
".html": "text",
".svg": "file",
".woff2": "file",
".woff": "file",
".eot": "file",
".ttf": "file",
}
});
if(result.errors.length > 0 || result.warnings.length > 0)
console.log(result);
// We *would* use SHA3 here, but we need to use SHA2 for subresource integrity // We *would* use SHA3 here, but we need to use SHA2 for subresource integrity
let algorithm = "sha256"; let algorithm = "sha256";
let css_hash = await hash_file(algorithm, path.join(outdir, "app.css")); let css_hash = await hash_file(algorithm, path.join(outdir, "app.css"));
@ -70,6 +48,49 @@ function hash_file(hashName, path) {
// TODO: Use fs.promises.copyFile() for index.html here, and also maybe find & replace for css/js filenames that we can then randomise? // TODO: Use fs.promises.copyFile() for index.html here, and also maybe find & replace for css/js filenames that we can then randomise?
await fs.promises.writeFile(path.join(outdir, "index.html"), html); await fs.promises.writeFile(path.join(outdir, "index.html"), html);
}
(async () => {
"use strict";
const result = await esbuild.build({
entryPoints: [
"./app.mjs",
"./app.css"
].map(filepath => path.resolve(__dirname, filepath)),
outdir,
bundle: true,
minify: true,
sourcemap: true,
treeShaking: true,
watch: typeof process.env.ESBUILD_WATCH === "undefined" ? false : {
async onRebuild(error, _result) {
if(error) {
l.error(error);
return;
}
if(result.errors.length > 0 || result.warnings.length > 0)
console.log(result);
await do_html();
l.log(`Build successful`);
}
},
loader: {
".html": "text",
".svg": "file",
".woff2": "file",
".woff": "file",
".eot": "file",
".ttf": "file",
}
});
if(result.errors.length > 0 || result.warnings.length > 0)
console.log(result);
await do_html();
// console.log(await esbuild.analyzeMetafile(result.metafile)); // console.log(await esbuild.analyzeMetafile(result.metafile));
})(); })();

View file

@ -16,7 +16,7 @@
<!-- Any items specified here *must* have the "static" class, otherwise they'll be mistaken for a rogue dynamic item and stripped --> <!-- Any items specified here *must* have the "static" class, otherwise they'll be mistaken for a rogue dynamic item and stripped -->
<li class="static"><a href="#settings"> <li class="static"><a href="#settings">
<span class="fa fa-cog fa-fw" aria-hidden="true"></span> <span class="fa fa-cog fa-fw" aria-hidden="true"></span>
Settings <span>settings</span>
</a></li> </a></li>
</ul> </ul>
</nav> </nav>

View file

@ -4,7 +4,7 @@ import human_filesize from '../misc/human_filesize.mjs';
export default { export default {
name: "CPU", name: "CPU",
icon: microchip, icon: "microchip",
items: [ items: [
{ {
name: "Frequency (GHz)", name: "Frequency (GHz)",

View file

@ -14,6 +14,8 @@ class GlobalUI {
async init() { async init() {
const status = await globalThis.sysquery.status(); const status = await globalThis.sysquery.status();
const el_version = document.querySelector(".version");
// 1: Update version display // 1: Update version display
el_version.replaceChildren( el_version.replaceChildren(
document.createTextNode(status.version) document.createTextNode(status.version)
@ -31,7 +33,14 @@ class GlobalUI {
// Generate new dynamic navigation items // Generate new dynamic navigation items
const result = document.createDocumentFragment(); const result = document.createDocumentFragment();
for(const table_name of status.tables) { for(const table_name of status.tables) {
result.append(...this.emel(`li>a[href=#table/?]>${forkawesome_emel(tabledefs[table_name].icon)}+{?}`, { console.log(`[nav] new dynamic item ${table_name}, def`, tabledefs[table_name]);
const icondef = typeof tabledefs[table_name] === "undefined"
? "question-circle"
: tabledefs[table_name].icon;
const emel_icon = forkawesome_emel(icondef);
console.log(`emel_icon`, emel_icon);
result.append(this.emel(`li>a[href=#table/?]>${emel_icon}+span{?}`, {
placeholders: [ table_name, table_name ] placeholders: [ table_name, table_name ]
})); }));
} }

View file

@ -1,10 +1,10 @@
"use strict"; "use strict";
export default function(def) { export default function(def, fixed_width=true) {
if(typeof def === "string") if(typeof def === "string")
return `span.fa.fa-${def}`; return `span[class="fa fa-${def}${fixed_width?` fa-fw`:``}"]`;
if(def instanceof Array) if(def instanceof Array)
return def.map(el, i => `span.fa.fa-${el}.fa-stack-${def.length-i}x`).join(`+`); return `(span[class="fa-stack${fixed_width?` fa-fw`:``}"]>${def.map((el, i) => `span[class="fa fa-${el} fa-stack-${def.length-i}x${fixed_width?` fa-fw`:``}"]`).join(`+`)})`;
throw new Error(`Error: Expected def of type string or Array, but got variable of type ${typeof def}`); throw new Error(`Error: Expected def of type string or Array, but got variable of type ${typeof def}`);
} }