85 lines
3.7 KiB
JavaScript
85 lines
3.7 KiB
JavaScript
import test from 'node:test';
|
|
import assert from 'node:assert/strict';
|
|
import {readFile, readdir} from 'node:fs/promises';
|
|
import {fonts} from '../font-catalog.js';
|
|
import {render, registerFont, renderLoaded, resolveFont, FONT_CACHE} from '../renderer.js';
|
|
|
|
test('catalog includes every bundled FIGlet font', async () => {
|
|
const files = await readdir(new URL('../fonts/figlet/', import.meta.url));
|
|
assert.deepEqual(fonts, files.filter(file => file.endsWith('.flf')).map(file => file.slice(0, -4)).sort());
|
|
});
|
|
|
|
for (const font of fonts) {
|
|
test(`renders ${font} from its local font file`, async () => {
|
|
registerFont(font, await readFile(new URL(`../fonts/figlet/${font}.flf`, import.meta.url), 'utf8'));
|
|
const art = renderLoaded('Hello World! 123', font);
|
|
assert.equal(typeof art, 'string');
|
|
assert.match(art, /\S/);
|
|
});
|
|
}
|
|
|
|
test('Standard preserves lowercase lettering and the familiar FIGlet shape', () => {
|
|
assert.equal(renderLoaded('Hi', 'Standard'), [
|
|
' _ _ _ ', ' | | | (_)', ' | |_| | |', ' | _ | |', ' |_| |_|_|',
|
|
].join('\n'));
|
|
});
|
|
|
|
test('old lowercase font links resolve to their library names', () => {
|
|
for (const [name, expected] of [['standard', 'Standard'], ['slant', 'Slant'], ['block', 'Block'], ['banner', 'Banner'], ['compact', 'Standard'], ['unknown', 'Standard']]) {
|
|
assert.equal(resolveFont(name), expected);
|
|
}
|
|
});
|
|
|
|
test('missing font requests can be retried', async () => {
|
|
const originalFetch = globalThis.fetch;
|
|
const data = await readFile(new URL('../fonts/figlet/Standard.flf', import.meta.url), 'utf8');
|
|
const figlet = (await import('../vendor/figlet.js')).default;
|
|
delete figlet.figFonts.Standard;
|
|
try {
|
|
globalThis.fetch = async () => new Response('', {status: 404});
|
|
await assert.rejects(render('Hi', 'Standard'), /Cannot load font/);
|
|
globalThis.fetch = async () => new Response(data);
|
|
assert.match(await render('Hi', 'Standard'), /\S/);
|
|
} finally {
|
|
globalThis.fetch = originalFetch;
|
|
}
|
|
});
|
|
|
|
test('caches only selected fonts and reuses them when offline', async () => {
|
|
const originalFetch = globalThis.fetch;
|
|
const originalCaches = globalThis.caches;
|
|
const entries = new Map();
|
|
const figlet = (await import('../vendor/figlet.js')).default;
|
|
for (const font of ['Standard', 'Slant', 'Small']) delete figlet.figFonts[font];
|
|
try {
|
|
globalThis.caches = {
|
|
async open(name) {
|
|
assert.equal(name, FONT_CACHE);
|
|
return {
|
|
async match(url) { return entries.get(url)?.clone(); },
|
|
async put(url, response) { entries.set(url, response.clone()); },
|
|
};
|
|
},
|
|
};
|
|
globalThis.fetch = async url => new Response(await readFile(new URL(url), 'utf8'));
|
|
await render('Hello', 'Standard');
|
|
await render('Hello', 'Slant');
|
|
assert.equal(entries.size, 2);
|
|
assert.ok([...entries.keys()].every(url => /\/(Standard|Slant)\.flf$/.test(url)));
|
|
delete figlet.figFonts.Standard;
|
|
globalThis.fetch = async () => { throw new Error('Offline'); };
|
|
assert.match(await render('Offline', 'Standard'), /\S/);
|
|
await assert.rejects(render('Offline', 'Small'), /Offline/);
|
|
assert.equal(entries.size, 2);
|
|
} finally {
|
|
globalThis.fetch = originalFetch;
|
|
if (originalCaches === undefined) delete globalThis.caches;
|
|
else globalThis.caches = originalCaches;
|
|
}
|
|
});
|
|
|
|
test('rejects unknown fonts and overlong input', async () => {
|
|
await assert.rejects(render('Hello', 'unknown'), /Unknown/);
|
|
await assert.rejects(render('x'.repeat(501)), /too long/);
|
|
});
|