// @ts-check // Tests: M1–M4 — MapLibre GL canvas renders on all three map surfaces // Requires demo data: run `make demo-load` before this suite. const { test, expect } = require('@playwright/test'); // ── M1: Full map page renders MapLibre canvas ───────────────────────────────── test('M1: /map page renders MapLibre GL canvas without JS errors', async ({ page }) => { const errors = []; page.on('pageerror', e => errors.push(e.message)); await page.goto('/trips/japan-korea-2026/map'); await expect(page.locator('canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); expect(errors, 'No JS errors on map page').toHaveLength(0); }); // ── M2: Full map page — dot markers are in the DOM ─────────────────────────── test('M2: /map page has at least one dot marker', async ({ page }) => { await page.goto('/trips/japan-korea-2026/map'); await expect(page.locator('canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); // Markers are added in map.on('load') — wait for first to appear in the DOM await expect(page.locator('.maplibregl-marker').first()).toBeVisible({ timeout: 15000 }); const markerCount = await page.locator('.maplibregl-marker').count(); expect(markerCount, 'At least one marker present').toBeGreaterThan(0); }); // ── M3: Dailies mini-map renders MapLibre canvas ───────────────────────────── test('M3: Dailies mini-map renders MapLibre GL canvas without JS errors', async ({ page }) => { const errors = []; page.on('pageerror', e => errors.push(e.message)); await page.goto('/trips/japan-korea-2026/dailies'); await expect(page.locator('#feed-map canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); expect(errors, 'No JS errors on dailies page').toHaveLength(0); }); // ── M4: Home map renders MapLibre canvas ───────────────────────────────────── test('M4: Home page map renders MapLibre GL canvas without JS errors', async ({ page }) => { const errors = []; page.on('pageerror', e => errors.push(e.message)); await page.goto('/'); await expect(page.locator('#home-map canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); expect(errors, 'No JS errors on home page').toHaveLength(0); }); // ── M5: Italy map — no JS errors with GPX present ──────────────────────────── test('M5: Italy map page renders without JS errors (GPX present)', async ({ page }) => { const errors = []; page.on('pageerror', e => errors.push(e.message)); await page.goto('/trips/italy-2026-demo/map'); await expect(page.locator('canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); // Wait for markers to confirm map.on('load') completed await expect(page.locator('.maplibregl-marker').first()).toBeVisible({ timeout: 15000 }); // Give Promise.all time to resolve await page.waitForTimeout(3000); expect(errors, 'No JS errors on Italy map page').toHaveLength(0); }); // ── M6: Italy map — journey source exists after GPX loads ──────────────────── test('M6: Italy map has a journey MapLibre source after GPX settles', async ({ page }) => { await page.goto('/trips/italy-2026-demo/map'); await expect(page.locator('canvas.maplibregl-canvas')).toBeVisible({ timeout: 10000 }); await expect(page.locator('.maplibregl-marker').first()).toBeVisible({ timeout: 15000 }); // Wait until the journey source appears — addJourneySegments runs inside Promise.all.then() // `var map = ...` in map.html.twig is a plain