capture-usermanual.mjs 104 lignes · 4813 octets
// Second pass : captures avec les noms exacts attendus par user_manual.
// Certaines URLs sont contextuelles (owner/repo) — on utilise le premier dépôt accessible.
//
// Usage :
//   GITRUST_USER=claude GITRUST_PASS='Pa33Word:' GITRUST_URL=https://gitrust.nuage.ebii \
//   node scripts/screenshot-runner/capture-usermanual.mjs

import { chromium } from 'playwright';
import { mkdir } from 'node:fs/promises';
import { fileURLToPath } from 'node:url';
import { dirname, resolve } from 'node:path';

const __dirname = dirname(fileURLToPath(import.meta.url));
const ROOT = resolve(__dirname, '..', '..');
const OUT = resolve(ROOT, 'screenshots');

const URL = process.env.GITRUST_URL || 'https://gitrust.nuage.ebii';
const USER = process.env.GITRUST_USER || 'claude';
const PASS = process.env.GITRUST_PASS || 'Pa33Word:';

async function capture(page, name, path, { waitSel, sleep = 0 } = {}) {
  try {
    console.log(`→ ${name} : ${path}`);
    await page.goto(URL + path, { waitUntil: 'load', timeout: 15000 });
    if (waitSel) {
      await page.waitForSelector(waitSel, { timeout: 5000 }).catch(() => {});
    }
    if (sleep) await page.waitForTimeout(sleep);
    await page.screenshot({ path: `${OUT}/${name}.png`, fullPage: true });
  } catch (e) {
    console.warn(`  ✗ ${name}: ${e.message}`);
  }
}

async function main() {
  await mkdir(OUT, { recursive: true });
  const browser = await chromium.launch({ headless: true });
  const context = await browser.newContext({
    ignoreHTTPSErrors: true,
    viewport: { width: 1440, height: 900 },
    locale: 'fr-FR',
  });
  const page = await context.newPage();

  // Login
  await page.goto(URL + '/login', { waitUntil: 'load' });
  await page.fill('input[name="username"], input[name="login"], input[type="text"]', USER);
  await page.fill('input[name="password"], input[type="password"]', PASS);
  await Promise.all([
    page.waitForURL(/\/(dashboard|login\/2fa|$)/, { timeout: 10000 }).catch(() => {}),
    page.click('button[type="submit"], input[type="submit"]'),
  ]);

  // Fix the two small captures from pass 1
  await capture(page, '111-settings-password-original', '/settings/password', { sleep: 1000 });
  await capture(page, '200-api-docs-original', '/api/docs', { waitSel: '.swagger-ui', sleep: 3000 });

  // Placeholders utilisés par user_manual (20)
  await capture(page, '100-settings-keys',         '/settings/keys',        { sleep: 500 });
  await capture(page, '110-settings-keys-list',    '/settings/keys',        { sleep: 500 });
  await capture(page, '111-settings-security',     '/settings/security',    { sleep: 500 });
  await capture(page, '112-settings-tokens',       '/settings/tokens',      { sleep: 500 });
  await capture(page, '117-import-form',           '/explore',              { sleep: 500 });
  await capture(page, '119-settings-notifications','/settings/notifications', { sleep: 500 });

  // Trouver un dépôt accessible via /explore
  await page.goto(URL + '/explore', { waitUntil: 'load' });
  const repoHref = await page.evaluate(() => {
    const a = document.querySelector('a[href^="/"][href*="/"][href$=""]');
    const all = Array.from(document.querySelectorAll('a[href]'))
      .map(el => el.getAttribute('href'))
      .filter(h => h && /^\/[a-z0-9_-]+\/[a-z0-9._-]+$/i.test(h))
      .filter(h => !h.startsWith('/api') && !h.startsWith('/explore') && !h.startsWith('/settings') && !h.startsWith('/admin') && !h.startsWith('/teams'));
    return all[0] || null;
  });

  console.log('→ dépôt détecté :', repoHref);

  if (repoHref) {
    await capture(page, '102-repo-after-push',  repoHref);
    await capture(page, '107-repo-settings-ci', repoHref + '/settings');
    await capture(page, '108-ci-pipeline-running', repoHref + '/ci');
    await capture(page, '109-ci-pipeline-success', repoHref + '/ci');
    await capture(page, '118-repo-security',    repoHref + '/security');
    await capture(page, '116-labels-page',      repoHref + '/labels');
    await capture(page, '114-new-pr-form',      repoHref + '/pulls/new');
    await capture(page, '115-pr-tabs',          repoHref + '/pulls');
    await capture(page, '105-pr-open',          repoHref + '/pulls');
    await capture(page, '104-issue-open',       repoHref + '/issues');
    await capture(page, '106-issue-closed',     repoHref + '/issues?state=closed');
    await capture(page, '101-clone-url-ssh',    repoHref);
  } else {
    console.warn('  ✗ aucun dépôt accessible — captures repo-level manquantes');
  }

  // Pages teams
  await capture(page, '103-team-created', '/dashboard', { sleep: 500 });
  await capture(page, '113-team-page',    '/dashboard', { sleep: 500 });

  await browser.close();
  console.log('\n✓ captures écrites dans', OUT);
}

main().catch(e => { console.error(e); process.exit(1); });