Import a folder of markdown

Bring a zipped folder of markdown pages into a project's documents — folders become nested pages, links and images come along.

Last updated 2026-10-10

A folder of markdown — your own, or an export from Notion, Confluence or Obsidian — comes in as a zip and becomes a tree of pages. One upload, a preview first, and the pages are ordinary documents from the moment they land.

Import

  1. Open the project’s Documents and choose Sources at the foot of the tree panel (the landing page’s Import… goes there too).
  2. Drop the .zip on the upload area, or click to pick it (if Sources already lists files, choose Upload file first). A zip opens the Import markdown preview instead of the upload queue: N documents · M folders, the tree they will make, and a count of the files that will be skipped. Nothing is written yet.
  3. Choose Import N documents. The pages are created and the first one opens; there is no report afterwards.

The pages land at the end of the root level of the document tree, nested as the folders were, as the project’s default document type, in your interface language when the project carries it and the project’s primary language otherwise. From there you move them as you would any page.

An import is a creation: importing the same zip twice makes a second copy, which an Admin moves to the Trash. It is one transaction: when the zip is refused — damaged or encrypted, over a limit, past the storage quota — nothing is written. A file that cannot be read is skipped, and a file whose markdown cannot be converted becomes an empty page.

How a folder becomes a tree

  • Every .md or .markdown file becomes a page; every folder on the way to one becomes a page that holds them. Folders with no documents beneath are left out.
  • A folder’s own text is the file that matches it: Name.md beside Name/ (how Notion exports), else index.md, else README.md, else Name/Name.md (how Obsidian keeps a folder note). The others are its children.
  • The title is the file name without its extension — Notion’s trailing id is stripped — and siblings are ordered by name, character by character (capitals before lower case, 10 before 2). Pages nest up to twenty-five levels deep; a deeper zip is refused.
  • A YAML front-matter block at the top of a file is removed and discarded; it does not become the title or properties.
  • A relative link to another .md in the zip becomes a link to the imported page, with its #fragment kept. A link to a file that was not imported stays as written. Wiki-style [[links]] and reference-style links stay as text.
  • A PNG, JPEG, GIF or WebP file in the zip that a page references with markdown image syntax is stored in the project and shown inline on the page (it is not listed under the page’s attachments); an image nobody references is left out, and Obsidian’s ![[image.png]] embeds and HTML <img> tags are not recognised. Images on the web stay as images pointing at their web address — Rindo neither fetches nor stores them; images embedded as data URIs are removed. SVG is not imported.
  • Anything else in the zip — a PDF, a Word file, another archive — is skipped and reported, never imported.

What the markdown becomes

Pages are built from the ten blocks the editor has — headings, paragraphs, bulleted, numbered and check lists, code, quotes, tables, images, dividers — so what the editor can write, the import can read: fenced code with its language, a mermaid fence rendered as a diagram, tables in the GitHub style with the first row as header, task lists as check lists, bold, italic, strikethrough and inline code, and the usual inline HTML pairs. Footnotes and autolinks in angle brackets stay as plain text; a link’s title is dropped, the link itself kept. Files must be UTF-8.

Limits

A zip is at most 25 MiB, holds at most five thousand entries and five hundred markdown files, and unpacks to at most 256 MiB of markdown; a markdown file over 1 MiB is skipped, and so is an image over the upload size limit. Encrypted zips are refused, archives inside the archive are skipped, and the images count toward the project’s storage limits like any upload.

Who, and from where

Importing takes Member. There is no MCP tool for it. Over the API, POST /api/v1/projects/{id}/documents/import takes the zip as the request body and, unlike the dialog, a parent_id, a type_id, a component_id and a source_lang; ?dry_run=true returns the preview and writes nothing.

Rindo imports documents, not issues: there is no importer for another tracker’s tasks. A single .md dropped on Sources goes through file ingestion instead — see Files and spreadsheets.