# **Chapter 13: Profile & Permission Management System in SartajPHP** ## Profile & Permission Management System in SartajPHP This chapter explains **how profiles and permissions are created, stored, assigned, and enforced** in SartajPHP, and how Apps like `mebProfile` and `mebProfilePermission` work together to provide a flexible authorization system. --- ## 13.1 Why SartajPHP Uses Profile-Based Permissions SartajPHP separates **authentication** from **authorization**: * **Authentication** → Who the user is * **Authorization** → What the user can do Instead of assigning permissions directly to users, SartajPHP assigns permissions to **profiles**, and users are linked to profiles. This design provides: * Easier permission management * Reusable permission sets * Safer delegation * Scalable multi-user systems --- ## 13.2 Core Database Tables Involved The permission system relies on two core tables: ### 1. `member` Table Represents users. Key fields used by the permission system: * `id` → User Record ID (Primary Key) * `profile_id` → Linked profile * `userid` → Creator user ID * `parentid` → Parent user ID * `spcmpid` → Company identifier * `usertype` → `ADMIN` or `MEMBER` --- ### 2. `profile_permission` Table Represents profiles and their assigned permissions. Important fields: * `id` → Profile ID (Primary Key) * `profile_name` → Human-readable profile name * `permission_id` → Permission list (CSV or serialized) * `userid`, `parentid`, `spcmpid` * `submit_timestamp`, `update_timestamp` Each record represents **one profile**. --- ## 13.3 How Permissions Are Defined (Registration Time) Permissions are declared **when an Gate is registered**, not in the database. Example: ```php uuregisterGate( "mebProfile", "{$slibpath}/apps/permis/uumebProfileGate.php", "", "Profile", [ ["view","Profile View"], ["add","Add Record"], ["delete","Delete Record"] ] ); ``` Meaning: * `"view"` → Internal permission name (developer-facing) * `"Profile View"` → Display label (user-facing) Internally, SartajPHP expands this into: ``` mebProfile-view mebProfile-add mebProfile-delete ``` These expanded permission keys are what the framework actually checks. --- ## 13.4 Profile Creation Workflow (`uumebProfileGate.php`) The Profile Gate allows administrators to: * Create new profiles * Edit existing profiles * Assign permissions Typical flow: 1. Admin opens Profile App 2. Uses **list FrontFile** to browse profiles 3. Uses **edit FrontFile** to create or update profiles 4. Permissions are saved as text in `permission_id` The Gate itself does not need to understand permissions deeply — it only stores them. --- ## 13.5 Permission Assignment UI (`uumebProfilePermissionGate.php`) The Permission Gate provides a UI that: * Reads all registered Apps * Reads permissions declared by each App * Displays them as grouped checkboxes * Prevents users from assigning permissions they do not own This ensures **permission inheritance safety**. --- ## 13.6 Permission Inheritance Rule (Very Important) A user can **only assign permissions that they already have**. This rule prevents: * Privilege escalation * Unauthorized permission granting If an admin does not have: ``` mebProfile-delete ``` They cannot assign that permission to any profile. This rule is enforced at runtime using: ```php SphpBase::sphp_permissions()->hasPermission() ``` --- ## 13.7 How Permissions Are Stored Permissions are stored as a **text list** inside: ```sql profile_permission.permission_id ``` Example value: ``` mebProfile-view,mebProfile-add,mebProfilePermission-view ``` Why text storage? * Database-agnostic * Easy migration * No join overhead * Faster permission checks Parsing is handled internally by SartajPHP. --- ## 13.8 Permission Evaluation at Runtime When a request is processed: 1. User logs in 2. Profile ID is loaded from `member.profile_id` 3. Permissions are loaded from `profile_permission.permission_id` 4. Permissions are cached in session: ```php $this->Client->session('lstpermis', $row['permission_id']); ``` 5. Permission checks are executed using: ```php $this->page->hasPermission("view"); ``` The Gate does **not** need to know: * Which profile the user has * Where permissions came from * How they are stored --- ## 13.9 Permission Checks Inside Apps Inside an App, permission checks are explicit: ```php if ($this->page->hasPermission("add")) { // allow insert } ``` Or globally at Gate entry: ```php $this->page->getAuthenticatePerm("view"); ``` This ensures: * No hidden logic * No magic behavior * Full developer control --- ## 13.10 Why `PermisApp` Makes This Easier `PermisApp` is a **helper parent class**, not a framework requirement. It provides: * Standard CRUD flow * Permission checks for common operations * Automatic DB binding * Reduced boilerplate But: * You can build permission-based Apps without it * The real parent class is always `BasicGate` --- ## 13.11 Common Mistakes to Avoid 1. Assuming permissions auto-apply → They don’t. You must check them. 2. Naming Apps poorly → AppGate name defines permission namespace. 3. Mixing role logic with permission logic → Keep them separate. 4. Forgetting `id` as primary key → Many components rely on it. --- ## 13.12 Design Philosophy SartajPHP treats permissions as: * **Data-driven** * **Developer-defined** * **User-assignable** * **Framework-enforced** Nothing is hidden. Nothing is forced. Everything is explicit. That is why SartajPHP can scale from: * Small admin panels * To multi-company SaaS platforms --- ### End of Chapter 13 ---