#!/usr/bin/env node /** * TDD Test for SectionManager Component Extraction * * Tests the extraction of SectionManager from the monolithic editor.js * Ensures all functionality is preserved during refactoring. */ const RefactorTestRunner = require('./refactor-test-runner.js'); const runner = new RefactorTestRunner(); // First, let's define what the SectionManager API should look like const EXPECTED_SECTION_MANAGER_API = [ 'constructor', 'createSectionsFromMarkdown', 'startEditing', 'stopEditing', 'getAllSections', 'sections', // Map property, not method 'getDocumentStatus', 'getDocumentMarkdown', 'on', // event system 'emit', // event system 'handleSectionSplit', 'updateContent', 'acceptChanges', 'cancelChanges', 'resetSection' ]; runner.describe('SectionManager Component Extraction', () => { runner.it('should define expected API methods', () => { // This test defines what we expect from the extracted SectionManager const expectedMethods = EXPECTED_SECTION_MANAGER_API; runner.expect(expectedMethods.length).toBe(15); runner.expect(expectedMethods).toContain('createSectionsFromMarkdown'); runner.expect(expectedMethods).toContain('startEditing'); runner.expect(expectedMethods).toContain('stopEditing'); }); runner.it('should extract from monolithic editor.js', () => { // Load the monolithic editor.js to extract SectionManager delete require.cache[require.resolve('/home/worsch/markitect_project/markitect/static/editor.js')]; try { const editorModule = require('/home/worsch/markitect_project/markitect/static/editor.js'); runner.expect(editorModule.SectionManager).toBeTruthy(); // Set global for other tests global.SectionManager = editorModule.SectionManager; global.Section = editorModule.Section; global.EditState = editorModule.EditState; } catch (error) { throw new Error(`Failed to load monolithic editor.js: ${error.message}`); } }); runner.it('should preserve SectionManager constructor functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); runner.expect(manager).toBeInstanceOf(SectionManager); runner.expect(manager.sections).toBeInstanceOf(Map); }); runner.it('should preserve createSectionsFromMarkdown functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); const testMarkdown = `# Heading 1\nContent 1\n\n## Heading 2\nContent 2`; const sections = manager.createSectionsFromMarkdown(testMarkdown); runner.expect(Array.isArray(sections)).toBeTruthy(); runner.expect(sections.length).toBe(2); runner.expect(sections[0].currentMarkdown).toContain('Heading 1'); runner.expect(sections[1].currentMarkdown).toContain('Heading 2'); }); runner.it('should preserve section editing state management', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); const sections = manager.createSectionsFromMarkdown('# Test\nContent'); const sectionId = sections[0].id; // Test start editing runner.expect(manager.startEditing(sectionId)).toBeTruthy(); const section = manager.sections.get(sectionId); runner.expect(section.isEditing()).toBeTruthy(); // Test stop editing section.stopEditing(); runner.expect(section.isEditing()).toBeFalsy(); }); runner.it('should preserve event system functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); let eventFired = false; let eventData = null; manager.on('test-event', (data) => { eventFired = true; eventData = data; }); manager.emit('test-event', { test: 'data' }); runner.expect(eventFired).toBeTruthy(); runner.expect(eventData).toEqual({ test: 'data' }); }); runner.it('should preserve document status functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); manager.createSectionsFromMarkdown('# Test\nContent'); const status = manager.getDocumentStatus(); runner.expect(status).toHaveProperty('totalSections'); runner.expect(status).toHaveProperty('editingSections'); runner.expect(status.totalSections).toBe(1); }); runner.it('should preserve getAllSections functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); const testMarkdown = '# One\nContent\n\n# Two\nMore content'; manager.createSectionsFromMarkdown(testMarkdown); const allSections = manager.getAllSections(); runner.expect(Array.isArray(allSections)).toBeTruthy(); runner.expect(allSections.length).toBe(2); }); runner.it('should preserve section splitting functionality', () => { const SectionManager = global.SectionManager; const manager = new SectionManager(); const sections = manager.createSectionsFromMarkdown('# Original\nContent'); const sectionId = sections[0].id; const newContent = '# Split 1\nContent 1\n\n# Split 2\nContent 2'; const newSections = manager.handleSectionSplit(sectionId, newContent); runner.expect(Array.isArray(newSections)).toBeTruthy(); runner.expect(newSections.length).toBe(2); runner.expect(manager.sections.has(sectionId)).toBeFalsy(); // Original removed }); }); // Export API tests for use during extraction const SECTION_MANAGER_API_TESTS = [ (SectionManager) => { const manager = new SectionManager(); if (!manager.sections || !(manager.sections instanceof Map)) { throw new Error('sections property missing or not a Map'); } }, (SectionManager) => { const manager = new SectionManager(); if (typeof manager.createSectionsFromMarkdown !== 'function') { throw new Error('createSectionsFromMarkdown method missing'); } }, (SectionManager) => { const manager = new SectionManager(); if (typeof manager.startEditing !== 'function') { throw new Error('startEditing method missing'); } }, (SectionManager) => { const manager = new SectionManager(); if (typeof manager.stopEditing !== 'function') { throw new Error('stopEditing method missing'); } } ]; module.exports = { runner, EXPECTED_SECTION_MANAGER_API, SECTION_MANAGER_API_TESTS }; // Run tests if called directly if (require.main === module) { console.log('🧪 Testing SectionManager Component Extraction'); runner.run().then(() => { console.log('✅ SectionManager extraction tests completed'); }); }