@casoon/auditmysite
Version:
A comprehensive command-line tool for automated accessibility, security, performance, and SEO testing using Playwright and pa11y, based on sitemap URLs
312 lines • 10.9 kB
JavaScript
"use strict";
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
Object.defineProperty(exports, "__esModule", { value: true });
exports.TestQueue = void 0;
const fs = __importStar(require("fs"));
class TestQueue {
constructor(options = {}) {
this.queue = [];
this.completed = [];
this.failed = [];
this.options = {
maxRetries: 3,
maxConcurrent: 1,
saveInterval: 5000, // 5 Sekunden
dataFile: './test-queue-data.json',
priorityPatterns: [
{ pattern: '/home', priority: 1 },
{ pattern: '/', priority: 2 },
{ pattern: '/about', priority: 3 },
{ pattern: '/contact', priority: 3 },
{ pattern: '/blog', priority: 4 },
{ pattern: '/products', priority: 4 }
],
...options
};
this.dataFile = this.options.dataFile;
this.loadQueue();
this.startAutoSave();
}
/**
* URLs zur Queue hinzufügen
*/
addUrls(urls) {
const newUrls = urls.map(url => ({
url,
priority: this.calculatePriority(url),
status: 'pending',
attempts: 0
}));
// Duplikate entfernen
const existingUrls = new Set(this.queue.map(item => item.url));
const uniqueNewUrls = newUrls.filter(item => !existingUrls.has(item.url));
this.queue.push(...uniqueNewUrls);
// Nach Priorität sortieren
this.queue.sort((a, b) => a.priority - b.priority);
console.log(`📋 Added ${uniqueNewUrls.length} URLs to queue (${this.queue.length} total)`);
}
/**
* Nächste URL aus der Queue holen
*/
getNextUrl() {
const pendingUrl = this.queue.find(item => item.status === 'pending');
if (!pendingUrl)
return null;
pendingUrl.status = 'in-progress';
pendingUrl.attempts++;
pendingUrl.lastAttempt = new Date();
return pendingUrl;
}
/**
* URL als abgeschlossen markieren
*/
markCompleted(url, result) {
const item = this.queue.find(item => item.url === url);
if (item) {
item.status = 'completed';
item.result = result;
this.completed.push(item);
this.queue = this.queue.filter(item => item.url !== url);
}
}
/**
* URL als fehlgeschlagen markieren
*/
markFailed(url, error) {
const item = this.queue.find(item => item.url === url);
if (item) {
if (item.attempts >= this.options.maxRetries) {
item.status = 'failed';
item.error = error;
this.failed.push(item);
this.queue = this.queue.filter(item => item.url !== url);
console.log(`❌ URL failed permanently: ${url} (${error})`);
}
else {
item.status = 'pending';
item.error = error;
console.log(`🔄 URL will be retried: ${url} (attempt ${item.attempts}/${this.options.maxRetries})`);
}
}
}
/**
* URL überspringen
*/
markSkipped(url, reason) {
const item = this.queue.find(item => item.url === url);
if (item) {
item.status = 'skipped';
item.error = reason || 'Skipped by user';
this.queue = this.queue.filter(item => item.url !== url);
}
}
/**
* Queue-Status abrufen
*/
getStatus() {
const total = this.queue.length + this.completed.length + this.failed.length;
const pending = this.queue.filter(item => item.status === 'pending').length;
const inProgress = this.queue.filter(item => item.status === 'in-progress').length;
const completed = this.completed.length;
const failed = this.failed.length;
const skipped = this.queue.filter(item => item.status === 'skipped').length;
const progress = total > 0 ? ((completed + failed) / total) * 100 : 0;
return {
total,
pending,
inProgress,
completed,
failed,
skipped,
progress: Math.round(progress)
};
}
/**
* Queue speichern
*/
saveQueue() {
try {
const data = {
queue: this.queue,
completed: this.completed,
failed: this.failed,
timestamp: new Date().toISOString(),
// 🆕 Parameter mit speichern
testParameters: this.options.testParameters
};
fs.writeFileSync(this.dataFile, JSON.stringify(data, null, 2));
console.log(`💾 Queue saved to ${this.dataFile}`);
}
catch (error) {
console.error(`💥 Failed to save queue: ${error}`);
}
}
/**
* Queue laden
*/
loadQueue() {
try {
if (fs.existsSync(this.dataFile)) {
const data = JSON.parse(fs.readFileSync(this.dataFile, 'utf8'));
// 🆕 Parameter-Validierung
if (this.options.testParameters && data.testParameters) {
const isValid = this.validateParameters(data.testParameters);
if (!isValid) {
console.log(`⚠️ Queue parameters changed, creating new queue...`);
this.clearQueueFile();
return;
}
}
this.queue = data.queue || [];
this.completed = data.completed || [];
this.failed = data.failed || [];
// In-Progress URLs zurücksetzen
this.queue.forEach(item => {
if (item.status === 'in-progress') {
item.status = 'pending';
}
});
console.log(`📋 Loaded queue: ${this.queue.length} pending, ${this.completed.length} completed, ${this.failed.length} failed`);
}
}
catch (error) {
console.error(`💥 Failed to load queue: ${error}`);
}
}
/**
* Parameter validieren
*/
validateParameters(savedParameters) {
if (!this.options.testParameters)
return false;
const current = this.options.testParameters;
const saved = savedParameters;
// Kritische Parameter vergleichen
return (current.sitemapUrl === saved.sitemapUrl &&
current.maxPages === saved.maxPages &&
current.pa11yStandard === saved.pa11yStandard &&
current.timeout === saved.timeout &&
current.collectPerformanceMetrics === saved.collectPerformanceMetrics &&
current.generateDetailedReport === saved.generateDetailedReport &&
current.generatePerformanceReport === saved.generatePerformanceReport &&
current.generateSeoReport === saved.generateSeoReport);
}
/**
* Queue-Datei löschen
*/
clearQueueFile() {
try {
if (fs.existsSync(this.dataFile)) {
fs.unlinkSync(this.dataFile);
console.log(`🗑️ Deleted invalid queue file: ${this.dataFile}`);
}
}
catch (error) {
console.error(`💥 Failed to delete queue file: ${error}`);
}
}
/**
* Auto-Save starten
*/
startAutoSave() {
this.saveTimer = setInterval(() => {
this.saveQueue();
}, this.options.saveInterval);
}
/**
* Auto-Save stoppen
*/
stopAutoSave() {
if (this.saveTimer) {
clearInterval(this.saveTimer);
this.saveTimer = undefined;
}
}
/**
* Priorität für URL berechnen
*/
calculatePriority(url) {
const pattern = this.options.priorityPatterns.find(p => url.includes(p.pattern));
return pattern ? pattern.priority : 10; // Standard-Priorität
}
/**
* Queue leeren
*/
clear() {
this.queue = [];
this.completed = [];
this.failed = [];
this.saveQueue();
}
/**
* Queue-Datei nach erfolgreichem Abschluss löschen
*/
cleanup() {
try {
if (fs.existsSync(this.dataFile)) {
fs.unlinkSync(this.dataFile);
console.log(`🧹 Cleaned up queue file: ${this.dataFile}`);
}
}
catch (error) {
console.error(`💥 Failed to cleanup queue file: ${error}`);
}
}
/**
* Fehlgeschlagene URLs erneut versuchen
*/
retryFailed() {
const failedUrls = this.failed.map(item => item.url);
this.failed = [];
this.addUrls(failedUrls);
console.log(`🔄 Added ${failedUrls.length} failed URLs back to queue`);
}
/**
* Queue-Statistiken anzeigen
*/
showStats() {
const status = this.getStatus();
console.log(`\n📊 Queue Statistics:`);
console.log(` 📋 Total URLs: ${status.total}`);
console.log(` ⏳ Pending: ${status.pending}`);
console.log(` 🔄 In Progress: ${status.inProgress}`);
console.log(` ✅ Completed: ${status.completed}`);
console.log(` ❌ Failed: ${status.failed}`);
console.log(` ⏭️ Skipped: ${status.skipped}`);
console.log(` 📈 Progress: ${status.progress}%`);
}
}
exports.TestQueue = TestQueue;
//# sourceMappingURL=test-queue.js.map