Skip to main content

Appendix A — Single or multi-tenant

Comment or suggest a change. Select any text to comment on it. Press Suggest edits to change the wording right on this page, then send your changes. Or comment at the end of the page with your GitHub account.

For stored data the choice barely matters, because each user’s rows are locked under that user’s own key. It matters for the server’s memory, for cost, and for who can see metadata.

One shared database One database per user
Stored data Isolated by each user’s key: another user’s rows, served by mistake, do not decrypt The same, plus physical separation
A compromised server Sees what every active user’s requests decrypt while it is compromised Sees one user’s
Metadata: counts, sizes, times Visible to the operator. Per-user tag keys stop matching across users. Visible to whoever runs it
Deleting a user Delete their copies of the account key and their rows Delete the database
Cost and operations One database to run One per user

Keys isolate stored data either way, and separate instances contain a breach

Figure A.1. One shared database compared with one database per user · Text version

The recommendation is one codebase that runs either way. Shared by default, with row-level security in the database as a second line behind the keys. A dedicated instance, run by the operator or by the user, for anyone who wants the smaller blast radius. The keys stay with the user in both.