Files
weerscherm/tests/js/format.test.js
T

154 lines
5.9 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { test } from 'node:test';
import assert from 'node:assert/strict';
import {
f1, fInt, fmm, markerPos, barHeights, wmoIcon, trendLabel,
formatDate, formatTime, dayAbbr, monthName, isOlderThan, msUntil,
} from '../../public/format.js';
const TZ = 'Europe/Berlin';
test('f1 uses a decimal comma and one decimal', () => {
assert.equal(f1(16.4), '16,4');
assert.equal(f1(0), '0,0');
assert.equal(f1(19.75), '19,8');
assert.equal(f1(null), '–');
assert.equal(f1(undefined), '–');
});
test('fInt rounds to whole degrees', () => {
assert.equal(fInt(18.3), '18');
assert.equal(fInt(9.5), '10');
assert.equal(fInt(null), '–');
});
test('fmm shows "0 mm" for zero', () => {
assert.equal(fmm(0), '0 mm');
assert.equal(fmm(0.4), '0,4 mm');
assert.equal(fmm(8.25), '8,3 mm');
assert.equal(fmm(null), '–');
});
test('markerPos interpolates and clamps', () => {
assert.ok(Math.abs(markerPos(16.4, 9.2, 19.8) - 67.92) < 0.01);
assert.equal(markerPos(5, 9.2, 19.8), 0);
assert.equal(markerPos(25, 9.2, 19.8), 100);
assert.equal(markerPos(10, 10, 10), 50);
assert.equal(markerPos(null, 1, 2), 50);
});
test('barHeights scales to the tallest bar with a 2px floor', () => {
const h = barHeights([1.2, 6.8, 0, 2.4]);
assert.ok(Math.abs(h[0] - 12.35) < 0.01);
assert.equal(h[1], 70);
assert.equal(h[2], 2);
assert.ok(Math.abs(h[3] - 24.7) < 0.01);
assert.deepEqual(barHeights([0, 0, 0, 0]), [2, 2, 2, 2]);
assert.deepEqual(barHeights([null, 0, undefined, 0]), [2, 2, 2, 2]);
assert.deepEqual(barHeights([null, 5]), [2, 70]);
});
test('wmoIcon maps every documented code', () => {
assert.equal(wmoIcon(0), 'sun');
assert.equal(wmoIcon(1), 'partly');
assert.equal(wmoIcon(2), 'partly');
assert.equal(wmoIcon(3), 'cloud');
assert.equal(wmoIcon(45), 'fog');
assert.equal(wmoIcon(48), 'fog');
assert.equal(wmoIcon(51), 'drizzle');
assert.equal(wmoIcon(57), 'drizzle');
assert.equal(wmoIcon(61), 'rain');
assert.equal(wmoIcon(67), 'rain');
assert.equal(wmoIcon(80), 'showers');
assert.equal(wmoIcon(82), 'showers');
assert.equal(wmoIcon(71), 'snow');
assert.equal(wmoIcon(77), 'snow');
assert.equal(wmoIcon(85), 'snow');
assert.equal(wmoIcon(86), 'snow');
assert.equal(wmoIcon(95), 'thunder');
assert.equal(wmoIcon(99), 'thunder');
assert.equal(wmoIcon(42), 'cloud');
assert.equal(wmoIcon(null), 'cloud');
});
test('trendLabel', () => {
assert.equal(trendLabel('up'), '↗ stijgend');
assert.equal(trendLabel('down'), '↘ dalend');
assert.equal(trendLabel('stable'), '→ stabiel');
assert.equal(trendLabel(null), '');
});
test('formatDate gives a capitalised Dutch date in the station timezone', () => {
assert.equal(formatDate(new Date('2026-09-11T12:32:05Z'), TZ), 'Vrijdag 11 september');
// 23:30 UTC is al de volgende dag in Berlijn
assert.equal(formatDate(new Date('2026-09-11T23:30:00Z'), TZ), 'Zaterdag 12 september');
});
test('formatTime uses HH:MM in the station timezone', () => {
assert.equal(formatTime('2026-09-11T06:10:00+02:00', TZ), '06:10');
assert.equal(formatTime('2026-09-11T22:05:00Z', TZ), '00:05');
assert.equal(formatTime(null, TZ), '–');
assert.equal(formatTime('kapot', TZ), '–');
});
test('dayAbbr gives two-letter Dutch weekday', () => {
assert.equal(dayAbbr('2026-09-12', TZ), 'Za');
assert.equal(dayAbbr('2026-09-13', TZ), 'Zo');
assert.equal(dayAbbr('2026-09-14', TZ), 'Ma');
assert.equal(dayAbbr('2026-09-15', TZ), 'Di');
assert.equal(dayAbbr('2026-09-16', TZ), 'Wo');
assert.equal(dayAbbr('2026-09-17', TZ), 'Do');
assert.equal(dayAbbr('2026-09-18', TZ), 'Vr');
});
test('monthName', () => {
assert.equal(monthName(new Date('2026-09-11T12:00:00Z'), TZ), 'September');
});
test('isOlderThan', () => {
const now = new Date('2026-09-11T12:32:00Z');
assert.equal(isOlderThan('2026-09-11T12:10:00Z', now, 30), false);
assert.equal(isOlderThan('2026-09-11T11:50:00Z', now, 30), true);
assert.equal(isOlderThan(null, now, 30), true);
});
test('msUntil computes the wait until the next local time', () => {
const now = new Date('2026-09-11T12:32:05.500Z'); // 14:32:05 in Berlijn
assert.equal(msUntil(now, TZ, 0), ((24 - 14) * 3600 - 32 * 60 - 5) * 1000 - 500);
assert.equal(msUntil(now, TZ, 4), ((24 - 14 + 4) * 3600 - 32 * 60 - 5) * 1000 - 500);
assert.equal(msUntil(now, TZ, 15), (28 * 60 - 5) * 1000 - 500);
assert.equal(msUntil(new Date('2026-09-11T22:00:00.000Z'), TZ, 0), 86400000, 'precies op het moment zelf: pas morgen weer');
});
import { co2Level, fPct, fHpa, seriesRange, sparklinePath } from '../../public/format.js';
test('co2Level uses the Netatmo thresholds', () => {
assert.deepEqual(co2Level(612), { level: 'good', label: 'goed' });
assert.deepEqual(co2Level(1000), { level: 'good', label: 'goed' });
assert.deepEqual(co2Level(1001), { level: 'medium', label: 'matig' });
assert.deepEqual(co2Level(1500), { level: 'medium', label: 'matig' });
assert.deepEqual(co2Level(1501), { level: 'bad', label: 'slecht' });
assert.deepEqual(co2Level(null), { level: 'unknown', label: '–' });
});
test('fPct and fHpa', () => {
assert.equal(fPct(48), '48%');
assert.equal(fPct(47.6), '48%');
assert.equal(fPct(null), '–');
assert.equal(fHpa(1014.2), '1014 hPa');
assert.equal(fHpa(null), '–');
});
test('seriesRange ignores nulls', () => {
assert.deepEqual(seriesRange([1010, null, 1015.5, 1008]), { min: 1008, max: 1015.5 });
assert.equal(seriesRange([null, undefined]), null);
});
test('sparklinePath scales points into the box', () => {
assert.equal(sparklinePath([1000, 1010, 1005], 100, 50, 0), 'M0.0,50.0 L50.0,0.0 L100.0,25.0');
assert.equal(sparklinePath([1000, 1010], 100, 50, 5), 'M5.0,45.0 L95.0,5.0');
assert.equal(sparklinePath([1010, 1010, 1010], 100, 50, 0), 'M0.0,25.0 L50.0,25.0 L100.0,25.0', 'vlakke reeks in het midden');
assert.equal(sparklinePath([1000, null, 1010], 100, 50, 0), 'M0.0,50.0 L100.0,0.0', 'null-punt overgeslagen');
assert.equal(sparklinePath([1000], 100, 50), '');
assert.equal(sparklinePath([], 100, 50), '');
});