Outline Wiki: Omitsis Edition
Confluence replaced by an Outline of our own: an importer we wrote that carried 343 spaces and 4,661 whole pages across, and page-level read restrictions Outline had no way to express. No per-seat licences.

Omitsis documented its work in Confluence: 343 spaces, 4,661 pages, 850 comments and 9,387 attachments, 8.4 GB in all. It worked, and it was the other half of the Atlassian bill — the first half we had already left behind when Plane replaced Jira.
The way out was the same one: take Outline, a wiki you can host yourself, deploy it on our own servers and build the missing pieces on top. Two were missing, and both are felt on day one: a Confluence importer, which Outline sells as an Enterprise feature, and a way to restrict who may read one particular page, which Outline cannot do at all.
And, as with Plane, what makes this add up is not only the base: it is that the development was done with AI. Every piece was written, tested and documented with Claude Code working on the repository, with the test suite as the safety net. A whole wiki migration and a new permission model are both, with the old tools, a team's work over months.
The base: Outline
Outline covers what a wiki is expected to do out of the box: collections, pages nested as deep as you like, a block editor with tables, attachments and diagrams, threaded comments, full-text search, groups, per-collection permissions, integrations and an API. That part was already there, and it is good.
The screenshots on this page are Outline's own, as the original project publishes them at getoutline.com. Our installation is not public and the fork is for internal use: we do not distribute it.

What we added to it
Three plugins of our own and a set of tools for the permissions. All of it is in the installation we use every day.
Importing from Confluence
- Spaces, pages and the tree — Every space is a collection and every page a page, nested exactly as it was. Personal spaces arrive as private ones.
- Authorship and dates — Each page's author and dates are the ones it had, not the day it was imported.
- Comments — With their threads and their resolved state. The ones past Outline's limit become a comment plus replies to itself, under the same name and timestamp.
- Attachments — All 9,387 files, bytes and all, without the size limit that applies the rest of the time.
- Groups and space permissions — Confluence's groups with their members, and each space's permissions as the collection's.
- Macros — Status lozenges become highlights, expands become toggle blocks, info and warning panels become notices, task lists become checkboxes. Where a live query cannot be reproduced, a visible note says what used to be there: a silently shorter page is worse than an honest gap.
- Jira links — The 1,117 issue links point at Plane under the very key they already had, and heal on their own as each project gets there.
- Nothing stops — The import is a command in a throwaway container built from the same image that is serving the site. The running service is not touched, not restarted and not redeployed. It can be run dry, or one space at a time.

Restricting who may read a page
- The switch — At the bottom of the sharing dialog: only the people listed above it, and nobody else. It applies to the whole subtree, the way Confluence view restrictions did.
- Outline could not express it — Its permission model only ever grants: a membership adds people to whoever already reached the page through its collection, and there is no deny anywhere. Without this, a wiki coming from Confluence cannot be reproduced.
- Three paths enforce it — The permission policy, the listings that filter in SQL, and search. A test asserts that a restricted page is absent from every one of them, and that test is what raises the alarm the day a fourth path appears.
- Search above all — It is the widest read path there is: it looks across every collection you can reach. Our search provider inherits Outline's own and adds the same clause, registered through the extension point they publish themselves.

Auditing and repairing the permissions
- They did not travel — Once the import was done, not one Confluence page restriction had survived: not a single row in the database. 1,997 pages could be read by people Confluence kept out, and 612 could not be read by people it let in.
- The same question of both systems — The audit reduces Confluence and Outline to “who can read this page” and shows the difference, taking into account that Confluence restrictions are inherited from the space root down.
- The repair — Each collection is given the audience most of its pages expect; the ones that want more get memberships of their own, and the ones that want less get the new restriction. 4,607 of 4,659 pages now have exactly the audience they had in Confluence, and none is unreadable by someone who was meant to reach it. The remaining 52 are listed one by one, with the two ways out.
- Checked against the application — Not only against the model: 3,200 requests made as twenty real people, and Outline's answer matched the prediction every time. Zero emails sent across the whole exercise, which with thousands of new permissions is a design decision rather than luck.

How it is built
It is a fork of Outline v1.10.1, built to keep taking their releases. What we add lives in files Outline does not have — three plugins of our own, registered through the extension points it publishes itself — and only ten files of theirs are touched, fifty-eight lines in all, each one declared with its reason written down. A script counts them and fails the build if anyone adds one without saying so.
The image that runs is ours, from the very first deploy, because Outline compiles its plugins and bundles its frontend at build time: nothing can be added to a running official image, not a plugin and not a logo. The deployment lives in a separate repository, with the database and the attachments inside the nightly backup.
Outline is published under BUSL-1.1. It is not open source — it will be in 2030, when it turns Apache 2.0 — but modifying it is explicitly allowed, and the use grant covers an internal wiki like ours without argument. What it would not cover is offering it as a service to third parties, which is why we do not.

The result
All 343 spaces are on a server of ours, with their comments, their attachments and — no small thing — the same people able to read exactly the same pages as before. The cost is the machine again, not a licence per person.
It is the second chapter of the same story as Plane, and we tell it for the same reason: with a solid base you can take home and AI to adapt it, a professional-grade internal tool stops being a team's project over months.