Public: anyone can read this; nobody can change it.

wiki: the three app tiers (anon, user, admin) and public apps #222

opened this view on origin

Check · Review · Land · Live — No review yet. Next: reviewer, no review yet.

Merges on the origin

docs-app-roles → main 1 commit

  • Merge on the origin. This repository mirrors open-platform/mitosis, which is truth for it. Merge there and the next sync brings back the merge commit it actually made. Open on the origin

A guest

This pull comes from a guest: its preview runs without the app's variables or a forge token until a person who can write here approves it.

This pull waits for a person who can write here to review it; it never lands on its own.

Review

Sign in to review this change.
2 files changed +16 −0
wiki/Security-Model.md +4
@@ -49,3 +49,7 @@ Every app namespace is fenced independently of CI. `pod-security.kubernetes.io/e
4949 ## Privacy defaults
5050
5151 New repos and orgs are **private by default** (`DEFAULT_PRIVATE: private`, `DEFAULT_ORG_VISIBILITY: private`). `DEFAULT_ORG_MEMBER_VISIBLE: false` closes org and org-package enumeration. The bulk users page is disabled. Anonymous browsing shows only the public seed repos. Where registration is open, it uses a sovereign image CAPTCHA — no third-party service — and internal accounts only. A new member signs in and sees exactly their own orgs, nothing else. Roles and teams are covered in [Users Teams and Access](Users-Teams-and-Access).
52
53 ## Public apps
54
55 An app is private by default: the edge signs every visitor in before the app is reached. An org can declare one app **public** (`apps/<app>/app.yaml`, `public: true`) so anonymous readers — link crawlers included — reach it. From then on the app's own door is the boundary: the template refuses every anonymous `/api` and `/openapi` request with one 401 before anything else can answer, keeps an explicit registry of anonymous reads, walks every route as a stranger in its tests, and adds a Content-Security-Policy, same-origin-only mutations and an anonymous rate limit. A signed-in stranger becomes a **user**; only Forgejo owners (or `PLAT_ADMIN_TEAMS`) are **admins**. Custom domains (`add_domain` → `verify_domain` → `set_app_domain`) get the same edge session through a host-bound handoff, so the shared login works on `shop.example` as it does on `*.__DOMAIN__`.
wiki/Users-Teams-and-Access.md +12
@@ -81,3 +81,15 @@ The platform derives each registry-bot password on demand and stores none. Agent
8181 The platform is private-first. A new member sees their own orgs and repos, the public seed repos on `/explore`, and nothing else. Every org and app repo is born private (`DEFAULT_ORG_VISIBILITY=private`, `DEFAULT_PRIVATE=private`). Other tenants' work stays invisible unless a team or collaborator grant says otherwise.
8282
8383 The first stop after sign-up is [Build Your First App](Build-Your-First-App). For app credentials, [Secrets and Config](Secrets-and-Config) shows the self-serve channel. Secrets go in repo settings, never in issues or comments.
84
85 ## Inside an app: anon, user, admin
86
87 Every app born from the template answers "who is asking?" with one of three tiers — decided in Forgejo, carried by the edge, never by a list of names in app code:
88
89 | Tier | Who | How they get it |
90 | --- | --- | --- |
91 | **anon** | No identity. | Only reaches the app when the org declares it public — `apps/<app>/app.yaml` in the org's ground with `public: true` — so link previews work. Every `/api` route still answers a stranger 401 unless the app lists that exact read as public. |
92 | **user** | A verified Forgejo identity. | Private app: anyone Forgejo lets read the repo (collaborator, team, org member). Public app: anyone who signs in. |
93 | **admin** | A Forgejo **owner**. | Org owners on every org repo; a repo's own admins on that repo. To make an org **team** admins of one app, set `PLAT_ADMIN_TEAMS=<team>,<team>` in that app's secrets — membership then lives in Forgejo. |
94
95 Granting access is therefore a Forgejo action: add someone to a team or a repo (user), make them a repo admin or an org owner (admin). Sign-in on a public app goes through the edge's `/_plat/login` on the app's own host; sign-out through `/_plat/logout`. The app's own wiki has a **Roles and Access** page with the guards and the door.

↑↓ navigate ↵ open ⌘↵ its app esc close

Keyboard shortcuts

Docs