| # HVAC Multi-Role Scenario Testing Plan This document outlines the structure and guidance for implementing comprehensive multi-role scenario tests for the HVAC Role Manager Testing Framework, building upon existing components like `HVAC_Test_User_Factory` and `HVAC_Test_Data_Manager`. ## Plan Overview The multi-role scenario tests will leverage the existing test framework components and transaction management to ensure isolated and reliable testing of complex role interactions. **1. Test Structure and Organization** * **Dedicated Test Class:** Create a new test class, e.g., `HVAC_Multi_Role_Test`, extending `WP_UnitTestCase`. This class will house all tests specifically related to multi-role scenarios. * **Scenario-Based Methods:** Organize tests into methods that represent specific multi-role scenarios (e.g., `test_user_with_editor_and_trainer_roles_can_publish_events`, `test_role_conflict_resolution_for_event_editing`). * **Setup Method:** Utilize the `setUp` method to initialize `HVAC_Test_User_Factory` and `HVAC_Test_Data_Manager` and potentially start a transaction if not handled by a base class. * **Teardown Method:** Ensure the `tearDown` method rolls back the transaction and cleans up any created users or data using `HVAC_Test_Data_Manager`. ```mermaid graph TD A[HVAC_Multi_Role_Test] --> B[setUp()] A --> C[test_scenario_X()] A --> D[test_scenario_Y()] A --> E[tearDown()] B --> F[Initialize Factories/Managers] B --> G[Start Transaction (if needed)] C --> H[Create User with Roles (HVAC_Test_User_Factory)] C --> I[Perform Actions/Checks] C --> J[Assert Expected Outcomes] E --> K[Rollback Transaction] E --> L[Cleanup Data/Users (HVAC_Test_Data_Manager)] ``` **2. Strategies for Testing Permission Inheritance and Conflict Resolution** * **Define Expected Capabilities:** For each multi-role combination, clearly define the expected set of capabilities based on the HVAC Role Manager's inheritance and conflict resolution logic. * **Create Users with Combinations:** Use `HVAC_Test_User_Factory` to create users with the specific role combinations being tested. The factory should handle assigning multiple roles. * **Verify Capabilities Directly:** After assigning roles, directly check the user's capabilities using WordPress functions like `user_can()` or `current_user_can()`. * **Test Actions Requiring Capabilities:** Beyond direct capability checks, test if the user can actually perform actions that require those capabilities (e.g., publishing an event, editing a specific post type). * **Pseudocode Example (Inheritance):** ```php // Assuming 'hvac_manager' inherits from 'editor' public function test_hvac_manager_inherits_editor_caps() { $user = HVAC_Test_User_Factory::get_instance()->create_test_user(['hvac_manager']); $this->assertTrue(user_can($user, 'edit_posts'), 'HVAC Manager should inherit edit_posts capability from Editor.'); $this->assertTrue(user_can($user, 'publish_posts'), 'HVAC Manager should inherit publish_posts capability from Editor.'); // Add more inherited capability checks } ``` * **Pseudocode Example (Conflict Resolution):** ```php // Assuming 'role_A' grants 'cap_X' and 'role_B' denies 'cap_X', and 'role_A' has higher priority public function test_role_conflict_resolution_priority() { $user = HVAC_Test_User_Factory::get_instance()->create_test_user(['role_A', 'role_B']); $this->assertTrue(user_can($user, 'cap_X'), 'User with Role A and Role B should have cap_X due to Role A priority.'); // Test the opposite priority if applicable // $user_b_a = HVAC_Test_User_Factory::get_instance()->create_test_user(['role_B', 'role_A']); // $this->assertFalse(user_can($user_b_a, 'cap_X'), 'User with Role B and Role A should NOT have cap_X due to Role B priority.'); } ``` **3. Approaches for Verifying Capability Checks Across Role Combinations** * **Matrix Approach:** Consider creating a matrix of relevant capabilities vs. role combinations. Each cell in the matrix represents an assertion that needs to be tested. * **Iterate Through Combinations:** Programmatically generate or define the key role combinations to test. * **Contextual Checks:** Test capabilities within the context they are used (e.g., can a user with roles X and Y edit *this specific* event?). This might involve creating test data using `HVAC_Test_Data_Manager`. * **Pseudocode Example (Capability Matrix Idea):** ```php public function test_capability_matrix() { $role_combinations = [ ['editor', 'hvac_trainer'], ['administrator', 'hvac_viewer'], // Add all relevant combinations ]; $capabilities_to_check = [ 'publish_tribe_events' => [ 'editor,hvac_trainer' => true, 'administrator,hvac_viewer' => true, // Example expected outcome ], 'view_hvac_reports' => [ 'editor,hvac_trainer' => false, 'administrator,hvac_viewer' => true, ], // Add all relevant capabilities ]; foreach ($role_combinations as $roles) { $user = HVAC_Test_User_Factory::get_instance()->create_test_user($roles); $combination_key = implode(',', $roles); foreach ($capabilities_to_check as $capability => $expected_outcomes) { if (isset($expected_outcomes[$combination_key])) { $expected = $expected_outcomes[$combination_key]; $message = "User with roles {$combination_key} should " . ($expected ? "have" : "not have") . " capability {$capability}."; $this->assertEquals($expected, user_can($user, $capability), $message); } } } } ``` **4. Best Practices for Testing Role Addition and Removal** * **Test Sequential Changes:** Test adding a role to an existing user and then removing it, verifying capabilities at each step. * **Edge Cases:** * Adding a role the user already has. * Removing a role the user doesn't have. * Removing the user's last role (should they revert to a default?). * Adding/removing roles that are part of an inheritance chain. * **Verify Persistence:** Ensure role changes persist after the operation (within the test's transaction). * **Pseudocode Example (Role Addition/Removal):** ```php public function test_role_addition_and_removal() { $user = HVAC_Test_User_Factory::get_instance()->create_test_user(['subscriber']); $this->assertFalse(user_can($user, 'publish_posts'), 'Subscriber should not publish posts initially.'); // Add editor role $user->add_role('editor'); $user = new WP_User($user->ID); // Reload user object to refresh capabilities $this->assertTrue(user_can($user, 'publish_posts'), 'User should publish posts after adding editor role.'); // Remove editor role $user->remove_role('editor'); $user = new WP_User($user->ID); // Reload user object $this->assertFalse(user_can($user, 'publish_posts'), 'User should not publish posts after removing editor role.'); } ``` **Compatibility with WordPress Testing and Architecture:** * The proposed structure uses `WP_UnitTestCase`, which is the standard for WordPress plugin unit testing. * Leveraging `HVAC_Test_User_Factory` and `HVAC_Test_Data_Manager` ensures integration with the existing framework components. * Using WordPress core functions like `user_can()`, `add_role()`, and `remove_role()` aligns with WordPress best practices. * Transaction management by `HVAC_Test_Data_Manager` provides necessary test isolation.