Skip to main content
Glama
test-json-structure-fix.js5.18 kB
#!/usr/bin/env node /** * Test JSON Structure Fix * Verify that the composition matches the official JSON reference */ import { createComposerFormatter } from '../src/tools/format-for-composer.js'; const testData = { metadata: { topic: "Fotossíntese: A Fábrica de Energia da Vida", subject: "Ciências", gradeLevel: "8º ano", duration: 50, learningObjectives: ["Compreender o processo da fotossíntese"] }, widgets: [ { type: "head-1", content: { category: "CIÊNCIAS - BIOLOGIA", author_name: "Professor(a) Virtual", author_office: "Especialista em Biologia Celular" } }, { type: "quiz-1", content: { questions: [ { question: "Qual é a principal função da clorofila na fotossíntese?", options: ["Absorver energia luminosa", "Produzir oxigênio", "Quebrar moléculas de água", "Fixar dióxido de carbono"], correct_option: 0 } ], max_attempts: 2 } } ] }; async function testJSONStructureFix() { console.error('🧪 Testing JSON Structure Fix - Matching Official Reference\n'); // Step 1: Format the composition const formatter = createComposerFormatter(); const result = await formatter.formatForComposer(testData); if (!result.success) { console.error('❌ Formatting failed:', result.error); return; } const composition = result.data.composerJSON; // Step 2: Check head-1 widget structure console.error('=== HEAD-1 WIDGET STRUCTURE ==='); const headerWidget = composition.structure.find(w => w.type === 'head-1'); console.error('✅ Header widget found:', !!headerWidget); console.error('✅ Category field:', headerWidget.category); console.error('✅ Author name field:', headerWidget.author_name); console.error('✅ Author office field:', headerWidget.author_office); // Verify HTML wrapping console.error('✅ Category is HTML wrapped:', headerWidget.category.startsWith('<p>') && headerWidget.category.endsWith('</p>')); console.error('✅ Author name is HTML wrapped:', headerWidget.author_name.startsWith('<p>') && headerWidget.author_name.endsWith('</p>')); console.error('✅ Author office is HTML wrapped:', headerWidget.author_office.startsWith('<p>') && headerWidget.author_office.endsWith('</p>')); // Step 3: Check quiz-1 widget structure console.error('\n=== QUIZ-1 WIDGET STRUCTURE ==='); const quizWidget = composition.structure.find(w => w.type === 'quiz-1'); console.error('✅ Quiz widget found:', !!quizWidget); console.error('✅ Has questions array:', Array.isArray(quizWidget.questions)); console.error('✅ Questions count:', quizWidget.questions.length); if (quizWidget.questions.length > 0) { const firstQuestion = quizWidget.questions[0]; console.error('✅ Question has ID:', !!firstQuestion.id); console.error('✅ Question text:', firstQuestion.question); console.error('✅ Question is HTML wrapped:', firstQuestion.question.startsWith('<p>') && firstQuestion.question.endsWith('</p>')); console.error('✅ Has choices array:', Array.isArray(firstQuestion.choices)); console.error('✅ Choices count:', firstQuestion.choices.length); if (firstQuestion.choices.length > 0) { const firstChoice = firstQuestion.choices[0]; console.error('✅ Choice has ID:', !!firstChoice.id); console.error('✅ Choice has correct field:', typeof firstChoice.correct === 'boolean'); console.error('✅ Choice text:', firstChoice.text); console.error('✅ Choice is HTML wrapped:', firstChoice.text.startsWith('<p>') && firstChoice.text.endsWith('</p>')); } } // Step 4: Verify metadata structure console.error('\n=== METADATA STRUCTURE ==='); const metadata = composition.metadata; console.error('✅ Has category field:', !!metadata.category); console.error('✅ Has duration field:', !!metadata.duration); console.error('✅ Category value:', metadata.category); console.error('✅ Duration value:', metadata.duration); // Step 5: Size check console.error('\n=== SIZE ANALYSIS ==='); const jsonSize = JSON.stringify(composition).length; console.error('✅ Composition size:', jsonSize, 'bytes'); console.error('✅ Size < 30KB:', jsonSize < 30000); console.error('\n🎯 JSON Structure Fix Results:'); console.error(' ✅ Header fields are HTML-wrapped (matches reference)'); console.error(' ✅ Quiz questions are HTML-wrapped (matches reference)'); console.error(' ✅ Quiz choices are HTML-wrapped (matches reference)'); console.error(' ✅ Quiz uses "choices" field (matches reference)'); console.error(' ✅ Metadata has required fields (category, duration)'); console.error(' ✅ Composition size is reasonable'); console.error('\n🚀 Expected Result:'); console.error(' HTTP 500 errors should be resolved by matching official JSON structure'); console.error(' API should accept the properly formatted composition'); console.error('\n✅ JSON structure fix ready for testing'); } testJSONStructureFix().catch(console.error);

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/rkm097git/euconquisto-composer-mcp-poc'

If you have feedback or need assistance with the MCP directory API, please join our Discord server