initial wcag-ada
This commit is contained in:
parent
042b8cb83a
commit
d52cfe7de2
112 changed files with 9069 additions and 0 deletions
152
apps/wcag-ada/worker/src/workers/scan-worker.ts
Normal file
152
apps/wcag-ada/worker/src/workers/scan-worker.ts
Normal file
|
|
@ -0,0 +1,152 @@
|
|||
import { Worker, Job } from 'bullmq';
|
||||
import { AccessibilityScanner } from '@wcag-ada/scanner';
|
||||
import type { AccessibilityScanOptions } from '@wcag-ada/shared';
|
||||
import { getWorkerConfig } from '@wcag-ada/config';
|
||||
import { logger } from '../utils/logger';
|
||||
import { prisma } from '../utils/prisma';
|
||||
import { createRedisConnection } from '../utils/redis';
|
||||
|
||||
interface ScanJobData {
|
||||
jobId: string;
|
||||
websiteId: string;
|
||||
userId: string;
|
||||
options: AccessibilityScanOptions;
|
||||
}
|
||||
|
||||
export class ScanWorker {
|
||||
private worker: Worker<ScanJobData> | null = null;
|
||||
private scanner: AccessibilityScanner | null = null;
|
||||
private config = getWorkerConfig();
|
||||
|
||||
async start(): Promise<void> {
|
||||
// Initialize scanner
|
||||
this.scanner = new AccessibilityScanner(logger);
|
||||
await this.scanner.initialize();
|
||||
|
||||
// Create worker
|
||||
this.worker = new Worker<ScanJobData>(
|
||||
this.config.queueName,
|
||||
async (job) => this.processJob(job),
|
||||
{
|
||||
connection: createRedisConnection(),
|
||||
concurrency: this.config.concurrency,
|
||||
}
|
||||
);
|
||||
|
||||
// Setup event handlers
|
||||
this.worker.on('completed', (job) => {
|
||||
logger.info('Job completed', { jobId: job.id, data: job.data });
|
||||
});
|
||||
|
||||
this.worker.on('failed', (job, err) => {
|
||||
logger.error('Job failed', {
|
||||
jobId: job?.id,
|
||||
error: err.message,
|
||||
stack: err.stack,
|
||||
});
|
||||
});
|
||||
|
||||
this.worker.on('error', (err) => {
|
||||
logger.error('Worker error', err);
|
||||
});
|
||||
}
|
||||
|
||||
private async processJob(job: Job<ScanJobData>): Promise<void> {
|
||||
const { jobId, websiteId, userId, options } = job.data;
|
||||
|
||||
logger.info('Processing scan job', { jobId, websiteId });
|
||||
|
||||
try {
|
||||
// Update job status
|
||||
await prisma.scanJob.update({
|
||||
where: { id: jobId },
|
||||
data: {
|
||||
status: 'RUNNING',
|
||||
startedAt: new Date(),
|
||||
},
|
||||
});
|
||||
|
||||
// Perform scan
|
||||
if (!this.scanner) {
|
||||
throw new Error('Scanner not initialized');
|
||||
}
|
||||
|
||||
const result = await this.scanner.scan(options);
|
||||
|
||||
// Save result
|
||||
const scanResult = await prisma.scanResult.create({
|
||||
data: {
|
||||
websiteId,
|
||||
jobId,
|
||||
url: result.url,
|
||||
scanDuration: result.scanDuration,
|
||||
summary: result.summary as any,
|
||||
violations: result.violations as any,
|
||||
passes: result.passes as any,
|
||||
incomplete: result.incomplete as any,
|
||||
inapplicable: result.inapplicable as any,
|
||||
pageMetadata: result.pageMetadata as any,
|
||||
wcagCompliance: result.wcagCompliance as any,
|
||||
},
|
||||
});
|
||||
|
||||
// Update job status
|
||||
await prisma.scanJob.update({
|
||||
where: { id: jobId },
|
||||
data: {
|
||||
status: 'COMPLETED',
|
||||
completedAt: new Date(),
|
||||
},
|
||||
});
|
||||
|
||||
// Update website compliance score
|
||||
await prisma.website.update({
|
||||
where: { id: websiteId },
|
||||
data: {
|
||||
lastScanAt: new Date(),
|
||||
complianceScore: result.summary.score,
|
||||
},
|
||||
});
|
||||
|
||||
logger.info('Scan job completed', {
|
||||
jobId,
|
||||
resultId: scanResult.id,
|
||||
score: result.summary.score,
|
||||
});
|
||||
} catch (error: any) {
|
||||
logger.error('Scan job failed', {
|
||||
jobId,
|
||||
error: error.message,
|
||||
stack: error.stack,
|
||||
});
|
||||
|
||||
// Update job status
|
||||
await prisma.scanJob.update({
|
||||
where: { id: jobId },
|
||||
data: {
|
||||
status: 'FAILED',
|
||||
error: error.message,
|
||||
completedAt: new Date(),
|
||||
},
|
||||
});
|
||||
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
async stop(): Promise<void> {
|
||||
logger.info('Stopping scan worker...');
|
||||
|
||||
if (this.worker) {
|
||||
await this.worker.close();
|
||||
this.worker = null;
|
||||
}
|
||||
|
||||
if (this.scanner) {
|
||||
await this.scanner.close();
|
||||
this.scanner = null;
|
||||
}
|
||||
|
||||
logger.info('Scan worker stopped');
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue