#!/usr/bin/env node /** * Fix Markdown Licences * * Replaces Apache 2.0 licence blocks with CC BY 4.0 in research paper markdown files. * Technical/code documentation files are left with Apache 2.0. * * Usage: * node scripts/fix-markdown-licences.js [--dry-run] */ const fs = require('fs').promises; const path = require('path'); const DRY_RUN = process.argv.includes('--dry-run'); // Files that should be CC BY 4.0 (research papers, articles, theoretical works) const CC_BY_FILES = [ // docs/markdown/ 'docs/markdown/tractatus-framework-research.md', 'docs/markdown/business-case-tractatus-framework.md', 'docs/markdown/organizational-theory-foundations.md', 'docs/markdown/tractatus-ai-safety-framework-core-values-and-principles.md', 'docs/markdown/GLOSSARY.md', 'docs/markdown/GLOSSARY-DE.md', 'docs/markdown/GLOSSARY-FR.md', 'docs/markdown/case-studies.md', // docs/research/ 'docs/research/pluralistic-values-research-foundations.md', 'docs/research/executive-summary-tractatus-inflection-point.md', 'docs/research/rule-proliferation-and-transactional-overhead.md', 'docs/research/concurrent-session-architecture-limitations.md', 'docs/research/ARCHITECTURAL-SAFEGUARDS-Against-LLM-Hierarchical-Dominance-Prose.md', ]; // Apache 2.0 licence text patterns to match (the block to replace) // Pattern 1: Standard block with "## License" heading const APACHE_BLOCK_STANDARD = /## License\n\nCopyright \d{4} (?:Agentic Governance Initiative|John Stroh)\n\nLicensed under the Apache License, Version 2\.0 \(the "License"\);[^]*?(?:See the License for the specific language governing permissions and limitations under the License\.)\n\n(?:\*\*Summary:\*\*\n(?:- [^\n]+\n)+)?/g; // Pattern 2: Compact header-style (lines 3-5 of some files) const APACHE_HEADER = /^(?:# .*\n)?(?:\n)?Licensed under the Apache License, Version 2\.0 \(the "License"\);\nyou may not use this file except in compliance with the License\.\nYou may obtain a copy of the License at\n\n\s+http:\/\/www\.apache\.org\/licenses\/LICENSE-2\.0\n\n(?:Unless required .*?under the License\.\n)?/m; // Pattern 3: Trailing "Apache License, Version 2.0, January 2004" line const APACHE_TRAIL = /\nApache License, Version 2\.0, January 2004\n?/g; // CC BY 4.0 replacement block function ccBy4Block(title) { return `## Licence Copyright \u00a9 2026 John Stroh. This work is licensed under the [Creative Commons Attribution 4.0 International Licence (CC BY 4.0)](https://creativecommons.org/licenses/by/4.0/). You are free to share, copy, redistribute, adapt, remix, transform, and build upon this material for any purpose, including commercially, provided you give appropriate attribution, provide a link to the licence, and indicate if changes were made. **Suggested citation:** Stroh, J., & Claude (Anthropic). (2026). *${title}*. Agentic Governance Digital. https://agenticgovernance.digital **Note:** The Tractatus AI Safety Framework source code is separately licensed under the Apache License 2.0. This Creative Commons licence applies to the research paper text and figures only. `; } // CC BY 4.0 for German glossary const CC_BY_4_DE = `## Lizenz Copyright \u00a9 2026 John Stroh. Dieses Werk ist lizenziert unter der [Creative Commons Namensnennung 4.0 International Lizenz (CC BY 4.0)](https://creativecommons.org/licenses/by/4.0/deed.de). Es steht Ihnen frei, das Material zu teilen, zu kopieren, weiterzuverbreiten, anzupassen, zu remixen, zu transformieren und darauf aufzubauen, auch kommerziell, sofern Sie eine angemessene Quellenangabe machen, einen Link zur Lizenz angeben und kenntlich machen, ob \u00c4nderungen vorgenommen wurden. **Hinweis:** Der Quellcode des Tractatus AI Safety Framework ist separat unter der Apache License 2.0 lizenziert. Diese Creative-Commons-Lizenz gilt nur f\u00fcr den Text und die Abbildungen der Forschungsarbeit. `; // CC BY 4.0 for French glossary const CC_BY_4_FR = `## Licence Copyright \u00a9 2026 John Stroh. Cette \u0153uvre est mise \u00e0 disposition selon les termes de la [Licence Creative Commons Attribution 4.0 International (CC BY 4.0)](https://creativecommons.org/licenses/by/4.0/deed.fr). Vous \u00eates libre de partager, copier, redistribuer, adapter, remixer, transformer et cr\u00e9er \u00e0 partir de ce mat\u00e9riel, y compris \u00e0 des fins commerciales, \u00e0 condition de fournir une attribution appropri\u00e9e, de fournir un lien vers la licence et d'indiquer si des modifications ont \u00e9t\u00e9 apport\u00e9es. **Note :** Le code source du Tractatus AI Safety Framework est licenci\u00e9 s\u00e9par\u00e9ment sous la Licence Apache 2.0. Cette licence Creative Commons s'applique uniquement au texte et aux figures du document de recherche. `; async function processFile(relPath) { const fullPath = path.resolve(__dirname, '..', relPath); let content; try { content = await fs.readFile(fullPath, 'utf-8'); } catch (err) { console.log(` SKIP (not found): ${relPath}`); return { file: relPath, status: 'not_found' }; } // Extract title from first H1 const titleMatch = content.match(/^#\s+(.+)$/m); const title = titleMatch ? titleMatch[1] : path.basename(relPath, '.md'); const original = content; // Determine language for glossary files const isGerman = relPath.includes('GLOSSARY-DE'); const isFrench = relPath.includes('GLOSSARY-FR'); // Replace standard Apache 2.0 block if (content.match(APACHE_BLOCK_STANDARD)) { let replacement; if (isGerman) { replacement = CC_BY_4_DE; } else if (isFrench) { replacement = CC_BY_4_FR; } else { replacement = ccBy4Block(title); } content = content.replace(APACHE_BLOCK_STANDARD, replacement); } // Replace compact header-style Apache licence (e.g., tractatus-framework-research.md) if (content.match(APACHE_HEADER)) { content = content.replace(APACHE_HEADER, ''); } // Remove trailing "Apache License, Version 2.0, January 2004" lines content = content.replace(APACHE_TRAIL, '\n'); if (content === original) { console.log(` NO CHANGE: ${relPath}`); return { file: relPath, status: 'no_change' }; } if (DRY_RUN) { console.log(` WOULD FIX: ${relPath}`); return { file: relPath, status: 'would_fix' }; } await fs.writeFile(fullPath, content, 'utf-8'); console.log(` FIXED: ${relPath}`); return { file: relPath, status: 'fixed' }; } async function main() { console.log(`\n=== Fix Markdown Licences (Apache 2.0 → CC BY 4.0) ===`); console.log(`Mode: ${DRY_RUN ? 'DRY RUN' : 'LIVE'}\n`); const results = []; for (const file of CC_BY_FILES) { results.push(await processFile(file)); } console.log('\n--- Summary ---'); const fixed = results.filter(r => r.status === 'fixed' || r.status === 'would_fix'); const noChange = results.filter(r => r.status === 'no_change'); const notFound = results.filter(r => r.status === 'not_found'); console.log(`Fixed: ${fixed.length}`); console.log(`No change needed: ${noChange.length}`); console.log(`Not found: ${notFound.length}`); if (DRY_RUN && fixed.length > 0) { console.log('\nRe-run without --dry-run to apply changes.'); } } main().catch(err => { console.error('Fatal error:', err); process.exit(1); });