arda-site-scan
Version:
A standalone CLI tool for comprehensive website analysis including screenshots, SEO, and accessibility testing using Playwright
220 lines ⢠8.42 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.ReporterManager = void 0;
const promises_1 = __importDefault(require("fs/promises"));
const path_1 = __importDefault(require("path"));
const child_process_1 = require("child_process");
const util_1 = require("util");
const chalk_1 = __importDefault(require("chalk"));
const html_reporter_js_1 = require("../lib/html-reporter.js");
const execAsync = (0, util_1.promisify)(child_process_1.exec);
class ReporterManager {
config;
sessionId;
reporters = [];
constructor(config, sessionId) {
this.config = config;
this.sessionId = sessionId;
if (this.config.enabled) {
this.initializeReporters();
}
}
initializeReporters() {
if (this.config.type === 'html') {
const htmlReporter = new html_reporter_js_1.HTMLReporter(this.config, this.sessionId);
this.reporters.push(htmlReporter);
}
}
async generateReports(sessionSummary, pageResults) {
if (!this.config.enabled || this.reporters.length === 0) {
return { success: true, reportPaths: [], errors: [] };
}
console.log(chalk_1.default.blue('\nš Generating HTML reports...'));
const reportPaths = [];
const errors = [];
try {
const reportData = {
sessionSummary,
pageResults,
generatedAt: new Date().toISOString(),
baseUrl: sessionSummary.url
};
// Generate reports from all configured reporters
for (const reporter of this.reporters) {
try {
const reportPath = await reporter.generateReport(reportData);
reportPaths.push(reportPath);
console.log(chalk_1.default.green(` ā
HTML report generated: ${reportPath}`));
}
catch (error) {
const errorMsg = error instanceof Error ? error.message : String(error);
errors.push(`HTML Reporter failed: ${errorMsg}`);
console.error(chalk_1.default.red(` ā HTML report generation failed: ${errorMsg}`));
}
}
// Handle post-generation actions
if (reportPaths.length > 0) {
await this.handleReportOpening(reportPaths[0]);
}
return {
success: errors.length === 0,
reportPaths,
errors
};
}
catch (error) {
const errorMsg = error instanceof Error ? error.message : String(error);
console.error(chalk_1.default.red(` ā Report generation failed: ${errorMsg}`));
return {
success: false,
reportPaths: [],
errors: [errorMsg]
};
}
}
async handleReportOpening(reportPath) {
const shouldOpen = this.shouldOpenReport();
if (shouldOpen) {
try {
await this.openReport(reportPath);
console.log(chalk_1.default.blue(` š Opened report in browser: ${reportPath}`));
}
catch (error) {
console.warn(chalk_1.default.yellow(` ā ļø Could not open report automatically: ${error}`));
console.log(chalk_1.default.blue(` š Report available at: ${reportPath}`));
}
}
else {
console.log(chalk_1.default.blue(` š Report available at: ${reportPath}`));
}
}
shouldOpenReport() {
switch (this.config.openBehavior) {
case 'always':
return true;
case 'never':
return false;
case 'on-failure':
// Would need access to test results to determine if there were failures
// For now, default to not opening
return false;
default:
return false;
}
}
async openReport(reportPath) {
const absolutePath = path_1.default.resolve(reportPath);
const fileUrl = `file://${absolutePath.replace(/\\/g, '/')}`;
let command;
switch (process.platform) {
case 'darwin': // macOS
command = `open "${fileUrl}"`;
break;
case 'win32': // Windows
command = `start "" "${fileUrl}"`;
break;
case 'linux': // Linux
command = `xdg-open "${fileUrl}"`;
break;
default:
throw new Error(`Unsupported platform: ${process.platform}`);
}
await execAsync(command);
}
async getReportSummary() {
return {
enabled: this.config.enabled,
type: this.config.enabled ? this.config.type : undefined,
outputPath: this.config.enabled ? this.config.outputPath : undefined
};
}
static createDefaultConfig() {
return {
enabled: false,
type: 'html',
openBehavior: 'never',
includeScreenshots: true,
includeDetailedLogs: false
};
}
static validateConfig(config) {
const errors = [];
if (config.enabled) {
if (!config.type) {
errors.push('Reporter type is required when reporter is enabled');
}
if (config.type !== 'html') {
errors.push(`Unsupported reporter type: ${config.type}`);
}
if (!['always', 'never', 'on-failure'].includes(config.openBehavior)) {
errors.push(`Invalid openBehavior: ${config.openBehavior}`);
}
if (config.outputPath) {
// Validate output path format
if (!path_1.default.isAbsolute(config.outputPath) && !config.outputPath.startsWith('./')) {
errors.push('Output path must be absolute or relative (starting with ./)');
}
}
}
return {
valid: errors.length === 0,
errors
};
}
async cleanup() {
// Cleanup any temporary files or resources
// Currently no cleanup needed, but structure for future enhancements
}
// Utility method to check if reports were generated successfully
async verifyReports(reportPaths) {
const details = [];
let allVerified = true;
for (const reportPath of reportPaths) {
try {
const stats = await promises_1.default.stat(reportPath);
if (stats.isFile() && stats.size > 0) {
details.push(`ā
${reportPath} (${Math.round(stats.size / 1024)}KB)`);
}
else {
details.push(`ā ${reportPath} (empty or invalid)`);
allVerified = false;
}
}
catch (error) {
details.push(`ā ${reportPath} (not found)`);
allVerified = false;
}
}
return {
verified: allVerified,
details
};
}
// Enhanced version that considers test failures for 'on-failure' behavior
updateOpenBehaviorBasedOnResults(sessionSummary) {
if (this.config.openBehavior === 'on-failure' && sessionSummary.testsFailed > 0) {
// Temporarily override to always open if there were failures
this.config = { ...this.config, openBehavior: 'always' };
}
}
// Get report metadata for display in session summary
getReportMetadata() {
const outputDir = this.config.outputPath ||
path_1.default.join('arda-site-scan-sessions', this.sessionId, 'html-report');
const features = [];
if (this.config.includeScreenshots)
features.push('Screenshots');
if (this.config.includeDetailedLogs)
features.push('Detailed Logs');
return {
type: this.config.type,
outputDir,
features
};
}
}
exports.ReporterManager = ReporterManager;
//# sourceMappingURL=reporter-manager.js.map