Roles and security

The six roles, what each may see and do, where those rules are enforced, and how keys and personal data are protected.

Nigraan's rule is that the database is the gate. Each app hides the buttons a role cannot use, but that is a convenience, not the protection. Every permission is enforced by PostgreSQL row-level security and database functions, so it holds for the website, the mobile app and anyone calling the API directly.

Roles

Role Console tabs on the website Can do
Signed out — Read guides and approved data.
public — Submit reports and relief listings; read their own reports at any stage; earn badges.
validator Review queue, Badge reviews Approve or refuse undecided reports; link duplicates; confirm or decline badges; expire or delete records.
partner Partner tools Upload datasets; read the Data page.
institutional Institutional dashboard Approve or refuse undecided reports from the Data page; expire or delete records.
donor Donor dashboard A read-only view. In the database a donor has exactly a public user's rights.
admin All six tabs Everything above, plus reversing decisions, changing roles, setting badges and removing accounts.

The rule for console tabs is in src/lib/roleAccess.ts, and the rule for review actions in src/lib/reviewStages.ts. Both are covered by tests.

Where each rule is enforced

Rule Enforced by
Only approved records are public RLS on map_records
Reporters see their own reports at any stage RLS on map_records
Only a reviewer can set or change a decision A trigger on map_records, which also covers the record's owner
A record is published or refused, never both A table constraint
Badges are reviewed by validators, and set directly only by admins SECURITY DEFINER functions that check the caller's role
Only admins manage users RLS on profiles, and the admin_remove_user function
Official data is written only by the ingest No write access for app users; the job uses the service key
Attachments have a size limit Column constraints (900,000 characters each)

The mobile app shows badges but never awards them. Awarding happens only in the website's console.

Keys

Key Where it lives Power
Publishable key In both apps, by design None by itself: every request is limited by RLS to what the caller's role allows.
Service key GitHub Actions secrets only Bypasses RLS. Used by the ingest and facilities jobs. Never in the apps, the repository, chat or screenshots.

Personal data

Reporting a security problem

If you find a way to see or change data you should not, please do not test it further on the live site. Email info@codeforpakistan.org with what you found.

← All technical documentation