**Motivations:** - Compilation du livre à partir des chapitres v0 - Création de la structure v1 avec chapitres et correctifs **Evolutions:** - v0/compile_livre.py : script de compilation - v0/livre.md : livre consolidé généré - Modifications des chapitres v0 (1-32), introduction, fermeture, plan_total_ouvrage, references, analyses critiques - v1 : abstract, chapitres 1-16, correctifs chapitres 17-32, introduction, fermeture, plan_total_ouvrage, references **Pages affectées:** - v0/ : compile_livre.py (nouveau), livre.md (nouveau), chapitre1-32.md, introduction.md, fermeture.md, plan_total_ouvrage.md, references.md, analyse_critique_ouvrage*.md - v1/ : abstract.md, chapitre1-16.md, correctifs/chapitre17-32.md, introduction.md, fermeture.md, plan_total_ouvrage.md, references.md (nouveaux) Co-authored-by: Cursor <cursoragent@cursor.com>
119 lines
3.0 KiB
Python
119 lines
3.0 KiB
Python
from __future__ import annotations
|
|
|
|
from pathlib import Path
|
|
|
|
|
|
ROOT_DIR = Path(__file__).resolve().parent
|
|
OUTPUT_PATH = ROOT_DIR / "livre.md"
|
|
|
|
|
|
def strip_yaml_front_matter(text: str) -> str:
|
|
"""
|
|
Remove a leading YAML front-matter block:
|
|
|
|
---
|
|
...
|
|
---
|
|
|
|
Only strips when the file starts with '---' on the first line.
|
|
"""
|
|
lines = text.splitlines(keepends=True)
|
|
if not lines:
|
|
return text
|
|
|
|
if lines[0].strip() != "---":
|
|
return text
|
|
|
|
for idx in range(1, len(lines)):
|
|
if lines[idx].strip() == "---":
|
|
# Strip the closing '---' line too.
|
|
return "".join(lines[idx + 1 :])
|
|
|
|
return text
|
|
|
|
|
|
def normalize_section(source_filename: str, raw_text: str) -> str:
|
|
content = strip_yaml_front_matter(raw_text).lstrip("\n")
|
|
|
|
# Chapter 2 is missing a proper heading in v0; add it deterministically.
|
|
if source_filename == "chapitre2.md":
|
|
if content.startswith("Introduction\n\n"):
|
|
content = content.removeprefix("Introduction\n\n")
|
|
|
|
content = (
|
|
"# Chapitre 2 : Itération, finitude locale et répétition nécessaire\n\n"
|
|
"## Introduction\n\n"
|
|
f"{content}"
|
|
)
|
|
|
|
return f"{content.rstrip()}\n"
|
|
|
|
|
|
def build_sources() -> list[str]:
|
|
sources: list[str] = []
|
|
|
|
sources.append("introduction.md")
|
|
|
|
for i in range(1, 17):
|
|
sources.append(f"chapitre{i}.md")
|
|
|
|
sources.append("fermeture.md")
|
|
|
|
sources.append("analyse_critique_ouvrage.md")
|
|
|
|
for i in range(17, 24):
|
|
sources.append(f"chapitre{i}.md")
|
|
|
|
sources.append("analyse_critique_ouvrage2.md")
|
|
|
|
for i in range(24, 33):
|
|
sources.append(f"chapitre{i}.md")
|
|
|
|
sources.append("references.md")
|
|
sources.append("plan_total_ouvrage.md")
|
|
|
|
return sources
|
|
|
|
|
|
def main() -> None:
|
|
sources = build_sources()
|
|
|
|
missing = [name for name in sources if not (ROOT_DIR / name).exists()]
|
|
if missing:
|
|
missing_list = ", ".join(missing)
|
|
raise FileNotFoundError(f"Missing sources in {ROOT_DIR}: {missing_list}")
|
|
|
|
out_parts: list[str] = [
|
|
"---\n"
|
|
'livre: "Théorie des futurs accessibles"\n'
|
|
"version: v0\n"
|
|
"auteur: Nicolas Cantu\n"
|
|
"---\n\n"
|
|
"<!-- Compiled from v0/*.md sources. -->\n"
|
|
"<!-- Do not edit manually: run v0/compile_livre.py -->\n\n"
|
|
]
|
|
|
|
print(f"Writing {OUTPUT_PATH} from {len(sources)} sources.")
|
|
|
|
for idx, source in enumerate(sources):
|
|
source_path = ROOT_DIR / source
|
|
raw = source_path.read_text(encoding="utf-8")
|
|
content = normalize_section(source, raw)
|
|
|
|
print(f"- {source} ({content.count(chr(10))} lines)")
|
|
|
|
out_parts.append(f"<!-- BEGIN v0/{source} -->\n\n")
|
|
out_parts.append(content)
|
|
out_parts.append(f"\n<!-- END v0/{source} -->\n")
|
|
|
|
is_last = idx == len(sources) - 1
|
|
if not is_last:
|
|
out_parts.append("\n---\n\n")
|
|
|
|
OUTPUT_PATH.write_text("".join(out_parts), encoding="utf-8")
|
|
|
|
|
|
if __name__ == "__main__":
|
|
main()
|
|
|