vk98's picture
Initial backend deployment - Hono proxy + ColPali embedding API
5dfbe50
import { Hono } from 'hono';
import { z } from 'zod';
import { config } from '../config';
import { cache } from '../services/cache';
const colpaliSearchApp = new Hono();
// Search request schema for GET requests
const searchQuerySchema = z.object({
query: z.string().min(1).max(500),
ranking: z.enum(['hybrid', 'colpali', 'bm25']).optional().default('hybrid'),
});
// Main search endpoint - matches Next.js /api/colpali-search
colpaliSearchApp.get('/', async (c) => {
try {
const query = c.req.query('query');
const ranking = c.req.query('ranking') || 'hybrid';
const validation = searchQuerySchema.safeParse({ query, ranking });
if (!validation.success) {
return c.json({ error: 'Invalid request', details: validation.error.issues }, 400);
}
const validatedData = validation.data;
// Check cache
const cacheKey = `search:${validatedData.query}:${validatedData.ranking}`;
const cachedResult = cache.get(cacheKey);
if (cachedResult) {
c.header('X-Cache', 'HIT');
return c.json(cachedResult);
}
// Proxy to backend /fetch_results endpoint
const searchUrl = `${config.backendUrl}/fetch_results?query=${encodeURIComponent(validatedData.query)}&ranking=${validatedData.ranking}`;
const response = await fetch(searchUrl);
if (!response.ok) {
throw new Error(`Backend returned ${response.status}`);
}
const data = await response.json();
// Cache the result
cache.set(cacheKey, data);
c.header('X-Cache', 'MISS');
return c.json(data);
} catch (error) {
console.error('Search error:', error);
return c.json({
error: 'Search failed',
message: error instanceof Error ? error.message : 'Unknown error'
}, 500);
}
});
export { colpaliSearchApp };