import axios from 'axios'; import { geminiService } from './geminiService.js'; interface XRayResult { success: boolean; data?: { metadata: { title: string; description: string; image: string; tags: string[]; }; analysis: { visualDna: string[]; sentimentGap: string; superiorPrompt: string; gapAnalysis: string; }; }; error?: string; } export const xrayService = { /** * Scrapes a product URL and performs deep AI analysis */ async analyzeProduct(url: string, apiKey?: string): Promise { try { console.log(`[X-Ray] Analyzing: ${url}`); // 1. WEB RESEARCH (Google Search Grounding) // Replaces legacy Axios scraping which gets blocked (403/422) by Etsy const researchResult = await geminiService.performWebResearch(url, apiKey); if (!researchResult.title) { throw new Error("AI Retrieval failed to extract product title. The URL may not be accessible or the product page structure is unsupported."); } if (!researchResult.image) { throw new Error("AI Retrieval could not find a product image URL. Please ensure the URL points to a valid product page."); } console.log("[X-Ray] Metadata extracted via Google:", researchResult.title); // 2. Perform AI Analysis (Visual + Text) // We pass the image URL directly if public, OR we might need to download it first base64. // For stability, let's download the image to base64 buffer // Note: Since we have the direct image URL now (likely CDN), downloadImage should work better // than scraping the main page. const imageBuffer = await this.downloadImage(researchResult.image); const imageBase64 = imageBuffer.toString('base64'); const metadata = { title: researchResult.title, description: researchResult.description, image: researchResult.image, tags: [] // Search might not return tags, optional }; const analysis = await geminiService.analyzeCompetitorProduct({ title: researchResult.title, description: researchResult.description, imageBase64: imageBase64, apiKey }); return { success: true, data: { metadata, analysis } }; } catch (error: any) { console.error("[X-Ray] Error:", error.message); return { success: false, error: error.message || "Failed to analyze product" }; } }, async downloadImage(url: string): Promise { const response = await axios.get(url, { responseType: 'arraybuffer', headers: { 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/121.0.0.0 Safari/537.36', 'Referer': 'https://www.etsy.com/' } }); return Buffer.from(response.data, 'binary'); } };