Skip to content

Adding a module ​

The platform is built to take new kinds of work without rewiring. Pick the kind you're adding.

A new feature inside institutions ​

For example a transport module that some institutions run and others don't:

  1. Permissions. Add the page and its permissions to the permission catalogue (20260915000400_permission_catalog.sql shows the shape), then run npm run gen:permission-defs.
  2. Feature. One app.features row, its app.feature_pages rows, and app.institution_type_features rows for the types that get it by default.
  3. Tables. Add each table to app.auth_table_manifest (scope column, page key, narrowing), then select * from app.generate_policies('<table>').
  4. UI. Routes behind PermissionGate (staff) or FeatureGate (student pages), and a nav item with the pageKey.

Branch on features, never on the institution type's name.

A new institution type ​

One app.institution_types row with its vocabulary and settings, plus its app.institution_type_features. No application code changes.

A new kind of public site ​

For example a hostel with its own public site:

  1. Database. Add a branch to app.site_labels and the kind to site_domains_kind_check. Give the entity a subdomain column with the same format and reserved-label checks as the others, and check availability across every kind.
  2. Frontend. Add an entry to SITE_MODULES in src/public-site/siteModules.ts, with a renderer in src/public-site/hostSites.tsx.

The edge router and resolve_site_host need no change: they already route by whatever app.site_labels returns.

A new platform entity with its own staff ​

Libraries and stores are the pattern: a scope type, a principal_grants scope, a manager role in app.roles, provisioning RPCs that mint the auth user, principal, aliases and grant together (see create_librarian_manager), and a portal route with its own layout.

Qurtuba Foundation · Sign in at app.qurtuba.in