# Contributing

Thank you for your interest in contributing to the OpenAI .NET library! This guide provides information about the repository structure, development setup, and workflows.

## Repository Structure

| Folder | Description |
|--------|-------------|
| `api/` | Public API listings (`OpenAI.net*.cs`) generated by `Export-Api.ps1`. Used to track public API changes. |
| `codegen/` | TypeSpec emitter and C# generator plugins that transform TypeSpec definitions into C# code. |
| `docs/` | Guides and documentation. |
| `examples/` | Usage examples organized by feature area (Chat, Audio, Images, Assistants, etc.). |
| `scripts/` | PowerShell scripts for development workflows (code generation, API export, testing). |
| `specification/` | TypeSpec definitions from which the client library is generated — `base/` contains the base API definitions and `client/` contains client-specific customizations. |
| `src/` | Library source code — `Generated/` contains generated code and `Custom/` contains hand-written customizations. |
| `tests/` | NUnit tests with `SessionRecords/` for recorded playback mode. |

## Prerequisites

The following tools are required for development:

- **.NET SDK 10.0.100+** — Required version is specified in `global.json`. Install from the [.NET download page](https://dotnet.microsoft.com/download/dotnet/10.0).
- **Node.js** — Required for TypeSpec compilation and code generation. Install from [nodejs.org](https://nodejs.org/).
- **PowerShell** — Required for running development scripts. Available by default on Windows; install [PowerShell Core](https://github.com/PowerShell/PowerShell) on macOS/Linux.

### Optional: VS Code Dev Container / Codespaces

This repository includes a `.devcontainer/devcontainer.json` for contributors who prefer a containerized dev environment, such as the VS Code Dev Containers extension or GitHub Codespaces. It installs the required .NET SDK, Node.js, and PowerShell, then restores `OpenAI.slnx` on first create. The container defaults tests to Playback mode and disables auto-recording; override `CLIENTMODEL_TEST_MODE`/`CLIENTMODEL_DISABLE_AUTO_RECORDING` if you want Record/Live behavior.

## Building the Library

Build the library from the repository root:

```bash
dotnet build OpenAI.slnx
```

## Running Tests

Tests use the [Microsoft.ClientModel.TestFramework](https://github.com/Azure/azure-sdk-for-net/blob/main/sdk/core/Microsoft.ClientModel.TestFramework/README.md) and can run in three modes:

Before running tests, restore the repo's local .NET tools (this installs the `test-proxy` tool used by the test framework):

```bash
dotnet tool restore
```

| Mode | Description |
|------|-------------|
| **Playback** | Tests run against pre-recorded session data in `tests/SessionRecords/`. No API key required. This is the default mode. |
| **Record** | Tests run against the live OpenAI API and record HTTP interactions for later playback. |
| **Live** | Tests run against the live OpenAI API without recording. |

To switch between test modes, set the `CLIENTMODEL_TEST_MODE` environment variable to `Playback`, `Record`, or `Live`.

> **Note:** In Playback mode, if an existing session record does not match the test's requests, the framework will automatically attempt to re-record the test against the live API. To disable this auto-recording behavior, set the `CLIENTMODEL_DISABLE_AUTO_RECORDING` environment variable to `true`.

### Running Tests in Playback Mode (Default)

```bash
dotnet test OpenAI.slnx
```

### Running Tests in Record or Live Mode

Set the `OPENAI_API_KEY` environment variable and the test mode:

```bash
# PowerShell
$env:OPENAI_API_KEY = "your-api-key"
$env:CLIENTMODEL_TEST_MODE = "Record"  # or "Live"

# Bash
export OPENAI_API_KEY="your-api-key"
export CLIENTMODEL_TEST_MODE="Record"  # or "Live"
```

Then run the tests:

```bash
dotnet test OpenAI.slnx
```

When recording tests, sensitive data such as API keys and other secrets are automatically sanitized before being saved to session files. This ensures that session recordings can be safely committed to the repository. Always verify that new recordings do not contain sensitive information before committing.

## Code Generation

> **⚠️ Important:** Files in `src/Generated/` are automatically generated and will be overwritten during code generation. To customize behavior, add or modify files in `src/Custom/` instead.

The library is generated from [TypeSpec](https://typespec.io/) definitions located in the `specification/` folder. The base API definitions are in `specification/base/`, and client-specific customizations are in `specification/client/`.

### Regenerating Code

To regenerate the code from the TypeSpec specification:

```powershell
./scripts/Invoke-CodeGen.ps1
```

This script:
1. Installs npm dependencies (`npm ci`)
2. Builds the TypeSpec emitter and generator in `codegen/`
3. Compiles the TypeSpec specification and generates C# code into `src/Generated/`

## API Surface and Compatibility

### Exporting the Public API

When making changes that affect the public API surface, run the export script to update the API listings in the `api/` folder:

```powershell
./scripts/Export-Api.ps1
```

This generates `OpenAI.net*.cs` files that document the public API for each target framework.

### API Compatibility Check

To check for breaking changes against a baseline version:

```powershell
./scripts/Test-ApiCompatibility.ps1
```

This compares the current build against the specified baseline NuGet package version and reports any API incompatibilities.

### AOT Compatibility Check

To verify Native AOT compatibility:

```powershell
./scripts/Test-AotCompatibility.ps1
```

This publishes a test application with AOT and checks for trimming warnings.

## Documentation Snippets

Code snippets in documentation are synchronized from actual test code. After modifying snippets in the `tests/Snippets/` folder, run:

```powershell
./scripts/Update-Snippets.ps1
```

This updates the corresponding snippets in markdown documentation files.

## Pull Request Checklist

Before submitting a pull request, please ensure:

- [ ] All tests pass (`dotnet test OpenAI.slnx`)
- [ ] If you modified the public API, run `./scripts/Export-Api.ps1` and commit the updated `api/` files
- [ ] If you modified code snippets, run `./scripts/Update-Snippets.ps1` and commit any updated documentation
- [ ] If you regenerated code, include the regenerated files in the same commit as the changes that caused them (TypeSpec or custom code changes)
