@viaalink/caddy-api-client 0.0.0-stage → 0.10.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Viaalink
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,3 +1,676 @@
1
- # Temporary Holding Version
1
+ # @viaalink/caddy-api-client
2
2
 
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
3
+ TypeScript client for Caddy Admin API with MITMproxy integration.
4
+ Maintained by [Viaalink](https://viaalink.com).
5
+
6
+ > Formerly `@accelerated-software-development/caddy-api-client`. Same API: replace the
7
+ > package name in your `package.json` and imports; subpaths stay the same. The old name is
8
+ > deprecated and its last version (0.10.1) only re-exports this package.
9
+
10
+ Package pages:
11
+
12
+ - npm: https://www.npmjs.com/package/@viaalink/caddy-api-client
13
+ - Yarn Classic: https://classic.yarnpkg.com/en/package/@viaalink/caddy-api-client
14
+
15
+ ## Features
16
+
17
+ - ✅ **Type-safe Caddy API client** - Full TypeScript support with Zod validation
18
+ - ✅ **Route builders** - Composable functions for building Caddy routes
19
+ - ✅ **Domain management** - TLS automation with Let's Encrypt
20
+ - ✅ **Load balancing** - Health checks and multiple upstream support
21
+ - ✅ **MITMweb integration** - Traffic inspection for tunnels
22
+ - ✅ **Minimal dependencies** - Only peer dependency: `zod` for runtime validation
23
+
24
+ ## Caddy Version Compatibility
25
+
26
+ | npm Package | Caddy | caddy-security | Notes |
27
+ | ------------ | ------- | -------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
28
+ | 0.9.x–0.10.x | v2.11.4 | v1.1.64 | Current — 0.9.0: security-dense dependency bump, `caddy-dns` DNS provider plugin sources, first public vscode-extension release. 0.10.0: test-coverage-only, no dependency changes |
29
+ | 0.6.x–0.8.0 | v2.11.2 | v1.1.59 | First `caddy-dns` plugin (0.8.0) |
30
+ | 0.4.x–0.5.x | v2.10.2 | v1.1.31 | First plugin framework release |
31
+ | 0.3.x | v2.10.2 | — | Self-contained type generation |
32
+ | 0.1.x–0.2.x | — | — | Used external caddy-json-types |
33
+
34
+ See [DEPENDENCIES.md](./DEPENDENCIES.md) for full version details including commit hashes.
35
+
36
+ ## Live Demo
37
+
38
+ Experience the library in action with our interactive demo showing dynamic MITMproxy traffic inspection via Caddy Admin API.
39
+
40
+ The demo showcases:
41
+
42
+ - **Split-screen view**: Interactive search UI + MITMproxy Web UI
43
+ - **Zero-downtime route switching**: Toggle monitoring without restarts
44
+ - **Library-powered routing**: All route configuration via `caddy-api-client`
45
+
46
+ Run locally: `docker compose -f demo/docker-compose.yml up -d` → http://localhost:9080/dashboard
47
+
48
+ ## Installation
49
+
50
+ ```bash
51
+ npm install @viaalink/caddy-api-client zod
52
+ # or
53
+ yarn add @viaalink/caddy-api-client zod
54
+ # or
55
+ bun add @viaalink/caddy-api-client zod
56
+ ```
57
+
58
+ ## Quick Start
59
+
60
+ ```typescript
61
+ import { CaddyClient, buildServiceRoutes } from "@viaalink/caddy-api-client/caddy";
62
+
63
+ // Create client
64
+ const client = new CaddyClient({
65
+ adminUrl: "http://127.0.0.1:2019",
66
+ });
67
+
68
+ // Build routes with type-safe builders
69
+ const routes = buildServiceRoutes({
70
+ host: "api.localhost",
71
+ dial: "127.0.0.1:3000",
72
+ securityHeaders: {
73
+ enableHsts: true,
74
+ frameOptions: "DENY",
75
+ },
76
+ });
77
+
78
+ // Add routes to Caddy
79
+ await client.addRoutes("https_server", routes);
80
+ ```
81
+
82
+ > **⚠️ Important:** Always use our type-safe builder functions instead of constructing raw Caddy JSON objects. Our builders provide:
83
+ >
84
+ > - ✅ Full TypeScript type checking and IDE autocomplete
85
+ > - ✅ Runtime Zod schema validation
86
+ > - ✅ Protection against common configuration errors
87
+ > - ✅ Clear documentation and examples
88
+ >
89
+ > **Raw Caddy JSON is error-prone and breaks easily.** Our builders are tested, validated, and prevent mistakes.
90
+
91
+ ## Usage
92
+
93
+ ### Basic Route Management
94
+
95
+ ```typescript
96
+ import { CaddyClient, buildServiceRoutes } from "@viaalink/caddy-api-client/caddy";
97
+
98
+ const client = new CaddyClient();
99
+
100
+ // Build host-based route
101
+ const routes = buildServiceRoutes({
102
+ host: "api.localhost",
103
+ dial: "127.0.0.1:3000",
104
+ serviceId: "my-api",
105
+ });
106
+
107
+ // Add routes
108
+ for (const route of routes) {
109
+ await client.addRoute("https_server", route);
110
+ }
111
+
112
+ // Get all routes
113
+ const allRoutes = await client.getRoutes("https_server");
114
+
115
+ // Remove routes by hostname
116
+ const removed = await client.removeRoutesByHost("old-api.localhost");
117
+ ```
118
+
119
+ ### Path-based Routes
120
+
121
+ ```typescript
122
+ import { buildServiceRoutes } from "@viaalink/caddy-api-client/caddy";
123
+
124
+ const routes = buildServiceRoutes({
125
+ path: "/api",
126
+ pathRouteHost: "example.localhost",
127
+ dial: "127.0.0.1:3000",
128
+ stripPrefix: true, // Strip /api before forwarding
129
+ });
130
+ ```
131
+
132
+ ### Load Balancing
133
+
134
+ ```typescript
135
+ import { CaddyClient, buildLoadBalancerRoute } from "@viaalink/caddy-api-client/caddy";
136
+
137
+ const client = new CaddyClient();
138
+
139
+ const lbRoute = buildLoadBalancerRoute({
140
+ host: "api.localhost",
141
+ upstreams: ["127.0.0.1:3000", "127.0.0.1:3001", "127.0.0.1:3002"],
142
+ policy: "round_robin", // or "first", "random", "least_conn"
143
+ healthCheckPath: "/health",
144
+ healthCheckInterval: "10s",
145
+ });
146
+
147
+ await client.addRoute("https_server", lbRoute);
148
+ ```
149
+
150
+ ### Security Headers
151
+
152
+ ```typescript
153
+ import { buildServiceRoutes } from "@viaalink/caddy-api-client/caddy";
154
+
155
+ const routes = buildServiceRoutes({
156
+ host: "secure.localhost",
157
+ dial: "127.0.0.1:3000",
158
+ securityHeaders: {
159
+ enableHsts: true,
160
+ hstsMaxAge: 31536000, // 1 year
161
+ frameOptions: "DENY",
162
+ enableCompression: true,
163
+ },
164
+ });
165
+ ```
166
+
167
+ ### Basic Authentication
168
+
169
+ ```typescript
170
+ import { buildServiceRoutes } from "@viaalink/caddy-api-client/caddy";
171
+
172
+ const routes = buildServiceRoutes({
173
+ host: "admin.localhost",
174
+ dial: "127.0.0.1:3000",
175
+ basicAuth: {
176
+ enabled: true,
177
+ username: "admin",
178
+ passwordHash: "$2y$10$...", // bcrypt hash
179
+ realm: "Admin Area",
180
+ },
181
+ });
182
+ ```
183
+
184
+ ### MITMproxy Integration
185
+
186
+ Transparently inspect HTTP traffic for debugging production services **without modifying client or backend code, and without service restarts.**
187
+
188
+ #### Quick Start
189
+
190
+ ```bash
191
+ # 1. Start MITMproxy in Docker
192
+ docker run -d \
193
+ -p 8082:8080 \
194
+ -p 8081:8081 \
195
+ --name mitmproxy \
196
+ mitmproxy/mitmproxy:10.4.2 \
197
+ mitmweb \
198
+ --mode reverse:http://your-backend:3000 \
199
+ --web-host 0.0.0.0 \
200
+ --listen-host 0.0.0.0 \
201
+ --no-web-open-browser \
202
+ --set keep_host_header=true
203
+ ```
204
+
205
+ ```typescript
206
+ // 2. Enable traffic inspection (zero downtime)
207
+ import { CaddyClient, buildMitmproxyRoute } from "@viaalink/caddy-api-client/caddy";
208
+
209
+ const client = new CaddyClient({ adminUrl: "http://localhost:2019" });
210
+
211
+ const route = buildMitmproxyRoute({
212
+ host: "api.example.com",
213
+ mitmproxyHost: "localhost",
214
+ mitmproxyPort: 8082,
215
+ });
216
+
217
+ await client.addRoute("https_server", route, "api_debug");
218
+
219
+ // 3. View captured traffic at http://localhost:8081
220
+
221
+ // 4. Disable when done (zero downtime)
222
+ await client.removeRouteById("https_server", "api_debug");
223
+ ```
224
+
225
+ #### Hot-Swapping Between Direct and Proxied Routing
226
+
227
+ Use `buildMitmproxyRoutePair()` to easily toggle traffic inspection on/off:
228
+
229
+ ```typescript
230
+ import { CaddyClient, buildMitmproxyRoutePair } from "@viaalink/caddy-api-client/caddy";
231
+
232
+ const client = new CaddyClient({ adminUrl: "http://localhost:2019" });
233
+
234
+ // Create both direct and proxied routes
235
+ const routes = buildMitmproxyRoutePair({
236
+ host: "api.example.com",
237
+ backendHost: "api-service",
238
+ backendPort: 3000,
239
+ mitmproxyHost: "localhost",
240
+ mitmproxyPort: 8082,
241
+ routeId: "api_route",
242
+ });
243
+
244
+ // Start with direct routing (no inspection)
245
+ await client.addRoute("https_server", routes.direct, routes.direct["@id"]);
246
+
247
+ // Hot-swap to enable inspection (zero downtime)
248
+ await client.removeRouteById("https_server", routes.direct["@id"]);
249
+ await client.addRoute("https_server", routes.proxied, routes.proxied["@id"]);
250
+
251
+ // Hot-swap back to disable inspection
252
+ await client.removeRouteById("https_server", routes.proxied["@id"]);
253
+ await client.addRoute("https_server", routes.direct, routes.direct["@id"]);
254
+ ```
255
+
256
+ #### Load Balancing with MITMproxy
257
+
258
+ Route some traffic through MITMproxy while keeping the rest direct:
259
+
260
+ ```typescript
261
+ import { CaddyClient, buildLoadBalancerRoute } from "@viaalink/caddy-api-client/caddy";
262
+
263
+ const client = new CaddyClient();
264
+ const lbRoute = buildLoadBalancerRoute({
265
+ host: "api.localhost",
266
+ upstreams: [
267
+ "localhost:8082", // MITMproxy (captures traffic)
268
+ "localhost:3000", // Direct to backend
269
+ ],
270
+ policy: "round_robin",
271
+ });
272
+
273
+ await client.addRoute("https_server", lbRoute);
274
+ ```
275
+
276
+ #### Docker Compose Setup
277
+
278
+ ```yaml
279
+ services:
280
+ mitmproxy:
281
+ image: mitmproxy/mitmproxy:10.4.2
282
+ ports:
283
+ - "8082:8080" # Proxy port
284
+ - "8081:8081" # Web UI
285
+ command: >
286
+ mitmweb
287
+ --mode reverse:http://backend:3000
288
+ --web-host 0.0.0.0
289
+ --web-port 8081
290
+ --listen-host 0.0.0.0
291
+ --listen-port 8080
292
+ --no-web-open-browser
293
+ --set keep_host_header=true
294
+ restart: unless-stopped
295
+
296
+ backend:
297
+ image: your-backend-image
298
+ ports:
299
+ - "3000:3000"
300
+ ```
301
+
302
+ **Features:**
303
+
304
+ - ✅ Zero client/backend code changes
305
+ - ✅ Zero service restarts required
306
+ - ✅ Hot-swappable at runtime
307
+ - ✅ Complete request/response inspection
308
+ - ✅ Web UI for viewing captured traffic
309
+ - ✅ Production-safe (tested with concurrent requests)
310
+
311
+ **Troubleshooting:** See the [MITMproxy Troubleshooting Guide](https://github.com/viaalink/asd-caddy-api-client/blob/main/docs/mitmproxy-troubleshooting.md) for common issues and solutions.
312
+
313
+ ### Domain Management
314
+
315
+ ```typescript
316
+ import { addDomainWithAutoTls, deleteDomain } from "@viaalink/caddy-api-client/caddy";
317
+
318
+ // Add domain with automatic TLS (Let's Encrypt)
319
+ const domain = await addDomainWithAutoTls({
320
+ domain: "example.com",
321
+ target: "127.0.0.1",
322
+ targetPort: 3000,
323
+ enableHsts: true,
324
+ redirectMode: "permanent",
325
+ });
326
+
327
+ // Delete domain
328
+ await deleteDomain({ domain: "example.com" });
329
+ ```
330
+
331
+ ## API Reference
332
+
333
+ ### CaddyClient
334
+
335
+ ```typescript
336
+ class CaddyClient {
337
+ constructor(options?: CaddyClientOptions);
338
+
339
+ // Configuration
340
+ getConfig(): Promise<unknown>;
341
+ reload(): Promise<void>;
342
+ stop(): Promise<void>; // Gracefully stop Caddy server
343
+ adapt(config: string, adapter?: string): Promise<unknown>; // Convert Caddyfile to JSON
344
+
345
+ // Routes
346
+ getRoutes(server: string): Promise<CaddyRoute[]>;
347
+ addRoute(server: string, route: CaddyRoute): Promise<boolean>;
348
+ addRoutes(server: string, routes: CaddyRoute[]): Promise<{ added: number; skipped: number }>;
349
+ patchRoutes(server: string, routes: CaddyRoute[]): Promise<void>;
350
+ insertRoute(
351
+ server: string,
352
+ route: CaddyRoute,
353
+ position?: "beginning" | "end" | "after-health-checks"
354
+ ): Promise<void>;
355
+ replaceRouteById(server: string, id: string, newRoute: CaddyRoute): Promise<boolean>;
356
+ removeRouteById(server: string, id: string): Promise<boolean>;
357
+ removeRoutesByHost(hostname: string, server?: string): Promise<number>;
358
+
359
+ // Servers
360
+ getServers(): Promise<unknown>;
361
+ getServerConfig(server: string): Promise<Record<string, unknown>>;
362
+ patchServer(serverConfig: Record<string, unknown>): Promise<void>;
363
+
364
+ // Upstreams (reverse proxy status)
365
+ getUpstreams(): Promise<UpstreamStatus[]>; // Get health/status of upstream servers
366
+
367
+ // Version
368
+ getVersion(): Promise<unknown>;
369
+ }
370
+ ```
371
+
372
+ ### Route Builders
373
+
374
+ ```typescript
375
+ // Service routes (host + path based)
376
+ buildServiceRoutes(options: ServiceRouteOptions): CaddyRoute[];
377
+
378
+ // Individual route types
379
+ buildHealthCheckRoute(options: HealthCheckRouteOptions): CaddyRoute;
380
+ buildHostRoute(options: HostRouteOptions): CaddyRoute;
381
+ buildPathRoute(options: PathRouteOptions): CaddyRoute;
382
+ buildLoadBalancerRoute(options: LoadBalancerRouteOptions): CaddyRoute;
383
+
384
+ // New handler routes (v0.3.0)
385
+ buildFileServerRoute(options: FileServerRouteOptions): CaddyRoute;
386
+ buildTemplatesRoute(options: TemplatesRouteOptions): CaddyRoute;
387
+ buildErrorRoute(options: ErrorRouteOptions): CaddyRoute;
388
+
389
+ // MITMproxy integration
390
+ buildMitmproxyRoute(options: MitmproxyRouteOptions): CaddyRoute;
391
+ buildMitmproxyRoutePair(options: MitmproxyRoutePairOptions): { direct: CaddyRoute; proxied: CaddyRoute };
392
+
393
+ // Handlers
394
+ buildReverseProxyHandler(dial: DialAddress): CaddyRouteHandler;
395
+ buildSecurityHeadersHandler(headers: SecurityHeaders): CaddyRouteHandler;
396
+ buildBasicAuthHandler(auth: BasicAuthOptions): CaddyRouteHandler;
397
+ buildRewriteHandler(prefix: string): CaddyRouteHandler;
398
+ buildCompressionHandler(options?: CompressionOptions): CaddyRouteHandler;
399
+ buildIngressTagHeadersHandler(tag: string): CaddyRouteHandler;
400
+ buildIframeHeadersHandler(allowedOrigin?: string): CaddyRouteHandler;
401
+
402
+ // New handlers (v0.3.0)
403
+ buildRequestBodyHandler(options: RequestBodyHandlerOptions): CaddyRouteHandler;
404
+ buildVarsHandler(options: VarsHandlerOptions): CaddyRouteHandler;
405
+ buildMapHandler(options: MapHandlerOptions): CaddyRouteHandler;
406
+ buildTracingHandler(options?: TracingHandlerOptions): CaddyRouteHandler;
407
+ ```
408
+
409
+ ### MITMweb Functions
410
+
411
+ ```typescript
412
+ // Installation & status
413
+ isMitmproxyInstalled(): Promise<boolean>;
414
+ getMitmproxyVersion(): Promise<string | null>;
415
+ autoInstallMitmproxy(): Promise<boolean>;
416
+
417
+ // Process management
418
+ startMitmweb(options?: MitmwebOptions): Promise<{ pid, webUrl, proxyUrl, pidFile }>;
419
+ stopMitmweb(workingDir?: string): Promise<void>;
420
+ getMitmwebStatus(workingDir?: string): MitmwebStatus;
421
+ ```
422
+
423
+ ### Domain Management
424
+
425
+ ```typescript
426
+ addDomainWithAutoTls(options: AddDomainWithAutoTlsOptions): Promise<DomainConfig>;
427
+ addDomainWithTls(options: AddDomainWithTlsOptions): Promise<DomainConfig>;
428
+ updateDomain(options: UpdateDomainOptions): Promise<DomainConfig>;
429
+ deleteDomain(options: DeleteDomainOptions): Promise<void>;
430
+ getDomainConfig(domain: Domain, adminUrl?: string): Promise<DomainConfig | null>;
431
+ ```
432
+
433
+ ### Advanced Schemas
434
+
435
+ Zod-validated schemas for advanced Caddy configurations:
436
+
437
+ ```typescript
438
+ import {
439
+ // Duration (Go format)
440
+ CaddyDurationSchema, // "10s", "1m30s", or nanoseconds
441
+
442
+ // Health checks
443
+ ActiveHealthChecksSchema, // uri, interval, timeout, expect_status, expect_body
444
+ PassiveHealthChecksSchema, // fail_duration, max_fails, unhealthy_status
445
+ HealthChecksSchema, // Combined active + passive
446
+
447
+ // Load balancing
448
+ LoadBalancingSchema, // selection_policy, retries, try_duration
449
+ UpstreamSchema, // dial, max_requests
450
+
451
+ // Route matching
452
+ ExtendedRouteMatcherSchema, // client_ip, remote_ip, path_regexp, expression, not
453
+
454
+ // Handler
455
+ ReverseProxyHandlerSchema, // Full reverse proxy with health checks + load balancing
456
+ } from "@viaalink/caddy-api-client";
457
+ ```
458
+
459
+ ### Handler Types (v0.3.0)
460
+
461
+ Full TypeScript support for all 20 Caddy HTTP handlers with Zod validation:
462
+
463
+ ```typescript
464
+ import {
465
+ // File serving
466
+ FileServerHandlerSchema, // Static files with browse, precompressed
467
+ TemplatesHandlerSchema, // Server-side template rendering
468
+
469
+ // Request manipulation
470
+ RewriteHandlerSchema, // URI rewriting
471
+ RequestBodyHandlerSchema, // Body size limits
472
+ VarsHandlerSchema, // Set request variables
473
+ MapHandlerSchema, // Variable mapping
474
+
475
+ // Response handling
476
+ StaticResponseHandlerSchema, // Return static content
477
+ HeadersHandlerSchema, // Modify headers
478
+ EncodeHandlerSchema, // Compression (gzip, zstd, br)
479
+ ErrorHandlerSchema, // Trigger error handling
480
+
481
+ // Proxy & routing
482
+ ReverseProxyHandlerSchema, // Proxy to upstreams
483
+ SubrouteHandlerSchema, // Nested routes
484
+ InvokeHandlerSchema, // Call named routes
485
+
486
+ // Interception
487
+ InterceptHandlerSchema, // Response interception
488
+ CopyResponseHandlerSchema, // Copy subrequest response
489
+ CopyResponseHeadersHandlerSchema, // Copy headers
490
+
491
+ // Utilities
492
+ AuthenticationHandlerSchema, // HTTP basic auth
493
+ PushHandlerSchema, // HTTP/2 server push
494
+ TracingHandlerSchema, // Distributed tracing
495
+ LogAppendHandlerSchema, // Custom log fields
496
+ } from "@viaalink/caddy-api-client";
497
+ ```
498
+
499
+ **Route builders for common patterns:**
500
+
501
+ ```typescript
502
+ import {
503
+ buildFileServerRoute, // Serve static files
504
+ buildTemplatesRoute, // Template processing
505
+ buildErrorRoute, // Error responses
506
+ buildRequestBodyHandler, // Body limits
507
+ buildVarsHandler, // Set variables
508
+ buildMapHandler, // Variable mapping
509
+ buildTracingHandler, // Tracing spans
510
+ } from "@viaalink/caddy-api-client/caddy";
511
+
512
+ // Example: Serve static files with browsing
513
+ const fileRoute = buildFileServerRoute({
514
+ path: "/static/*",
515
+ root: "/var/www/static",
516
+ browse: true,
517
+ hidePatterns: [".git", ".env"],
518
+ precompressed: true,
519
+ });
520
+
521
+ // Example: Template rendering
522
+ const templateRoute = buildTemplatesRoute({
523
+ path: "/*.html",
524
+ fileRoot: "/var/www/templates",
525
+ mimeTypes: ["text/html"],
526
+ });
527
+
528
+ // Example: Variable mapping for routing
529
+ const mapHandler = buildMapHandler({
530
+ source: "{http.request.uri.path}",
531
+ destinations: ["{backend}"],
532
+ mappings: [
533
+ { input: "/api/*", outputs: ["api-server"] },
534
+ { input: "/admin/*", outputs: ["admin-server"] },
535
+ ],
536
+ defaults: ["default-server"],
537
+ });
538
+ ```
539
+
540
+ ### Extended Caddy Types
541
+
542
+ For advanced configurations beyond our Zod-validated builders, we re-export comprehensive type definitions from [caddy-json-types](https://github.com/CafuChino/caddy-json-types):
543
+
544
+ ```typescript
545
+ import type {
546
+ IConfig,
547
+ IModulesCaddyhttpRoute,
548
+ IModulesCaddyhttpReverseproxyHandler,
549
+ IModulesCaddytlsConnectionPolicy,
550
+ } from "@viaalink/caddy-api-client/caddy-types";
551
+ ```
552
+
553
+ **Includes 591 types covering:**
554
+
555
+ - Full Caddy JSON configuration structure
556
+ - 50+ DNS providers for ACME challenges
557
+ - Layer 4 (TCP/UDP) proxy configuration
558
+ - PKI/CA management types
559
+ - Storage backends (Redis, S3, DynamoDB, etc.)
560
+ - All HTTP handlers, matchers, and encoders
561
+
562
+ ## Error Handling
563
+
564
+ The library provides custom error classes:
565
+
566
+ ```typescript
567
+ import {
568
+ CaddyApiError,
569
+ ValidationError,
570
+ NetworkError,
571
+ TimeoutError,
572
+ DomainNotFoundError,
573
+ MitmproxyNotInstalledError,
574
+ } from "@viaalink/caddy-api-client";
575
+
576
+ try {
577
+ await client.addRoute("https_server", route);
578
+ } catch (error) {
579
+ if (error instanceof ValidationError) {
580
+ console.error("Invalid route configuration:", error.errors);
581
+ } else if (error instanceof CaddyApiError) {
582
+ console.error(`Caddy API error (${error.statusCode}):`, error.responseBody);
583
+ } else if (error instanceof NetworkError) {
584
+ console.error("Network error:", error.cause);
585
+ } else if (error instanceof TimeoutError) {
586
+ console.error(`Request timed out after ${error.timeoutMs}ms`);
587
+ }
588
+ }
589
+ ```
590
+
591
+ ## Examples
592
+
593
+ ### Tested Examples (Always Current)
594
+
595
+ Our **integration tests** serve as comprehensive, tested examples that are verified in CI:
596
+
597
+ - **[caddy-mitmproxy-flow.integration.test.ts](./src/__tests__/integration/caddy-mitmproxy-flow.integration.test.ts)** - Complete MITMproxy integration patterns
598
+ - **[asd-scenarios.integration.test.ts](./src/__tests__/integration/asd-scenarios.integration.test.ts)** - Production routing scenarios (load balancing, multi-host, path-based)
599
+ - **[critical-modules.integration.test.ts](./src/__tests__/integration/critical-modules.integration.test.ts)** - All route builders, domain management, TLS
600
+
601
+ **Run examples locally:**
602
+
603
+ ```bash
604
+ # Start services
605
+ docker compose -f docker-compose.test.yml up -d
606
+
607
+ # Run all integration tests (86+ examples)
608
+ INTEGRATION_TEST=true bun test src/__tests__/integration/
609
+
610
+ # Run specific example file
611
+ INTEGRATION_TEST=true bun test src/__tests__/integration/caddy-mitmproxy-flow.integration.test.ts
612
+ ```
613
+
614
+ ### Standalone Examples
615
+
616
+ See the [`examples/`](./examples/) directory for standalone examples (require published package):
617
+
618
+ - [`basic-usage.ts`](./examples/basic-usage.ts) - Basic route management
619
+ - [`load-balancer.ts`](./examples/load-balancer.ts) - Load balancing with health checks
620
+ - [`mitmproxy-integration.ts`](./examples/mitmproxy-integration.ts) - Traffic inspection with MITMproxy
621
+
622
+ ## API Documentation
623
+
624
+ 📚 **[View Full API Documentation](https://viaalink.github.io/asd-caddy-api-client/)** ← Auto-generated from source code
625
+
626
+ Full API documentation is generated using TypeDoc and hosted on GitHub Pages. It includes detailed information for all exported functions, classes, and types with examples.
627
+
628
+ **Generate locally:**
629
+
630
+ ```bash
631
+ bun run docs:build # Generate docs
632
+ bun run docs:serve # Generate and open in browser
633
+ ```
634
+
635
+ ## Development
636
+
637
+ ```bash
638
+ # Install dependencies
639
+ bun install
640
+
641
+ # Build
642
+ bun run build
643
+
644
+ # Test
645
+ bun run test
646
+
647
+ # Type check
648
+ bun run typecheck
649
+
650
+ # Lint
651
+ bun run lint
652
+
653
+ # Format
654
+ bun run format
655
+ ```
656
+
657
+ ## Contributing
658
+
659
+ Contributions are welcome! Please [open an issue](https://github.com/viaalink/asd-caddy-api-client/issues) or submit a pull request if you have any improvements or fixes.
660
+
661
+ 1. Fork the repository
662
+ 2. Create a new branch (`git checkout -b my-feature-branch`)
663
+ 3. Make your changes
664
+ 4. Commit your changes (`git commit -am 'Add new feature'`)
665
+ 5. Push to the branch (`git push origin my-feature-branch`)
666
+ 6. Create a new Pull Request
667
+
668
+ ## License
669
+
670
+ This project is licensed under the MIT License. See the [LICENSE](LICENSE) file for details.
671
+
672
+ ## Acknowledgements
673
+
674
+ This project is not affiliated with or endorsed by the Caddy project. It is an independent project created to improve the developer experience when working with Caddy JSON configurations in TypeScript.
675
+
676
+ For more information on Caddy and its configuration options, please visit the [official Caddy documentation](https://caddyserver.com/docs/).