diff --git a/docs/.vitepress/gen-meta.js b/docs/.vitepress/gen-meta.js new file mode 100644 index 00000000..e2d30585 --- /dev/null +++ b/docs/.vitepress/gen-meta.js @@ -0,0 +1,118 @@ +#!/usr/bin/env node +/** + * docs:gen-meta — Pre-build metadata generator for VitePress docs. + * + * Checks that the environment is ready (PHP installed, composer dependencies + * present, bin/spc executable), then runs: + * bin/spc dev:gen-deps-data → docs/.vitepress/deps-data.json + * bin/spc dev:gen-ext-docs → docs/.vitepress/ext-data.json + */ + +'use strict' + +const { execSync, spawnSync } = require('child_process') +const fs = require('fs') +const path = require('path') + +// __dirname is docs/.vitepress/, so two levels up is the project root +const ROOT = path.resolve(__dirname, '../..') + +function fail(msg) { + console.error(`\x1b[31m[gen-meta] ERROR: ${msg}\x1b[0m`) + process.exit(1) +} + +function info(msg) { + console.log(`\x1b[36m[gen-meta] ${msg}\x1b[0m`) +} + +function ok(msg) { + console.log(`\x1b[32m[gen-meta] ${msg}\x1b[0m`) +} + +// --- 1. Check PHP ------------------------------------------------------------ +info('Checking PHP installation...') +const phpResult = spawnSync('php', ['--version'], { encoding: 'utf8' }) +if (phpResult.status !== 0 || phpResult.error) { + fail( + 'PHP is not installed or not in PATH.\n' + + ' Please install PHP 8.1+ and ensure it is available in your PATH.' + ) +} +const phpVersion = phpResult.stdout.split('\n')[0].trim() +ok(`Found: ${phpVersion}`) + +// --- 2. Check composer CLI --------------------------------------------------- +info('Checking composer...') +const composerCheck = spawnSync('composer', ['--version'], { encoding: 'utf8' }) +if (composerCheck.status !== 0 || composerCheck.error) { + fail( + 'composer is not installed or not in PATH.\n' + + ' Please install Composer: https://getcomposer.org/download/' + ) +} +ok(`Found: ${composerCheck.stdout.split('\n')[0].trim()}`) + +// --- 3. Install composer dependencies if missing ---------------------------- +info('Checking composer dependencies...') +const autoload = path.join(ROOT, 'vendor', 'autoload.php') +if (!fs.existsSync(autoload)) { + info('vendor/autoload.php not found — running composer install --no-dev ...') + const installResult = spawnSync('composer', ['install', '--no-dev'], { + cwd: ROOT, + stdio: 'inherit', + }) + if (installResult.status !== 0) { + fail('composer install --no-dev failed (exit code ' + installResult.status + ').') + } + ok('Composer dependencies installed.') +} else { + ok('Composer vendor directory found.') +} + +// --- 4. Check bin/spc -------------------------------------------------------- +info('Checking bin/spc...') +const spc = path.join(ROOT, 'bin', 'spc') +if (!fs.existsSync(spc)) { + fail('bin/spc not found. Make sure you are in the project root.') +} +// Quick sanity check — list commands +const spcCheck = spawnSync('php', [spc, 'list', '--format=txt'], { + cwd: ROOT, + encoding: 'utf8', + env: { ...process.env, SPC_EXECUTION_SOURCE: '1' }, +}) +if (spcCheck.status !== 0) { + fail( + 'bin/spc failed to run.\n' + + (spcCheck.stderr ?? '') + + '\n Make sure PHP extensions required by static-php-cli are available.' + ) +} +ok('bin/spc is operational.') + +// --- 5. Run dev:gen-deps-data ------------------------------------------------ +info('Running bin/spc dev:gen-deps-data ...') +const depsResult = spawnSync('php', [spc, 'dev:gen-deps-data'], { + cwd: ROOT, + stdio: 'inherit', + env: { ...process.env, SPC_EXECUTION_SOURCE: '1' }, +}) +if (depsResult.status !== 0) { + fail('dev:gen-deps-data failed (exit code ' + depsResult.status + ').') +} +ok('deps-data.json generated.') + +// --- 6. Run dev:gen-ext-docs ------------------------------------------------- +info('Running bin/spc dev:gen-ext-docs ...') +const extResult = spawnSync('php', [spc, 'dev:gen-ext-docs'], { + cwd: ROOT, + stdio: 'inherit', + env: { ...process.env, SPC_EXECUTION_SOURCE: '1' }, +}) +if (extResult.status !== 0) { + fail('dev:gen-ext-docs failed (exit code ' + extResult.status + ').') +} +ok('ext-data.json generated.') + +ok('Metadata generation complete. Proceeding to VitePress build...') diff --git a/package.json b/package.json index 53b6988a..59011a01 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,8 @@ { "scripts": { "docs:dev": "vitepress dev docs", - "docs:build": "vitepress build docs", + "docs:gen-meta": "node docs/.vitepress/gen-meta.js", + "docs:build": "npm run docs:gen-meta && vitepress build docs", "docs:preview": "vitepress preview docs" }, "devDependencies": {