<?xml version="1.0" encoding="UTF-8"?>
<gsl-prompt id="20250729T185556-0400" type="feat">
<gsl-header>

# Bulletproof Pytest Setup
</gsl-header>
<gsl-block>
<gsl-purpose>
<gsl-title>

## 1. Purpose
</gsl-title>
<gsl-description>

Ensure the OBK CLI has a robust Pytest setup. 
</gsl-description>
</gsl-purpose>

<gsl-inputs>
<gsl-title>

## 2. Inputs
</gsl-title>
<gsl-description>

This table lists key artifacts—tools, articles, or other sources—that directly guide or constrain the OBK scaffold.

| Input                                                   | Notes   |
| ------------------------------------------------------- | ------- |
| ChatGPT / Codex                                         | Tool    |
| **Bulletproof Pytest Setup**                            | Article |

</gsl-description>
</gsl-inputs>

<gsl-outputs>
<gsl-title>

## 3. Outputs
</gsl-title>
<gsl-description>

This section lists the main components produced by the OBK scaffold.

* pytest.ini with coverage options
* .gitignore updated for pytest artifacts
* Manual tests for pytest usage
* tests/conftest.py
* tests/test\_sample.py

</gsl-description>
</gsl-outputs>

<gsl-workflows>
<gsl-title>

## 4. Workflows
</gsl-title>
<gsl-description>

This section lists the main steps or processes required to complete tasks in the project.

* Add test dependencies to pyproject.toml
* Install with `pip install -e .[test]`
* Create pytest.ini with correct config
* Run pytest and verify coverage
* Create conftest.py for fixtures
* Add sample test files
* Update .gitignore for pytest artifacts
* Integrate pytest into CI

</gsl-description>
</gsl-workflows>
<gsl-acceptance-tests>
<gsl-title>

## 5. Acceptance Tests
</gsl-title>
<gsl-acceptance-test id="1">
<gsl-performed-action>

1. When I run the command `pytest --help` 
</gsl-performed-action>
<gsl-expected-result>

    The console displays usage information for pytest.
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="2">
<gsl-performed-action>

2. When I run the command `pytest` with the default scaffold in place (`tests/test_sample.py`)
</gsl-performed-action>
<gsl-expected-result>

    Pytest collects and runs the sample test(s), and reports at least one passing test.
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="3">
<gsl-performed-action>

3. When I run `pytest --cov` (assuming `pytest-cov` is installed)
</gsl-performed-action>
<gsl-expected-result>

    A coverage report is displayed in the console, confirming that coverage is enabled in `pytest.ini` and works with the scaffold.
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="4">
<gsl-performed-action>

4. After running tests, I check the project directory for pytest artifacts (e.g., `.pytest_cache/` or `.coverage`)
</gsl-performed-action>
<gsl-expected-result>

    Artifacts are present, and their paths are listed in `.gitignore` to prevent accidental versioning.
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="5">
<gsl-performed-action>

5. When I run `pytest` in a CI workflow (e.g., GitHub Actions)
</gsl-performed-action>
<gsl-expected-result>

    The test suite completes successfully in CI, with output confirming that pytest and its dependencies are installed and operational in the CI environment.
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="6">
<gsl-performed-action>

6. When I review `pytest.ini`, it contains appropriate configuration for coverage and other relevant pytest options.
</gsl-performed-action>
<gsl-expected-result>

    `pytest.ini` exists at project root and specifies sensible default options (e.g., min required coverage, testpaths, etc).
</gsl-expected-result>
</gsl-acceptance-test>

<gsl-acceptance-test id="7">
<gsl-performed-action>

7. When I review `tests/conftest.py`, it contains at least one fixture or demonstrates valid fixture structure.
</gsl-performed-action>
<gsl-expected-result>

    `conftest.py` is present and importable, providing at least a placeholder fixture or instructions for extension.
</gsl-expected-result>
</gsl-acceptance-test>
</gsl-acceptance-tests>
</gsl-block>
</gsl-prompt>
