# c77_rbac_laravel A PostgreSQL extension that provides Laravel integration for the `c77_rbac` Role-Based Access Control system. This extension simplifies the use of `c77_rbac` in Laravel applications by providing Laravel-specific functions and utilities. ## Prerequisites - PostgreSQL 13 or later (tested on 17) - `c77_rbac` extension must be installed - Laravel 9.0 or later ## Installation ### Step 1: Install the Extension Copy the extension files to your PostgreSQL extension directory: ```bash sudo cp c77_rbac_laravel--1.0.sql c77_rbac_laravel.control /usr/share/postgresql/17/extension/ ``` ### Step 2: Create/Connect to Your Database Ensure you have a database with the `c77_rbac` extension already installed: ```sql -- Connect to your database \c your_database_name -- Verify c77_rbac is installed SELECT * FROM pg_extension WHERE extname = 'c77_rbac'; ``` ### Step 3: Enable the Laravel Extension ```sql CREATE EXTENSION c77_rbac_laravel; ``` ## Features The extension provides two key functions: 1. **c77_rbac_laravel_auth_id()** - Retrieves the current Laravel user ID from the session variable - Used in RLS policies to identify the current user - Returns NULL if the session variable is not set 2. **c77_rbac_laravel_assign_user()** - Assigns a Laravel user to a role with optional scope - Automatically converts Laravel's integer IDs to the text format used by `c77_rbac` ## Integration with Laravel ### Middleware Setup Create a middleware to set the current user's ID as the `c77_rbac.external_id` session variable: ```php [ // Other middleware... \App\Http\Middleware\SetRbacExternalId::class, ], ]; ``` ### Setting Up RBAC in Migrations ```php get(); ``` ### Manual Access Checks You can also perform manual access checks in your code: ```php $userId = Auth::id(); $canAccess = DB::selectOne(" SELECT public.c77_rbac_can_access(?, ?, ?, ?) AS result ", ['edit_content', $userId, 'department', 'marketing'])->result; if ($canAccess) { // Allow the action } else { // Deny the action } ``` ## Connection Pooling Considerations If you're using connection pooling (e.g., PgBouncer), be aware that session variables like `c77_rbac.external_id` persist for the duration of the database connection. For session pooling to work correctly: 1. Ensure your pooling is configured in "Session" mode, not "Transaction" mode 2. Set the external ID at the beginning of each request via middleware 3. Consider using a cleanup middleware for long-lived connections ## Troubleshooting ### No Rows Returned If your queries return no rows when you expect data: 1. Verify the middleware is setting the external ID: ```php $externalId = DB::selectOne("SELECT current_setting('c77_rbac.external_id', true) AS id")->id; ``` 2. Check if your user has the required role and feature: ```php $hasAccess = DB::selectOne(" SELECT public.c77_rbac_can_access(?, ?, ?, ?) AS result ", ['required_feature', Auth::id(), 'scope_type', 'scope_id'])->result; ``` ### Database Errors For "undefined_object" errors related to `c77_rbac.external_id`, ensure your middleware is running and setting the variable correctly. ## License MIT License. See `LICENSE` file for details. ## Related Projects - [c77_rbac](https://github.com/yourusername/c77_rbac) - The core RBAC extension for PostgreSQL --- For more detailed information on the underlying RBAC system, please refer to the documentation for the `c77_rbac` extension.