--- name: parse_obsidian_frontmatter kind: function lang: py domain: obsidian version: "1.0.0" purity: pure signature: "def parse_obsidian_frontmatter(content: str) -> dict" description: "Separa una nota de Obsidian (Markdown plano) en su frontmatter YAML y su cuerpo. Parsea el bloque YAML delimitado por --- al inicio del archivo con yaml.safe_load. Si no hay frontmatter valido al inicio, devuelve frontmatter vacio y el contenido completo como body. Soporta finales de linea \\n y \\r\\n. Pura, sin I/O." tags: [obsidian, frontmatter, yaml, markdown, parse, note] uses_functions: [] uses_types: [] returns: [] returns_optional: false error_type: "" imports: ["yaml"] params: - name: content desc: "Texto completo de una nota de Obsidian/Markdown. El frontmatter, si existe, debe ser un bloque YAML delimitado por lineas '---' que empieza en la primera linea del archivo." output: "Dict con dos claves: 'frontmatter' (dict con el mapping YAML parseado, o {} si no hay frontmatter valido) y 'body' (str con el cuerpo de la nota tras el bloque frontmatter, o el contenido completo cuando no hay frontmatter valido)." tested: true tests: - "frontmatter basico" - "crlf line endings" - "sin frontmatter devuelve content completo" - "frontmatter sin cierre es body" - "frontmatter vacio" - "yaml invalido es body" - "content vacio" test_file_path: "python/functions/obsidian/parse_obsidian_frontmatter_test.py" file_path: "python/functions/obsidian/parse_obsidian_frontmatter.py" --- ## Ejemplo ```python note = "---\ntitle: My Note\ntags:\n - a\n - b\n---\n\nHello [[other]]." result = parse_obsidian_frontmatter(note) # { # "frontmatter": {"title": "My Note", "tags": ["a", "b"]}, # "body": "\nHello [[other]].", # } plain = "just a body, no frontmatter" parse_obsidian_frontmatter(plain) # {"frontmatter": {}, "body": "just a body, no frontmatter"} ``` ## Cuando usarla Usala al leer una nota de Obsidian desde disco cuando necesites acceder a sus metadatos YAML (tags, aliases, status, fechas) por separado del texto, o antes de modificar el frontmatter y volver a serializar con `format_obsidian_note`. Es el primer paso del round-trip parse -> modificar -> format. ## Gotchas - Un bloque frontmatter vacio (`---\n---`) parsea a `None` en YAML, que no es un dict, por lo que se trata como "sin frontmatter" y el contenido completo vuelve como body. Esto es intencional para mantener la inversa con `format_obsidian_note` (que omite frontmatter vacio). - El `---` de apertura debe estar en la primera linea exacta del contenido. Un `---` precedido de lineas en blanco o texto NO se considera frontmatter. - YAML invalido se trata como "sin frontmatter": devuelve el contenido como body en lugar de lanzar excepcion (funcion pura, sin error_type).