Skill: Exporter
SkillWeb & browsingAdding or modifying export formats (HTML5, SCORM, EPUB3, IMS-CP) in src/shared/export/. Every change must ship with colocated `*.spec.ts` tests validating the generated ZIP structure and manifests, keep patch coverage ≥ 90% on changed lines, include or update a Playwright spec exercising both browser-side and server-side export paths, and pass `make fix`, `make test-unit`, `make test-integration`, `make test-e2e`, and `make test-e2e-static` before submission.
Available today. Use it from your connected AI after setup.
No other account needed.
Connect ahel once, and every AI you use reads what you have installed.
Then ask your AI: use the Skill: Exporter skill
What this skill tells your AI
The instructions your AI receives, as published by exelearning/exelearning in .agents/skills/exporter/SKILL.md and read by ahel’s review.
Parent: AGENTS.md | Related: backend-service, idevice
When to Use
Adding or modifying export formats in src/shared/export/.
Key Files
src/shared/export/exporters/BaseExporter.ts— abstract base class (extend this)src/shared/export/exporters/Html5Exporter.ts— reference implementationsrc/shared/export/exporters/*.ts— Html5, Scorm12, Scorm2004, Ims, Epub3, Elpx, Component, Page, PrintPreviewsrc/shared/export/renderers/—PageRenderer.ts,IdeviceRenderer.tssrc/shared/export/generators/—OdeXmlGenerator.ts, manifest generators,LomMetadata.ts,I18nGenerator.tssrc/shared/export/providers/— asset and resource providerssrc/shared/export/adapters/—YjsDocumentAdapter.ts,BrowserAssetProvider.ts,ExportAssetResolver.tssrc/shared/export/browser/— browser-side shims for shared codesrc/shared/export/utils/—LibraryDetector.ts,GlobalFontGenerator.tspublic/preview-sw.js— Service Worker for preview
Architecture
Browser (primary path) Server (CLI/API only)
───────────────────── ─────────────────────
SharedExporters → ZIP in memory POST /api/export/:sessionId/:type
→ download (web) / save (Electron) → Y.Doc from DB → exporters → ZIP → stream
The primary export path is browser-side. Server-side export exists only for CLI commands and the external API.
generateForPreview()— generates files in memory, sends to Service Worker viapostMessagegenerate()— full export with ZIP creation
Memory Considerations
Large projects (150MB+) can cause OOM during export. Key patterns (example: PR #1527):
- Chunked base64 conversion — never convert large blobs to base64 in one shot.
- Sequential asset processing — process assets one at a time, not all in parallel.
- Metadata-only listing — use lightweight metadata APIs instead of loading full asset content.
Use the built-in profiling flags to diagnose issues before adding ad-hoc logging:
window.eXeLearning.config.debugElpxExport = true;
// After export: window.__lastElpxExportSummary
Commands
bun test src/shared/export/exporters/MyExporter.spec.ts # Single test
bun test src/shared/export/ # All export tests
make fix # Lint
Gotchas
- Browser-first architecture — the exporter must work in the browser. Server-side is the secondary path.
- JSZip for extraction, Archiver for creation — don't mix them up. Always check
zipEntry.dirbefore reading content. - Test both
generate()andgenerateForPreview()— they have different code paths (ZIP vs in-memory files). - Browser adapter required — if your exporter needs browser APIs, create a shim in
src/shared/export/browser/. - IdeviceRenderer wrapper divs —
<div class="exe-text">wrappers accumulate on re-import. Normalize during import, not during export. Example: PR #1559. - Library detection — if the exported content uses MathJax or other libraries,
LibraryDetectormust find them. Tests should verify no 404s for library resources. - Preview resource loading — preview must not tolerate missing resources. MathJax loads from
/app/common/exe_math/tex-mml-svg.js(bypasses the Service Worker whenaddMathJax: true). Other libraries are detected byLibraryDetector, fetched byResourceFetcher, and served by the Service Worker. Verify no 404s in preview flows when touching export or resource detection.
Done When
- Extends
BaseExporter -
.spec.tscolocated and passing at 90%+ coverage - Both
generate()andgenerateForPreview()tested - Browser adapter created if needed (
src/shared/export/browser/) - Large-file scenario considered (no O(n^2) conversions)
-
make fixpasses clean
Signals
- GitHub stars
- 142
- Forks
- 32
- Last commit
- Sep 2026
Advanced
- Catalog kind
- skill
- Gateway key
exporter- Source
- github.com/exelearning/exelearning