From c776efaec95d8eb7bfd4ec4f92a2e6afd21448ff Mon Sep 17 00:00:00 2001 From: Lucas Santana Date: Fri, 27 Dec 2024 15:56:41 -0300 Subject: [PATCH] Erro ao salvar no supabase --- supabase/functions/process-audio/analyzer.ts | 12 +++- supabase/functions/process-audio/index.ts | 61 ++++++++------------ supabase/functions/process-audio/logger.ts | 37 ++++++++++++ supabase/functions/process-audio/whisper.ts | 12 +++- 4 files changed, 81 insertions(+), 41 deletions(-) create mode 100644 supabase/functions/process-audio/logger.ts diff --git a/supabase/functions/process-audio/analyzer.ts b/supabase/functions/process-audio/analyzer.ts index a828a26..81839bf 100644 --- a/supabase/functions/process-audio/analyzer.ts +++ b/supabase/functions/process-audio/analyzer.ts @@ -1,5 +1,6 @@ import { OpenAI } from 'https://deno.land/x/openai@v4.20.1/mod.ts' import { createClient } from 'https://esm.sh/@supabase/supabase-js@2' +import { createLogger } from './logger.ts' const openai = new OpenAI({ apiKey: Deno.env.get('OPENAI_API_KEY') @@ -22,10 +23,11 @@ interface ReadingAnalysis { export async function analyzeReading( transcription: string, - storyId: string + storyId: string, + logger: Logger ): Promise { try { - console.log('Analisando leitura para story_id:', storyId) + logger.info('analysis_start', 'Iniciando análise', { storyId }) const supabase = createClient( Deno.env.get('SUPABASE_URL') ?? '', @@ -40,10 +42,14 @@ export async function analyzeReading( .order('page_number', { ascending: true }) if (storyError) { - console.error('Erro ao buscar história:', storyError) + logger.error('story_fetch', storyError) throw storyError } + logger.info('story_loaded', 'História carregada', { + pageCount: storyPages?.length + }) + if (!storyPages || storyPages.length === 0) { console.error('Dados da história inválidos:', storyPages) throw new Error('Texto da história não encontrado') diff --git a/supabase/functions/process-audio/index.ts b/supabase/functions/process-audio/index.ts index 98b8767..332ef7d 100644 --- a/supabase/functions/process-audio/index.ts +++ b/supabase/functions/process-audio/index.ts @@ -2,6 +2,7 @@ import { serve } from 'https://deno.land/std@0.168.0/http/server.ts' import { createClient } from 'https://esm.sh/@supabase/supabase-js@2' import { processAudioWithWhisper } from './whisper.ts' import { analyzeReading } from './analyzer.ts' +import { createLogger } from './logger.ts' const corsHeaders = { 'Access-Control-Allow-Origin': '*', @@ -37,56 +38,44 @@ serve(async (req) => { return new Response('ok', { headers: corsHeaders }) } - let data: any = null - + let logger: any = null + try { - // Log dos headers para debug - console.log('Headers:', Object.fromEntries(req.headers.entries())) + const data = await req.json() + logger = createLogger(data?.record?.id || 'unknown') - // Validação inicial do body - const body = await req.text() - console.log('Raw body:', body) - console.log('Body length:', body.length) - console.log('Body type:', typeof body) + logger.info('request_received', 'Iniciando processamento', { + headers: Object.fromEntries(req.headers.entries()) + }) - data = JSON.parse(body) - - // Validação do record - if (!data.record || !data.record.id || !data.record.audio_url) { - return new Response( - JSON.stringify({ - error: 'Payload inválido', - details: 'record, id e audio_url são obrigatórios', - receivedData: data - }), - { - status: 400, - headers: { ...corsHeaders, 'Content-Type': 'application/json' } - } - ) + // Validação + if (!data?.record?.id || !data?.record?.audio_url) { + logger.error('validation', new Error('Payload inválido')) + throw new Error('Dados inválidos') } + const audioRecord = data.record as AudioRecord + logger.info('record_loaded', 'Registro carregado', audioRecord) + + // Processamento + logger.info('processing_start', 'Iniciando processamento do áudio') + const transcription = await processAudioWithWhisper(audioRecord.audio_url, logger) + logger.info('transcription_complete', 'Transcrição concluída', { length: transcription.length }) + + const analysis = await analyzeReading(transcription, audioRecord.story_id, logger) + logger.info('analysis_complete', 'Análise concluída', { scores: analysis }) + const supabase = createClient( Deno.env.get('SUPABASE_URL') ?? '', Deno.env.get('SUPABASE_SERVICE_ROLE_KEY') ?? '' ) - const audioRecord = data.record as AudioRecord - console.log('AudioRecord', audioRecord) - // 1. Atualiza status para processing await supabase .from('story_recordings') .update({ status: 'processing' }) .eq('id', audioRecord.id) - // 2. Processa o áudio com Whisper - const transcription = await processAudioWithWhisper(audioRecord.audio_url) - - // 3. Analisa a leitura - const analysis = await analyzeReading(transcription, audioRecord.story_id) - console.log('Análise concluída', analysis) - // 4. Atualiza o registro com os resultados const updateData = { status: 'completed', @@ -102,11 +91,11 @@ serve(async (req) => { self_corrections: analysis.self_corrections || 0, strengths: Array.isArray(analysis.strengths) ? analysis.strengths : [], improvements: Array.isArray(analysis.improvements) ? analysis.improvements : [], - suggestions: analysis.suggestions || '', - analysis: JSON.stringify(analysis.raw_data) + suggestions: analysis.suggestions || '' } console.log('Dados para atualização:', updateData) + console.log('AudioRecord', audioRecord) const { error: updateError } = await supabase .from('story_recordings') diff --git a/supabase/functions/process-audio/logger.ts b/supabase/functions/process-audio/logger.ts new file mode 100644 index 0000000..84750f7 --- /dev/null +++ b/supabase/functions/process-audio/logger.ts @@ -0,0 +1,37 @@ +export interface LogContext { + requestId: string + recordId: string + step: string + timestamp: string +} + +export function createLogger(recordId: string) { + const requestId = crypto.randomUUID() + + return { + info: (step: string, message: string, data?: any) => { + console.log(JSON.stringify({ + level: 'info', + requestId, + recordId, + step, + message, + data, + timestamp: new Date().toISOString() + })) + }, + + error: (step: string, error: Error, data?: any) => { + console.error(JSON.stringify({ + level: 'error', + requestId, + recordId, + step, + message: error.message, + stack: error.stack, + data, + timestamp: new Date().toISOString() + })) + } + } +} \ No newline at end of file diff --git a/supabase/functions/process-audio/whisper.ts b/supabase/functions/process-audio/whisper.ts index 9200c97..a46e197 100644 --- a/supabase/functions/process-audio/whisper.ts +++ b/supabase/functions/process-audio/whisper.ts @@ -1,17 +1,25 @@ import { OpenAI } from 'https://deno.land/x/openai@v4.20.1/mod.ts' +import { createLogger } from './logger.ts' const openai = new OpenAI({ apiKey: Deno.env.get('OPENAI_API_KEY') }) -export async function processAudioWithWhisper(audioUrl: string): Promise { +export async function processAudioWithWhisper(audioUrl: string, logger: Logger): Promise { try { - // Download do áudio + logger.info('whisper_start', 'Iniciando download do áudio', { url: audioUrl }) + const audioResponse = await fetch(audioUrl) if (!audioResponse.ok) { + logger.error('whisper_download', new Error(`HTTP ${audioResponse.status}`)) throw new Error('Falha ao baixar áudio') } + const audioBlob = await audioResponse.blob() + logger.info('whisper_download_complete', 'Download concluído', { + size: audioBlob.size, + type: audioBlob.type + }) // Debug do áudio console.log('Audio blob:', {