import { runOcr } from '../../utils/ocr/tesseractOcr' /** * Server-side OCR for mobile return page. * * POST /api/mobile/ocr-scan * Body: multipart form-data with 'image' file field (JPEG/PNG binary) * - Legacy fallback: JSON { image: "data:image/..." } (base64 data URL) * * Returns lines of recognized text. The heavy lifting (tesseract.js, deu+eng, * temp file, timeout, language cache) now lives in the shared util * server/utils/ocr/tesseractOcr.ts so the incoming-invoice pipeline reuses it. */ const OCR_TIMEOUT_MS = 60_000 export default defineEventHandler(async (event) => { const reqId = Date.now().toString(36) + Math.random().toString(36).slice(2, 6) console.log(`[OCR ${reqId}] Request received`) let imageBuffer: Buffer | null = null let filename = 'capture.jpg' const contentType = getRequestHeader(event, 'content-type') || '' try { if (contentType.includes('multipart/form-data')) { const formData = await readMultipartFormData(event) if (formData) { for (const part of formData) { if (part.name === 'image') { imageBuffer = part.data filename = part.filename || filename } } } console.log(`[OCR ${reqId}] Multipart parsed, size=${imageBuffer?.length ?? 0} bytes, filename=${filename}`) } else { // Legacy JSON base64 path const body = await readBody(event) const imageData: string | undefined = body?.image if (imageData && imageData.startsWith('data:image/')) { const base64 = imageData.split(',')[1] || '' imageBuffer = Buffer.from(base64, 'base64') console.log(`[OCR ${reqId}] JSON/base64 decoded, size=${imageBuffer.length} bytes`) } } } catch (err: any) { console.error(`[OCR ${reqId}] Failed to read request body:`, err?.message || err) throw createError({ statusCode: 400, statusMessage: 'Failed to read image from request' }) } if (!imageBuffer || imageBuffer.length === 0) { console.error(`[OCR ${reqId}] No image data in request`) throw createError({ statusCode: 400, statusMessage: 'Image data is required' }) } try { console.log(`[OCR ${reqId}] Starting OCR (deu+eng)`) const started = Date.now() const result = await runOcr(imageBuffer, { lang: 'deu+eng', timeoutMs: OCR_TIMEOUT_MS }) console.log(`[OCR ${reqId}] Completed in ${Date.now() - started}ms, confidence=${result.confidence}, textLen=${result.text.length}`) if (result.lines.length === 0) { return { success: false, message: 'No text detected in image', lines: [] } } return { success: true, lines: result.lines, fullText: result.text, confidence: result.confidence } } catch (err: any) { console.error(`[OCR ${reqId}] Processing failed:`, err?.message || err, err?.stack) throw createError({ statusCode: 500, statusMessage: 'OCR processing failed: ' + (err?.message || 'Unknown error') }) } })