All checks were successful
build-and-deploy / build-and-deploy (push) Successful in 2m41s
69 lines
1.7 KiB
TypeScript
69 lines
1.7 KiB
TypeScript
/**
|
|
* Proxy endpoint para obtener eventos de Frigate
|
|
* GET /api/frigate/events?camera=X&limit=10
|
|
*/
|
|
|
|
export default defineEventHandler(async (event) => {
|
|
// Verificar autenticación via headers de Authentik
|
|
const headers = getRequestHeaders(event)
|
|
const username = headers['x-authentik-username']
|
|
|
|
if (!username) {
|
|
throw createError({
|
|
statusCode: 401,
|
|
message: 'No autenticado'
|
|
})
|
|
}
|
|
|
|
// Leer query params
|
|
const query = getQuery(event)
|
|
const camera = query.camera as string | undefined
|
|
const limit = query.limit ? parseInt(query.limit as string) : 10
|
|
|
|
// URL interna de Frigate
|
|
const FRIGATE_URL = process.env.FRIGATE_URL || 'http://192.168.87.29:5000'
|
|
|
|
// Construir URL con filtros
|
|
const params = new URLSearchParams()
|
|
if (camera) {
|
|
// Extraer nombre base de la cámara (sin _main o _sub)
|
|
params.set('camera', camera.replace(/_main$|_sub$/, ''))
|
|
}
|
|
params.set('limit', limit.toString())
|
|
params.set('has_clip', '1') // Solo eventos con clip (1 = true)
|
|
|
|
try {
|
|
const response = await fetch(
|
|
`${FRIGATE_URL}/api/events?${params.toString()}`,
|
|
{
|
|
method: 'GET',
|
|
headers: {
|
|
'Accept': 'application/json'
|
|
}
|
|
}
|
|
)
|
|
|
|
if (!response.ok) {
|
|
throw createError({
|
|
statusCode: response.status,
|
|
message: `Error al obtener eventos: ${response.statusText}`
|
|
})
|
|
}
|
|
|
|
const events = await response.json()
|
|
|
|
return events
|
|
} catch (error: unknown) {
|
|
console.error('[Frigate Events] Error:', error)
|
|
|
|
if ((error as any).statusCode) {
|
|
throw error
|
|
}
|
|
|
|
throw createError({
|
|
statusCode: 500,
|
|
message: (error as Error)?.message || 'Error al obtener eventos'
|
|
})
|
|
}
|
|
})
|