- Move deprecated directories to src/_deprecated/: - hydration/ (old pipeline approach) - scraper-v2/ (old Puppeteer scraper) - canonical-hydration/ (merged into tasks) - Unused services: availability, crawler-logger, geolocation, etc - Unused utils: age-gate-playwright, HomepageValidator, stealthBrowser - Archive outdated docs to docs/_archive/: - ANALYTICS_RUNBOOK.md - ANALYTICS_V2_EXAMPLES.md - BRAND_INTELLIGENCE_API.md - CRAWL_PIPELINE.md - TASK_WORKFLOW_2024-12-10.md - WORKER_TASK_ARCHITECTURE.md - ORGANIC_SCRAPING_GUIDE.md - Add docs/CODEBASE_MAP.md as single source of truth - Add warning files to deprecated/archived directories - Slim down CLAUDE.md to essential rules only 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
116 lines
2.8 KiB
TypeScript
116 lines
2.8 KiB
TypeScript
/**
|
|
* HomepageValidator - Content validation for homepage and marketing pages
|
|
*
|
|
* Validates that homepage content adheres to enterprise-safe phrasing
|
|
* and contains no forbidden terminology.
|
|
*/
|
|
|
|
import { ContentValidator } from './ContentValidator';
|
|
|
|
export interface HomepageContent {
|
|
hero?: {
|
|
headline?: string;
|
|
subheadline?: string;
|
|
ctaPrimary?: string;
|
|
ctaSecondary?: string;
|
|
};
|
|
features?: Array<{
|
|
title: string;
|
|
description: string;
|
|
}>;
|
|
stats?: Array<{
|
|
label: string;
|
|
value: string;
|
|
}>;
|
|
testimonials?: Array<{
|
|
quote: string;
|
|
author: string;
|
|
}>;
|
|
faq?: Array<{
|
|
question: string;
|
|
answer: string;
|
|
}>;
|
|
[key: string]: unknown;
|
|
}
|
|
|
|
export interface ValidationResult {
|
|
valid: boolean;
|
|
forbiddenTerms: string[];
|
|
warnings: string[];
|
|
}
|
|
|
|
/**
|
|
* Validate homepage content for forbidden terms
|
|
* Throws an error if forbidden terms are found (for build/deploy)
|
|
*/
|
|
export function validateHomepageContent(content: HomepageContent): void {
|
|
ContentValidator.validateOrThrow(content, 'homepage content');
|
|
}
|
|
|
|
/**
|
|
* Validate homepage content (non-throwing)
|
|
* Returns validation result with details
|
|
*/
|
|
export function checkHomepageContent(content: HomepageContent): ValidationResult {
|
|
const result = ContentValidator.validate(content);
|
|
|
|
const warnings: string[] = [];
|
|
|
|
// Check for potential issues even if technically valid
|
|
const jsonContent = JSON.stringify(content).toLowerCase();
|
|
|
|
// Warn about terms that might be close to forbidden
|
|
if (jsonContent.includes('data') && jsonContent.includes('collect')) {
|
|
warnings.push('Content mentions "data" and "collect" - ensure context is appropriate');
|
|
}
|
|
|
|
if (jsonContent.includes('automat')) {
|
|
warnings.push('Content mentions automation - verify phrasing is enterprise-appropriate');
|
|
}
|
|
|
|
return {
|
|
valid: result.valid,
|
|
forbiddenTerms: result.forbiddenTerms,
|
|
warnings,
|
|
};
|
|
}
|
|
|
|
/**
|
|
* Sanitize homepage content
|
|
* Returns cleaned content with forbidden terms replaced
|
|
*/
|
|
export function sanitizeHomepageContent<T extends HomepageContent>(content: T): T {
|
|
return ContentValidator.sanitizeContent(content);
|
|
}
|
|
|
|
/**
|
|
* Validate and sanitize in one call
|
|
* Logs warnings but returns sanitized content
|
|
*/
|
|
export function processHomepageContent<T extends HomepageContent>(
|
|
content: T,
|
|
options?: { logWarnings?: boolean }
|
|
): T {
|
|
const check = checkHomepageContent(content);
|
|
|
|
if (options?.logWarnings && check.warnings.length > 0) {
|
|
console.warn('[HomepageValidator] Warnings:', check.warnings);
|
|
}
|
|
|
|
if (!check.valid) {
|
|
console.warn(
|
|
'[HomepageValidator] Forbidden terms found and sanitized:',
|
|
check.forbiddenTerms
|
|
);
|
|
}
|
|
|
|
return sanitizeHomepageContent(content);
|
|
}
|
|
|
|
export default {
|
|
validateHomepageContent,
|
|
checkHomepageContent,
|
|
sanitizeHomepageContent,
|
|
processHomepageContent,
|
|
};
|