Skip to main content
Înapoi la blog
obsidianmiroautomationtoolsopen-source

Îmi scot board-urile din Miro și le aduc în Obsidian

Butonul Export din Miro îți dă un PNG sau un PDF — o fotografie a datelor, nu datele. Dacă board-urile tale sunt load-bearing maps of thinking adunate de-a lungul anilor, locul lor e în Obsidian: editable, searchable, într-un vault local. Cum am scos board-urile din Miro prin REST API și le-am convertit în Excalidraw / Obsidian Canvas — păstrând poziții, culori, fonturi, curved connectors, mindmap nodes — iar lecția merge mai departe decât Miro: orice SaaS merită un exit plan ÎNAINTE să-l deschizi vreodată.

Publicat 30 iunie 20266 min de citit

Orice instrument care trăiește în browser te ține ostatic la UI-ul lui. Mai ales după ce ai investit în el timp, carduri, boards — și îți dai seama că map of thinking-ul tău stă pe serverul altcuiva, într-un format pe care nu-l poți deschide fără pagina lor încărcată.

Am câteva boards în Miro care demult au devenit load-bearing — reflecții, planuri, hărți mentale adunate de-a lungul anilor. Butonul Export îți dă un PNG sau un PDF. Astea nu sunt date, e o fotografie a datelor.

De ce să le scoți afară

Vendor lock-in nu e o problemă teoretică. E concretă: ca să-ți descarci propriile date prin API, trebuie să faci upgrade la Expert tier. Adică plătești pentru permisiunea de a-ți lua înapoi ceea ce oricum e al tău.

Trăiesc de mult după principiul Obsidian-first: tot ce e important stă într-un vault local, în plain files pe care le pot pune în git, le pot da grep și le pot citi peste zece ani. Un instrument care nu exportă în formatul ăsta e un instrument din care trebuie să pleci înainte ca dependența să devină imposibil de rupt.

De ce Export nu te salvează

Butonul Export din Miro îți dă un PNG sau un PDF. Ăsta e raster — structura s-a dus. Nu poți schimba textul dintr-un box. Nu poți muta un shape. Nu poți da grep pe o etichetă. E anunțul de deces al board-ului, nu board-ul în sine.

Obsidian are două alternative care trăiesc în interiorul vault-ului: plugin-ul Excalidraw și Canvas-ul nativ. Ambele sunt JSON. Ambele sunt editable. Ambele sunt searchable. Ambele stau în vault-ul tău lângă notițe, și poți da grep pe text direct din Obsidian.

Cum le scoți când nu există un buton 'Export to Obsidian'

Când Export-ul din UI nu-ți dă ce ai nevoie, te bagi în API. Miro are un REST API: îți returnează o descriere JSON a fiecărui shape de pe un board. Excalidraw și Obsidian Canvas sunt amândouă JSON open-format. Între ele stă un mapping.

Am scris două scripturi Python. miro_to_excalidraw.py și miro_to_canvas.py. Standard library only — zero deps. Le rulezi cu un token și un board ID, primești un fișier, îl arunci în vault.

Ce a supraviețuit conversiei

Sarcina nu era doar să mut shapes dintr-o parte în alta — era să păstrez vizualul astfel încât board-ul să se citească la fel ca în Miro.

  • Poziții și dimensiuni — coordonatele fiecărui shape 1:1
  • Culori cu fill opacity (un galben la 40% rămâne la 40%)
  • Borders — culoare, grosime, stil (solid / dashed)
  • Fonturi și alignment — monospace rămâne monospace, center rămâne center
  • Connectors — săgețile se prind în aceleași puncte în care le-a prins Miro
  • Curved connectors — arce bow în loc de linii drepte
  • Images încorporate în fișier (nu URL-uri externe)
  • Mindmap nodes — textul extras prin experimental Mindmap API
  • Z-ordering — overlap-ul nu se încurcă

Unde a fost incomod

API-ul Miro are câteva găuri pe care a trebuit să le ocolesc prin reverse engineering.

  • Curved connectors — Miro nu expune control points prin API. Așa că în loc de curba originală exactă sintetizez un bow — un arc cu rază fixă între cele două endpoints. Vizual apropiat, mathematically nu identic.
  • Z-index — API-ul Miro nu returnează deloc un câmp z. Care shape stă deasupra, care dedesubt? Euristică: suprafață mai mare = mai în spate. Funcționează pentru că în board-urile reale containerele mari stau de obicei sub elementele mai mici.
  • Mindmap — textul din mindmap nodes nu e accesibil prin items API-ul obișnuit. Ai nevoie de un call separat către experimental Mindmap endpoint. Filled nodes devin boxes, unfilled devin plain text.

Excalidraw vs Canvas — cum alegi

Dacă gândești în stil drawings — sketchy lines, hand-drawn feel, compoziții freeform — alege Excalidraw. Plugin-ul Excalidraw randează fișierul în aceeași estetică pe care ai văzut-o pe whiteboards.

Dacă board-urile tale sunt mai ales dreptunghiuri cu text legate prin săgeți și trăiești în Obsidian ca second brain — alege Canvas. Canvas e nativ, se deschide dintr-un click și e cusut în backlinks și tags-urile vault-ului.

Unele board-uri le convertesc în Excalidraw (unde contează visual style), altele în Canvas (unde contează viteza și feel-ul nativ). Repo-ul suportă ambele formate — alegi la rulare.

Rezumat

Python 3, standard library only. Fără pip install, fără virtualenv, fără node_modules. python3 miro_to_excalidraw.py 'BOARD_ID' 'output.excalidraw' — și fișierul e în mâinile tale.

Repo: github.com/oleksiimazurenko/miro-to-obsidian. Licență MIT. PR-uri binevenite — mai ales pentru edge case-uri pe care încă nu le-am întâlnit.

Lecția e mai mare decât Miro

SaaS lock-in-ul e un drog. Primele luni sunt gratis. La șase luni, e deja obicei. La un an, datele tale trăiesc într-un format pe care doar UI-ul lor îl poate citi. La doi ani, plătești Expert tier ca să scoți ce oricum era al tău.

Concluzia nu e „nu folosi SaaS”. Concluzia e că orice instrument pe care îl lași să devină load-bearing are nevoie de un exit plan ÎNAINTE să-l deschizi vreodată. Întrebarea „cum ies de aici când o să am nevoie” cântărește la fel de mult ca „cât de plăcut e UI-ul”. Un instrument fără export în plain-text sau fără un API deschis e un instrument cu un preț ascuns pe care îl plătești peste doi ani.

Obsidian-first nu pentru că Obsidian ar fi perfect. Ci pentru că plain markdown files sunt un format care va supraviețui însuși Obsidian-ului. La fel cum un fișier JSON Excalidraw simplu va supraviețui plugin-ului. La fel cum scriptul ăsta Python va supraviețui Miro-ului.