# Cursor Rules for Refactoring Scripts to Support Integration Tests We’ve already done this for `designation_based_group_provisioning`, which you can refer to as a reference. It has both a refactored script and a corresponding `tests/` folder with integration tests to guide you. ### Step 1: Convert Directory to Snake Case If the script directory is in kebab-case (e.g., `designation-based-group-provisioning), rename it to snake_case (e.g., `designation_based_group_provisioning`). > When doing this: > - Update any relevant references in documentation in `mkdocs.yml` file > - Delete the old kebab-case directory > - Verify imports, links, and other dependencies continue to work **Before:** ```plaintext designation-based-group-provisioning/ ├── main.py ├── index.md └── tests/ └── test_main.py ``` **After:** ```plaintext designation_based_group_provisioning/ ├── main.py ├── index.md └── tests/ └── test_main.py ``` ### Step 2: Refactor `main.py` **Only Refactor (strict):** - Keep **all logic inside functions**, with a single entry point: `main(args: argparse.Namespace)` - Within `main()` there are different functions: - Pass **only the necessary `args`** to those functions - Avoid any use of global or implicit access - **Do NOT**: - Restructure or rename any functions or logic - Don't change any args parsing code - Change the sequence or flow of logic blocks **Example:** ```python def main(args: argparse.Namespace): # Initialize Atlan client client = get_client(impersonate_user_id=args.user_id) client = set_package_headers(client) # Use args in each function call result1 = operation1(args.some_value1, client) result2 = operation2(result1, args.some_value2, client) if __name__ == "__main__": args = parser.parse_args() main(args=args) ``` ## Step3: Implementing Testing Rules ### Expected Directory Structure ```plaintext my_script/ ├── main.py └── tests/ └── test_main.py # Integration tests ``` ### Test Guidelines for `test_main.py` Structure your test file similar to `designation_based_group_provisioning/tests/test_main.py`. 1. `def test_main_functions`: For small pure functions — call them directly. 2. `def test_main`: Full `main()` execution with a mocked or real config. 3. `def test_after_main` (optional): Post-checks like DB validation, audit log verification, etc. ### Mocking Strategy - Do not use `mock` or `patch` — run `main()` directly against a live Atlan tenant. - Do not mock any `pyatlan` client methods. - Use environment variables instead of hardcoded secrets/config ### Example Fixtures ```python @pytest.fixture(scope="module") def config(): return SimpleNamespace(user_id="user_123", input_file="test.csv") @pytest.fixture(scope="module") def client(config): if config.user_id: client = get_client(impersonate_user_id=config.user_id) else: client = AtlanClient() return set_package_headers(client) ``` .