From c7b3f85c204668e5ee3f413dc9e14283e3baa485 Mon Sep 17 00:00:00 2001 From: waldekmastykarz Date: Sun, 1 Mar 2026 10:30:29 +0100 Subject: [PATCH 1/6] Optimize Copilot instructions for clarity and maintainability - Reorganize sections: Critical (non-obvious) vs Reference (architecture) - Add best practices link and key points from MCP server docs - Add testing guidelines: use --as-system-proxy false --port 0 --api-port 0 - Add plugin development guidance (interface selection) - Add commit message and release conventions - Add M365/Azure auth workaround notes - Add cleanup instructions for log files Architecture sections kept for cache efficiency (free after first turn) while clearly separating non-discoverable critical info. --- .github/copilot-instructions.md | 128 +++++++++++++++----------------- 1 file changed, 60 insertions(+), 68 deletions(-) diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index 3a3ce7ab..40d23711 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -1,75 +1,67 @@ # Copilot Instructions for Dev Proxy ## Overview -Dev Proxy is a cross-platform .NET API simulator and proxy for testing how applications handle API failures, rate limits, latency, and more. It is highly extensible via a plugin architecture and is configured using JSON files. The project is organized as a multi-project .NET solution. - -**Key technologies:** -- Uses a fork of Titanium.Web.Proxy: [svrooij/unobtanium-web-proxy](https://github.com/svrooij/unobtanium-web-proxy) -- CLI built with System.CommandLine -- .NET Dependency Injection is used throughout - -## Architecture -- **Main entry point:** `DevProxy/Program.cs` sets up the web host, loads configuration, logging, and plugins, and starts the proxy engine. -- **Proxy Engine:** `DevProxy/Proxy/ProxyEngine.cs` manages network interception, request/response handling, plugin invocation, and system proxy integration. -- **Plugins:** Implement the `IPlugin` interface (`DevProxy.Abstractions/Plugins/IPlugin.cs`). For most plugins, inherit from `BasePlugin` or `BaseReportingPlugin` in `DevProxy.Abstractions/Plugins/`. Plugins are loaded dynamically based on configuration in `devproxyrc.json` or similar config files. Plugins can: - - Intercept and modify requests/responses - - Add custom commands/options to the CLI (via System.CommandLine) - - React to events (recording, logging, etc.) -- **Configuration:** - - Main config: `DevProxy/config/devproxyrc.json` (or other JSON files in `config/`) - - Plugins and URLs to watch are defined here. See `m365.json` for examples. -- **Commands:** - - CLI commands are defined in `DevProxy/Commands/` and registered via `DevProxyCommand.cs` (using System.CommandLine). - - Certificate management: `cert ensure` and `cert remove` (see `CertCommand.cs`). -- **Cross-platform support:** - - macOS-specific scripts: `trust-cert.sh`, `remove-cert.sh`, `toggle-proxy.sh` in `DevProxy/`. - -## Dev Proxy MCP Server -- The Dev Proxy MCP server exposes access to Dev Proxy documentation and JSON schemas, making it invaluable for both contributors and users. -- Use the MCP server to programmatically retrieve up-to-date docs and schema definitions for config and plugins. -- See: [@devproxy/mcp on npm](https://www.npmjs.com/package/@devproxy/mcp) - -## Developer Workflows -- **Build:** Use the VS Code task `build` or run `dotnet build DevProxy.sln`. -- **Run:** Use the VS Code task `watch` or run `dotnet watch run --project DevProxy.sln`. -- **Publish:** Use the VS Code task `publish` or run `dotnet publish DevProxy.sln`. -- **Debug:** Attach to the running process or use `dotnet watch run` for hot reload. -- **Test:** (No test project detected; add tests in `tests/` if needed.) - -## Project Conventions -- **Plugin loading:** Plugins must be registered in the config file and implement `IPlugin` (preferably via `BasePlugin` or `BaseReportingPlugin`). Use the `PluginServiceExtensions` for registration logic. -- **URL matching:** URLs to watch are defined as wildcards in config and converted to regexes at runtime. -- **Logging:** Uses Microsoft.Extensions.Logging. Log levels and output are configurable. -- **Configuration tokens:** Paths in config can use `~appFolder` for resolution. -- **Hotkeys:** When running interactively, hotkeys are available (see console output for details). -- **Schema validation:** Config files reference a `$schema` for validation and versioning. -- **CLI:** All CLI commands and options are built using System.CommandLine. -- **Dependency Injection:** All services, plugins, and commands are registered and resolved via .NET DI. - -## Key Files & Directories -- `DevProxy/Program.cs` — Main entry -- `DevProxy/Proxy/ProxyEngine.cs` — Core proxy logic -- `DevProxy/Commands/` — CLI commands (System.CommandLine) -- `DevProxy/Plugins/` — Plugin loader and helpers -- `DevProxy.Abstractions/Plugins/IPlugin.cs` — Plugin interface -- `DevProxy.Abstractions/Plugins/BasePlugin.cs`, `BaseReportingPlugin.cs` — Plugin base classes -- `DevProxy/config/` — Example and default configs -- `media/` — Branding assets -- `scripts/` — Local build/setup scripts - -## External Dependencies -- [svrooij/unobtanium-web-proxy](https://github.com/svrooij/unobtanium-web-proxy) — Core proxy engine (fork of Titanium.Web.Proxy) -- Microsoft.Extensions.* — Logging, configuration, DI -- System.CommandLine — CLI framework - -## Examples -- To add a new plugin, inherit from `BasePlugin` or `BaseReportingPlugin`, implement `IPlugin`, and register it in the config file under `plugins`. -- To add a new CLI command, implement a `Command` in `DevProxy/Commands/` and register it in `DevProxyCommand.cs`. + +Dev Proxy is a cross-platform .NET API simulator and proxy for testing how applications handle API failures, rate limits, latency, and more. + +## Critical (Non-Obvious) + +- **Proxy engine:** Uses [svrooij/unobtanium-web-proxy](https://github.com/svrooij/unobtanium-web-proxy) (fork of Titanium.Web.Proxy) +- **Config tokens:** Paths in config files can use `~appFolder` for resolution +- **MCP Server:** Use [@devproxy/mcp](https://www.npmjs.com/package/@devproxy/mcp) to programmatically retrieve up-to-date docs and JSON schemas + +## Best Practices + +See the comprehensive best practices guide: https://raw.githubusercontent.com/dev-proxy-tools/mcp/refs/heads/main/assets/best-practices.md + +Key points: +- Store Dev Proxy files in `.devproxy` folder in the workspace +- Schema version in `$schema` must match installed Dev Proxy version +- In config files: `plugins` first, then `urlsToWatch`, then plugin configs +- Plugin order matters: latency plugins first, response simulators before reporters, reporters last +- URL matching is order-dependent: most specific URLs first, use `!` prefix to exclude +- File paths are relative to the config file where they're defined +- Hot reload (v2.1.0+): config changes apply automatically without restart + +## Plugin Development + +To create a new plugin: +1. Pick the relevant interface: `IProxyPlugin` (HTTP interception) or `IStdioPlugin` (stdio communication) +2. Implement as a **public class** in a class library project +3. Override the relevant methods/events for your use case + +## Commits & Releases + +- **Commit messages:** Clear, succinct, and reference the issue they close when applicable +- **Versioning:** We follow semver. Use the `upgrade-devproxy-version` skill for version bumps +- **Release:** After release builds, homebrew and winget are updated manually + +## Testing Code Changes + +When testing code, features, or changes, **always launch the proxy in detached mode** with these settings to avoid conflicts: + +```bash +dotnet run --project DevProxy -- --as-system-proxy false --port 0 --api-port 0 +``` + +- `--as-system-proxy false` — prevents modifying system-wide network settings +- `--port 0` — lets the OS assign a random available port for the proxy +- `--api-port 0` — lets the OS assign a random available port for the API + +**Auth for M365/Azure:** No automated auth. You can try `m365 util accesstoken get` or `az account get-access-token` (use `-h` for options) but the user may not be signed in. + +**Cleanup:** After testing, stop the proxy process using `kill `. Clean up any generated log files (`devproxy-*.log`). + +## Reference (Architecture) + +- **Main entry point:** `DevProxy/Program.cs` — sets up web host, configuration, logging, plugins, and starts proxy engine +- **Proxy Engine:** `DevProxy/Proxy/ProxyEngine.cs` — network interception, request/response handling, plugin invocation +- **Plugins:** Implement `IPlugin` interface (`DevProxy.Abstractions/Plugins/IPlugin.cs`). Base classes: `BasePlugin`, `BaseReportingPlugin` in `DevProxy.Abstractions/Plugins/` +- **CLI Commands:** `DevProxy/Commands/` — built with System.CommandLine, registered via `DevProxyCommand.cs` +- **Configuration:** `DevProxy/config/devproxyrc.json` and other JSON files in `config/` +- **macOS scripts:** `trust-cert.sh`, `remove-cert.sh`, `toggle-proxy.sh` in `DevProxy/` ## Resources + - [Official documentation](https://aka.ms/devproxy) - [YouTube channel](https://youtube.com/@devproxy) - ---- - -*Update this file as project conventions evolve. For questions, see the README or open an issue.* From 7f3834783f93683cb67ab0fba89ff822c005e88c Mon Sep 17 00:00:00 2001 From: Waldek Mastykarz Date: Sun, 1 Mar 2026 11:13:40 +0100 Subject: [PATCH 2/6] Update .github/copilot-instructions.md Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- .github/copilot-instructions.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index 40d23711..de6974e5 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -50,7 +50,7 @@ dotnet run --project DevProxy -- --as-system-proxy false --port 0 --api-port 0 **Auth for M365/Azure:** No automated auth. You can try `m365 util accesstoken get` or `az account get-access-token` (use `-h` for options) but the user may not be signed in. -**Cleanup:** After testing, stop the proxy process using `kill `. Clean up any generated log files (`devproxy-*.log`). +**Cleanup:** After testing, stop the proxy using `devproxy stop` (preferred, cross-platform). If you started it with `dotnet run`, you can also stop it with `Ctrl+C` in that terminal; as a last resort, terminate the process using OS-specific tools (for example, `kill ` on Unix-like systems or Task Manager on Windows). Clean up any generated log files (`devproxy-*.log`). ## Reference (Architecture) From 1bd63e120bb5fd8886809463389252ca87e6a731 Mon Sep 17 00:00:00 2001 From: Waldek Mastykarz Date: Sun, 1 Mar 2026 11:14:20 +0100 Subject: [PATCH 3/6] Update .github/copilot-instructions.md Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- .github/copilot-instructions.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index de6974e5..f969b8af 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -26,9 +26,9 @@ Key points: ## Plugin Development To create a new plugin: -1. Pick the relevant interface: `IProxyPlugin` (HTTP interception) or `IStdioPlugin` (stdio communication) -2. Implement as a **public class** in a class library project -3. Override the relevant methods/events for your use case +1. Implement the `IPlugin` interface (`DevProxy.Abstractions/Plugins/IPlugin.cs`) either directly or by inheriting from `BasePlugin` / `BaseReportingPlugin`. Optionally implement `IStdioPlugin` for stdio-based communication. +2. Implement it as a **public class** in a class library project. +3. Implement the required interface members and override any relevant base class methods/events for your use case. ## Commits & Releases From ae7a5fe9a3f914638fda75cc08672b61bc02388b Mon Sep 17 00:00:00 2001 From: Waldek Mastykarz Date: Sun, 1 Mar 2026 11:14:32 +0100 Subject: [PATCH 4/6] Update .github/copilot-instructions.md Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- .github/copilot-instructions.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index f969b8af..12a01836 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -41,7 +41,7 @@ To create a new plugin: When testing code, features, or changes, **always launch the proxy in detached mode** with these settings to avoid conflicts: ```bash -dotnet run --project DevProxy -- --as-system-proxy false --port 0 --api-port 0 +dotnet run --project DevProxy -- --detach --as-system-proxy false --port 0 --api-port 0 ``` - `--as-system-proxy false` — prevents modifying system-wide network settings From cc184a0987e6de88dd337db8cfbb60e5caa7e792 Mon Sep 17 00:00:00 2001 From: Waldek Mastykarz Date: Sun, 1 Mar 2026 11:14:53 +0100 Subject: [PATCH 5/6] Update .github/copilot-instructions.md Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- .github/copilot-instructions.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/copilot-instructions.md b/.github/copilot-instructions.md index 12a01836..e7ee32f1 100644 --- a/.github/copilot-instructions.md +++ b/.github/copilot-instructions.md @@ -21,7 +21,7 @@ Key points: - Plugin order matters: latency plugins first, response simulators before reporters, reporters last - URL matching is order-dependent: most specific URLs first, use `!` prefix to exclude - File paths are relative to the config file where they're defined -- Hot reload (v2.1.0+): config changes apply automatically without restart +- Hot reload (v2.1.0+): config changes are detected and the proxy restarts automatically to apply them ## Plugin Development From 3d745642daac07585b450f29ed78948ed5ce3fc9 Mon Sep 17 00:00:00 2001 From: Garry Trinder Date: Mon, 2 Mar 2026 11:26:02 +0000 Subject: [PATCH 6/6] chore: trigger CI checks