@techspokes/typescript-wsdl-client 0.7.15 → 0.8.14
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/README.md +1504 -263
- package/dist/cli.js +423 -270
- package/dist/{emit/clientEmitter.d.ts → client/generateClient.d.ts} +2 -2
- package/dist/client/generateClient.d.ts.map +1 -0
- package/dist/{emit/clientEmitter.js → client/generateClient.js} +5 -5
- package/dist/{emit/typesEmitter.d.ts → client/generateTypes.d.ts} +4 -4
- package/dist/client/generateTypes.d.ts.map +1 -0
- package/dist/{emit/typesEmitter.js → client/generateTypes.js} +6 -6
- package/dist/{emit/utilsEmitter.d.ts → client/generateUtils.d.ts} +4 -4
- package/dist/client/generateUtils.d.ts.map +1 -0
- package/dist/{emit/utilsEmitter.js → client/generateUtils.js} +7 -7
- package/dist/{emit/catalogEmitter.d.ts → compiler/generateCatalog.d.ts} +4 -4
- package/dist/compiler/generateCatalog.d.ts.map +1 -0
- package/dist/{emit/catalogEmitter.js → compiler/generateCatalog.js} +5 -5
- package/dist/compiler/schemaCompiler.d.ts +1 -1
- package/dist/compiler/schemaCompiler.js +1 -1
- package/dist/config.d.ts +13 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +17 -0
- package/dist/gateway/generateGateway.d.ts +73 -0
- package/dist/gateway/generateGateway.d.ts.map +1 -0
- package/dist/gateway/generateGateway.js +135 -0
- package/dist/gateway/generators.d.ts +90 -0
- package/dist/gateway/generators.d.ts.map +1 -0
- package/dist/gateway/generators.js +270 -0
- package/dist/gateway/helpers.d.ts +115 -0
- package/dist/gateway/helpers.d.ts.map +1 -0
- package/dist/gateway/helpers.js +224 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +18 -18
- package/dist/loader/wsdlLoader.d.ts.map +1 -1
- package/dist/loader/wsdlLoader.js +1 -3
- package/dist/openapi/generateOpenAPI.d.ts +25 -1
- package/dist/openapi/generateOpenAPI.d.ts.map +1 -1
- package/dist/openapi/generateOpenAPI.js +28 -27
- package/dist/openapi/{buildPaths.d.ts → generatePaths.d.ts} +6 -6
- package/dist/openapi/generatePaths.d.ts.map +1 -0
- package/dist/openapi/{buildPaths.js → generatePaths.js} +1 -1
- package/dist/openapi/{buildSchemas.d.ts → generateSchemas.d.ts} +10 -10
- package/dist/openapi/generateSchemas.d.ts.map +1 -0
- package/dist/openapi/{buildSchemas.js → generateSchemas.js} +5 -5
- package/dist/openapi/security.d.ts.map +1 -1
- package/dist/openapi/security.js +2 -1
- package/dist/pipeline.d.ts +21 -7
- package/dist/pipeline.d.ts.map +1 -1
- package/dist/pipeline.js +66 -32
- package/dist/util/builder.d.ts +25 -0
- package/dist/util/builder.d.ts.map +1 -0
- package/dist/util/builder.js +52 -0
- package/dist/util/cli.d.ts +106 -0
- package/dist/util/cli.d.ts.map +1 -0
- package/dist/util/cli.js +164 -0
- package/package.json +11 -8
- package/dist/emit/catalogEmitter.d.ts.map +0 -1
- package/dist/emit/clientEmitter.d.ts.map +0 -1
- package/dist/emit/typesEmitter.d.ts.map +0 -1
- package/dist/emit/utilsEmitter.d.ts.map +0 -1
- package/dist/openapi/buildPaths.d.ts.map +0 -1
- package/dist/openapi/buildSchemas.d.ts.map +0 -1
package/README.md
CHANGED
|
@@ -9,354 +9,1595 @@
|
|
|
9
9
|
[](https://github.com/techspokes)
|
|
10
10
|
[](https://github.com/sponsors/TechSpokes)
|
|
11
11
|
|
|
12
|
-
> **Mission**:
|
|
12
|
+
> **Mission**: Transform complex WSDL/XSD definitions into ergonomic, type-safe TypeScript SOAP clients with optional OpenAPI 3.1 specs and Fastify REST gateway scaffolding — enabling confident integration with legacy enterprise services.
|
|
13
13
|
|
|
14
14
|
---
|
|
15
|
+
|
|
16
|
+
## Table of Contents
|
|
17
|
+
|
|
18
|
+
- [1. Why This Project](#1-why-this-project-what-sets-it-apart)
|
|
19
|
+
- [2. Installation](#2-installation)
|
|
20
|
+
- [3. Quick Start](#3-quick-start)
|
|
21
|
+
- [4. Commands Overview](#4-commands-overview)
|
|
22
|
+
- [5. Command: `compile`](#5-command-compile)
|
|
23
|
+
- [6. Command: `client`](#6-command-client)
|
|
24
|
+
- [7. Command: `openapi`](#7-command-openapi)
|
|
25
|
+
- [8. Command: `gateway`](#8-command-gateway)
|
|
26
|
+
- [9. Command: `pipeline`](#9-command-pipeline)
|
|
27
|
+
- [10. Working With Generated Clients](#10-working-with-generated-clients)
|
|
28
|
+
- [11. OpenAPI Configuration](#11-openapi-configuration)
|
|
29
|
+
- [12. Programmatic API](#12-programmatic-api)
|
|
30
|
+
- [13. Advanced Topics](#13-advanced-topics)
|
|
31
|
+
- [14. Troubleshooting](#14-troubleshooting)
|
|
32
|
+
- [15. Contributing](#15-contributing)
|
|
33
|
+
- [16. License](#16-license)
|
|
34
|
+
- [17. Sponsors](#17-sponsors)
|
|
35
|
+
|
|
36
|
+
---
|
|
37
|
+
|
|
15
38
|
## 1. Why This Project (What Sets It Apart)
|
|
16
|
-
Most generators stop at loosely typed stubs or leak XML complexity into your application layer. This tool focuses on **correct flattening and determinism**:
|
|
17
|
-
|
|
18
|
-
| Core Differentiator | What You Get |
|
|
19
|
-
|----------------------------------|------------------------------------------------------------------------------------------------------|
|
|
20
|
-
| Attribute + Element Flattening | Attributes and child elements appear as peer properties (no nested wrapper noise). |
|
|
21
|
-
| `$value` Text Content Convention | Simple text & mixed content always represented as a `$value` property (collision-safe & documented). |
|
|
22
|
-
| Inheritance Resolution | `complexContent` and `simpleContent` extensions are merged or extended consistently. |
|
|
23
|
-
| Choice Strategy | Predictable `all-optional` modeling today (future advanced discriminators planned). |
|
|
24
|
-
| WS‑Policy Security Hints | Inline scan of policies surfaces required auth hints (e.g. `usernameToken`, `https`). |
|
|
25
|
-
| Deterministic Output | Sorted declarations and stable alias resolution for diff‑friendly regeneration. |
|
|
26
|
-
| Primitive Mapping Controls | Explicit flags for long / big integer / decimal / temporal families (string‑first safety). |
|
|
27
|
-
| Catalog Introspection | One JSON artifact (`catalog.json`) to drive further tooling (including OpenAPI). |
|
|
28
|
-
| OpenAPI 3.1 Bridge | Mirrors the exact TypeScript model — no divergence between runtime and spec. |
|
|
29
|
-
| Multi‑format Output | `--format json\|yaml\|both` with always‑on validation (unless disabled). |
|
|
30
|
-
| One‑Shot Pipeline | Single pass (parse → TS → OpenAPI) for CI & automation. |
|
|
31
39
|
|
|
32
|
-
|
|
40
|
+
Most WSDL generators produce loosely typed stubs or expose raw XML complexity to your application layer. This tool delivers **correct flattening, determinism, and multiple integration paths**:
|
|
33
41
|
|
|
42
|
+
| Core Differentiator | What You Get |
|
|
43
|
+
|--------------------------------------|------------------------------------------------------------------------------------------------------|
|
|
44
|
+
| **Attribute + Element Flattening** | Attributes and child elements appear as peer properties (no nested wrapper noise). |
|
|
45
|
+
| **`$value` Text Content Convention** | Simple text & mixed content always represented as a `$value` property (collision-safe & documented). |
|
|
46
|
+
| **Inheritance Resolution** | `complexContent` and `simpleContent` extensions are merged or extended consistently. |
|
|
47
|
+
| **Choice Strategy** | Predictable `all-optional` modeling today (future advanced discriminators planned). |
|
|
48
|
+
| **WS-Policy Security Hints** | Inline scan of policies surfaces required auth hints (e.g. `usernameToken`, `https`). |
|
|
49
|
+
| **Deterministic Output** | Sorted declarations and stable alias resolution for diff-friendly regeneration. |
|
|
50
|
+
| **Primitive Mapping Controls** | Explicit flags for long / big integer / decimal / temporal families (string-first safety). |
|
|
51
|
+
| **Catalog Introspection** | One JSON artifact (`catalog.json`) to drive further tooling (including OpenAPI & gateway). |
|
|
52
|
+
| **OpenAPI 3.1 Bridge** | Mirrors the exact TypeScript model with no divergence between runtime and spec. |
|
|
53
|
+
| **Standard Response Envelope** | Always-on, debuggable envelope structure (status, message, data, error) for REST gateways. |
|
|
54
|
+
| **Fastify Gateway Scaffolding** | Route and schema generation with JSON Schema validation (handler implementation in progress). |
|
|
55
|
+
| **Multi-format Output** | `--openapi-format json\|yaml\|both` with always-on validation (unless disabled). |
|
|
56
|
+
| **One-Shot Pipeline** | Single pass (parse to TS to OpenAPI to Gateway) for CI & automation. |
|
|
57
|
+
|
|
58
|
+
**Vendor**: [TechSpokes](https://www.techspokes.com) · **Maintainer**: Serge Liatko ([@sergeliatko](https://github.com/sergeliatko))
|
|
34
59
|
|
|
35
60
|
---
|
|
61
|
+
|
|
36
62
|
## 2. Installation
|
|
63
|
+
|
|
37
64
|
```bash
|
|
38
|
-
npm
|
|
39
|
-
npm
|
|
65
|
+
npm install --save-dev @techspokes/typescript-wsdl-client
|
|
66
|
+
npm install soap # Runtime dependency for SOAP calls
|
|
40
67
|
```
|
|
41
68
|
|
|
69
|
+
**Requirements**:
|
|
70
|
+
- Node.js 20.0.0 or later
|
|
71
|
+
- `soap` package (runtime dependency for generated clients)
|
|
72
|
+
|
|
42
73
|
---
|
|
43
|
-
|
|
44
|
-
|
|
74
|
+
|
|
75
|
+
## 3. Quick Start
|
|
76
|
+
|
|
77
|
+
### Generate TypeScript SOAP Client
|
|
78
|
+
|
|
79
|
+
```bash
|
|
80
|
+
npx wsdl-tsc client --wsdl-source ./wsdl/Weather.wsdl --client-dir ./src/services/weather
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
**Try with included example:**
|
|
84
|
+
|
|
85
|
+
```bash
|
|
86
|
+
npx wsdl-tsc client --wsdl-source examples/minimal/weather.wsdl --client-dir ./tmp/weather
|
|
45
87
|
```
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
88
|
+
|
|
89
|
+
### Generate Everything (Pipeline)
|
|
90
|
+
|
|
91
|
+
```bash
|
|
92
|
+
npx wsdl-tsc pipeline \
|
|
93
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
94
|
+
--client-dir ./tmp/client \
|
|
95
|
+
--openapi-file ./tmp/openapi.json \
|
|
96
|
+
--gateway-dir ./tmp/gateway \
|
|
97
|
+
--gateway-service-name weather \
|
|
98
|
+
--gateway-version-prefix v1
|
|
55
99
|
```
|
|
56
|
-
|
|
100
|
+
|
|
101
|
+
**Output**: Generates client files in `tmp/client/`, OpenAPI spec at `tmp/openapi.json`, gateway code in `tmp/gateway/`, and catalog at `tmp/client/catalog.json`.
|
|
57
102
|
|
|
58
103
|
---
|
|
59
|
-
## 4. Primary Usage: Generate a TypeScript SOAP Client
|
|
60
|
-
The **SOAP client generation** is the core of this project and the most common use case.
|
|
61
104
|
|
|
62
|
-
|
|
105
|
+
## 4. Commands Overview
|
|
106
|
+
|
|
107
|
+
The tool provides **five commands** for different integration scenarios:
|
|
108
|
+
|
|
109
|
+
| Command | Purpose | Typical Use Case |
|
|
110
|
+
|--------------|----------------------------------------------------------------|-----------------------------------------------------|
|
|
111
|
+
| `compile` | Parse WSDL and emit `catalog.json` only | Debugging, inspection, or multi-stage builds |
|
|
112
|
+
| `client` | Generate TypeScript SOAP client from WSDL or catalog | Standard SOAP integration (most common) |
|
|
113
|
+
| `openapi` | Generate OpenAPI 3.1 spec from WSDL or catalog | Documentation, REST proxies, API gateways |
|
|
114
|
+
| `gateway` | Generate Fastify gateway scaffolding from OpenAPI spec | REST gateway foundation (handler stubs) |
|
|
115
|
+
| `pipeline` | Run full pipeline: client + OpenAPI + gateway in one pass | CI/CD automation, complete stack generation |
|
|
116
|
+
|
|
117
|
+
---
|
|
118
|
+
|
|
119
|
+
## 5. Command: `compile`
|
|
120
|
+
|
|
121
|
+
**Purpose**: Parse WSDL and generate only the intermediate `catalog.json` representation without TypeScript client code.
|
|
122
|
+
|
|
123
|
+
**When to use**:
|
|
124
|
+
- Multi-stage builds where you want to cache the parsed WSDL
|
|
125
|
+
- Debugging or inspecting the compiled schema structure
|
|
126
|
+
- Sharing a compiled catalog across multiple generation targets
|
|
127
|
+
|
|
128
|
+
### Usage
|
|
129
|
+
|
|
63
130
|
```bash
|
|
64
|
-
npx wsdl-tsc --wsdl
|
|
131
|
+
npx wsdl-tsc compile --wsdl-source <file|url> --catalog-file <path> [options]
|
|
65
132
|
```
|
|
66
133
|
|
|
67
|
-
|
|
134
|
+
### Required Flags
|
|
135
|
+
|
|
136
|
+
| Flag | Description |
|
|
137
|
+
|---------------------|------------------------------------------|
|
|
138
|
+
| `--wsdl-source` | Path or URL to the WSDL file |
|
|
139
|
+
| `--catalog-file` | Output path for `catalog.json` |
|
|
140
|
+
|
|
141
|
+
### Optional Flags
|
|
142
|
+
|
|
143
|
+
| Flag | Default | Description |
|
|
144
|
+
|------------------------------------|----------------|--------------------------------------------------------------|
|
|
145
|
+
| `--import-extensions` | `js` | Import specifier style: `js`, `ts`, or `bare` |
|
|
146
|
+
| `--client-attributes-key` | `$attributes` | Attribute bag key for runtime mapper |
|
|
147
|
+
| `--client-class-name` | (derived) | Override generated client class name |
|
|
148
|
+
| `--client-int64-as` | `string` | Map 64-bit integers: `string`, `number`, or `bigint` |
|
|
149
|
+
| `--client-bigint-as` | `string` | Map arbitrary-size integers: `string` or `number` |
|
|
150
|
+
| `--client-decimal-as` | `string` | Map `xs:decimal`: `string` or `number` |
|
|
151
|
+
| `--client-date-as` | `string` | Map date/time types: `string` or `Date` |
|
|
152
|
+
| `--client-choice-mode` | `all-optional` | Choice element strategy: `all-optional` or `union` |
|
|
153
|
+
| `--client-fail-on-unresolved` | `false` | Fail build on unresolved type references |
|
|
154
|
+
| `--client-nillable-as-optional` | `false` | Treat nillable elements as optional properties |
|
|
155
|
+
|
|
156
|
+
### Examples
|
|
157
|
+
|
|
158
|
+
#### Basic Compilation
|
|
159
|
+
|
|
68
160
|
```bash
|
|
69
|
-
npx wsdl-tsc
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
| `utils.ts` | Metadata (attribute vs element, occurrence, nillable). |
|
|
83
|
-
| `catalog.json` | (If `--catalog`) compiled representation for debugging / OpenAPI reuse. |
|
|
84
|
-
|
|
85
|
-
### 4.3 Key Modeling Rules Recap
|
|
86
|
-
- **Attributes & elements** → peer properties.
|
|
87
|
-
- **Text content** → `$value`.
|
|
88
|
-
- **Required attributes**: `use!=optional`; elements `min>=1`.
|
|
89
|
-
- **Multiplicity**: `max>1` or `unbounded` → arrays.
|
|
90
|
-
- **Nillable**: `nillable="true"` preserved (optionally modelled optional with `--nillable-as-optional`).
|
|
91
|
-
- **Inheritance**: extensions merged or emitted as extends; simpleContent base collapsed logically.
|
|
92
|
-
|
|
93
|
-
### 4.4 CLI Flags (SOAP Client)
|
|
94
|
-
| Flag | Default | Description |
|
|
95
|
-
|--------------------------|----------------|---------------------------------------------------|
|
|
96
|
-
| `--wsdl` | (required) | Local path or URL to WSDL. |
|
|
97
|
-
| `--out` | (required) | Output directory. |
|
|
98
|
-
| `--imports` | `js` | Intra‑generated import style: `js`, `ts`, `bare`. |
|
|
99
|
-
| `--catalog` | `false` | Emit `catalog.json`. |
|
|
100
|
-
| `--client-name` | derived | Override exported class name. |
|
|
101
|
-
| `--attributes-key` | `$attributes` | Attribute bag key. |
|
|
102
|
-
| `--choice` | `all-optional` | Current choice strategy. |
|
|
103
|
-
| `--nillable-as-optional` | `false` | Treat nillable elements as optional props. |
|
|
104
|
-
| `--fail-on-unresolved` | `true` | Fail build on unresolved references. |
|
|
105
|
-
| `--int64-as` | `string` | Map 64‑bit integer types. |
|
|
106
|
-
| `--bigint-as` | `string` | Map arbitrary-size integer family. |
|
|
107
|
-
| `--decimal-as` | `string` | Map `xs:decimal`. |
|
|
108
|
-
| `--date-as` | `string` | Map date/time/duration primitives. |
|
|
109
|
-
|
|
110
|
-
### 4.5 Example With Safer Numeric Decisions
|
|
111
|
-
```bash
|
|
112
|
-
npx wsdl-tsc \
|
|
113
|
-
--wsdl https://example.com/Hotel.wsdl \
|
|
114
|
-
--out ./src/integrations/soap/hotel \
|
|
115
|
-
--int64-as number \
|
|
116
|
-
--decimal-as string \
|
|
117
|
-
--date-as string \
|
|
118
|
-
--catalog
|
|
119
|
-
```
|
|
120
|
-
|
|
121
|
-
### 4.6 Programmatic Generation (TypeScript Only)
|
|
122
|
-
```ts
|
|
123
|
-
import { compileWsdlToProject } from "@techspokes/typescript-wsdl-client";
|
|
124
|
-
await compileWsdlToProject({
|
|
125
|
-
wsdl: "./wsdl/Hotel.wsdl",
|
|
126
|
-
outDir: "./src/integrations/soap/hotel"
|
|
127
|
-
});
|
|
161
|
+
npx wsdl-tsc compile \
|
|
162
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
163
|
+
--catalog-file tmp/catalog.json
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
#### With Custom Output Path
|
|
167
|
+
|
|
168
|
+
```bash
|
|
169
|
+
npx wsdl-tsc compile \
|
|
170
|
+
--wsdl-source https://example.com/Hotel.wsdl \
|
|
171
|
+
--catalog-file ./build/hotel-catalog.json \
|
|
172
|
+
--client-int64-as number \
|
|
173
|
+
--client-decimal-as string
|
|
128
174
|
```
|
|
129
175
|
|
|
176
|
+
#### For Debugging
|
|
177
|
+
|
|
178
|
+
```bash
|
|
179
|
+
# Compile to inspect types and operations
|
|
180
|
+
npx wsdl-tsc compile \
|
|
181
|
+
--wsdl-source ./wsdl/ComplexService.wsdl \
|
|
182
|
+
--catalog-file ./debug/catalog.json \
|
|
183
|
+
--client-fail-on-unresolved false
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
### Output
|
|
187
|
+
|
|
188
|
+
- `catalog.json` - Compiled schema representation including types, operations, and metadata
|
|
189
|
+
|
|
190
|
+
### Catalog Structure
|
|
191
|
+
|
|
192
|
+
The catalog.json file contains the compiled WSDL representation:
|
|
193
|
+
|
|
194
|
+
```json
|
|
195
|
+
{
|
|
196
|
+
"wsdlUri": "path/to/service.wsdl",
|
|
197
|
+
"targetNamespace": "http://example.com/service",
|
|
198
|
+
"serviceName": "WeatherService",
|
|
199
|
+
"types": [
|
|
200
|
+
{
|
|
201
|
+
"name": "GetWeatherRequest",
|
|
202
|
+
"properties": []
|
|
203
|
+
}
|
|
204
|
+
],
|
|
205
|
+
"operations": [
|
|
206
|
+
{
|
|
207
|
+
"name": "GetWeather",
|
|
208
|
+
"input": "GetWeatherRequest",
|
|
209
|
+
"output": "GetWeatherResponse"
|
|
210
|
+
}
|
|
211
|
+
],
|
|
212
|
+
"options": {
|
|
213
|
+
"imports": "js",
|
|
214
|
+
"catalog": true
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
```
|
|
218
|
+
|
|
219
|
+
**Key sections**:
|
|
220
|
+
- `types` - All compiled type definitions with properties and inheritance
|
|
221
|
+
- `operations` - SOAP operations with input/output type references
|
|
222
|
+
- `options` - Compiler options used during generation
|
|
223
|
+
|
|
224
|
+
This catalog can be reused with the `client` and `openapi` commands via `--catalog-file`.
|
|
225
|
+
|
|
226
|
+
### Catalog File Organization
|
|
227
|
+
|
|
228
|
+
**Default behavior**: Catalog files are **co-located** with their primary output files for better organization and discoverability.
|
|
229
|
+
|
|
230
|
+
**Catalog Location by Command**:
|
|
231
|
+
- `compile`: Always requires explicit `--catalog-file` (no default)
|
|
232
|
+
- `client`: Defaults to `{client-dir}/catalog.json`
|
|
233
|
+
- `openapi`: Defaults to `{openapi-file-dir}/catalog.json`
|
|
234
|
+
- `pipeline`: Intelligent cascade - first available: `{client-dir}` > `{openapi-dir}` > `{gateway-dir}` > `tmp/`
|
|
235
|
+
|
|
236
|
+
**Common patterns**:
|
|
237
|
+
|
|
238
|
+
1. **Co-located with client** (recommended for most projects):
|
|
239
|
+
```bash
|
|
240
|
+
npx wsdl-tsc client --wsdl-source service.wsdl --client-dir src/services/weather
|
|
241
|
+
```
|
|
242
|
+
|
|
243
|
+
Creates `src/services/weather/catalog.json` automatically.
|
|
244
|
+
|
|
245
|
+
Result:
|
|
246
|
+
```
|
|
247
|
+
src/services/weather/
|
|
248
|
+
├── client.ts
|
|
249
|
+
├── types.ts
|
|
250
|
+
├── utils.ts
|
|
251
|
+
└── catalog.json
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
2. **Pipeline with multiple outputs** (catalog in client directory):
|
|
255
|
+
```bash
|
|
256
|
+
npx wsdl-tsc pipeline --wsdl-source service.wsdl --client-dir src/client --openapi-file docs/api.json
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
Creates `src/client/catalog.json` (co-located with client).
|
|
260
|
+
|
|
261
|
+
3. **Shared catalog for multiple commands** (custom location):
|
|
262
|
+
```bash
|
|
263
|
+
npx wsdl-tsc compile --wsdl-source service.wsdl --catalog-file build/shared-catalog.json
|
|
264
|
+
npx wsdl-tsc client --catalog-file build/shared-catalog.json --client-dir src/client
|
|
265
|
+
npx wsdl-tsc openapi --catalog-file build/shared-catalog.json --openapi-file docs/api.json
|
|
266
|
+
```
|
|
267
|
+
|
|
130
268
|
---
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
###
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
| `--out` | Base path or explicit file (extension optional). |
|
|
148
|
-
|
|
149
|
-
### 5.2 Core Schema Parity
|
|
150
|
-
The OpenAPI schemas reproduce the **exact** flattening & naming used in `types.ts` — crucial for avoiding drift between SOAP and REST surfaces.
|
|
151
|
-
|
|
152
|
-
### 5.3 Additional Flags (Selected)
|
|
153
|
-
| Flag | Description |
|
|
154
|
-
|------------------------|------------------------------------------------------------------------------------------|
|
|
155
|
-
| `--openapi-out` | Output base or file for OpenAPI (if omitted chooses `openapi.json`). |
|
|
156
|
-
| `--basePath` | Prefix for REST path segments (e.g. `/v1/booking`). |
|
|
157
|
-
| `--pathStyle` | Control operation name → path transformation: `kebab`, `asis`, `lower`. Default: `kebab` |
|
|
158
|
-
| `--method` | Default HTTP method (per‑op override via `--ops`). Default: `post`. |
|
|
159
|
-
| `--tag-style` | Tag inference: `default`, `service`, `first`. Default: `default`. |
|
|
160
|
-
| `--security` | Path to `security.json` (schemes + headers + overrides). |
|
|
161
|
-
| `--tags` | Path to `tags.json` (explicit operation → tag map). |
|
|
162
|
-
| `--ops` | Path to `ops.json` (method/summary/description/deprecated). |
|
|
163
|
-
| `--closedSchemas` | Apply `additionalProperties:false` globally. Default: `false`. |
|
|
164
|
-
| `--pruneUnusedSchemas` | Emit only reachable schemas. Default: `false`. |
|
|
165
|
-
| `--servers` | Comma‑separated server base URLs for the spec. Default: `/`. |
|
|
166
|
-
|
|
167
|
-
Deterministic ordering: all path keys, HTTP methods, component schema names, securitySchemes, parameters, component section keys, and operation tag arrays are alphabetically sorted for diff‑friendly output. The generator also omits a custom `jsonSchemaDialect` declaration to maximize IDE/tool compatibility (JetBrains warning avoidance) unless a future flag introduces non‑default dialect selection.
|
|
168
|
-
|
|
169
|
-
### 5.4 Programmatic OpenAPI Generation
|
|
170
|
-
```ts
|
|
171
|
-
import { generateOpenAPI } from "@techspokes/typescript-wsdl-client";
|
|
172
|
-
const { jsonPath, yamlPath } = await generateOpenAPI({
|
|
173
|
-
wsdl: "./wsdl/Hotel.wsdl",
|
|
174
|
-
outFile: "./openapi/hotel",
|
|
175
|
-
format: "both",
|
|
176
|
-
servers: ["https://api.example.com/v1"] // optional; defaults to ["/"] when omitted
|
|
177
|
-
});
|
|
269
|
+
|
|
270
|
+
## 6. Command: `client`
|
|
271
|
+
|
|
272
|
+
**Purpose**: Generate strongly-typed TypeScript SOAP client code from WSDL or a pre-compiled catalog.
|
|
273
|
+
|
|
274
|
+
**When to use**:
|
|
275
|
+
- Standard SOAP integration (most common use case)
|
|
276
|
+
- When you need TypeScript types and client methods for SOAP operations
|
|
277
|
+
- When building applications that consume SOAP services
|
|
278
|
+
|
|
279
|
+
### Usage
|
|
280
|
+
|
|
281
|
+
```bash
|
|
282
|
+
npx wsdl-tsc client --wsdl-source <file|url> --client-dir <path> [options]
|
|
283
|
+
# OR
|
|
284
|
+
npx wsdl-tsc client --catalog-file <path> --client-dir <path> [options]
|
|
178
285
|
```
|
|
179
286
|
|
|
180
|
-
###
|
|
181
|
-
To provide a consistent, debuggable, gateway‑friendly REST surface over SOAP operations, all responses are wrapped in a **standard envelope**. You can customize naming, but disabling the envelope is no longer supported.
|
|
287
|
+
### Required Flags
|
|
182
288
|
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
-
|
|
186
|
-
-
|
|
187
|
-
|
|
289
|
+
| Flag | Description |
|
|
290
|
+
|------------------|-------------------------------------------------|
|
|
291
|
+
| `--wsdl-source` | Path or URL to WSDL file (see note below) |
|
|
292
|
+
| `--client-dir` | Output directory for generated TypeScript files |
|
|
293
|
+
|
|
294
|
+
### Optional Input Flags
|
|
295
|
+
|
|
296
|
+
| Flag | Default | Description |
|
|
297
|
+
|------------------|-----------------------------|----------------------------------------------------------------------|
|
|
298
|
+
| `--catalog-file` | `{client-dir}/catalog.json` | Path to pre-compiled `catalog.json` (when not using `--wsdl-source`) |
|
|
299
|
+
|
|
300
|
+
**Note**: Provide **either** `--wsdl-source` (to compile from WSDL) **or** `--catalog-file` (to use pre-compiled catalog). When using `--wsdl-source`, the catalog is automatically generated in the client directory unless you override with `--catalog-file`.
|
|
301
|
+
|
|
302
|
+
### Generated Files
|
|
303
|
+
|
|
304
|
+
| File | Purpose |
|
|
305
|
+
|----------------|------------------------------------------------------------------------------|
|
|
306
|
+
| `client.ts` | Strongly-typed SOAP client wrapper with one method per operation |
|
|
307
|
+
| `types.ts` | Flattened TypeScript interfaces, type aliases, and enums |
|
|
308
|
+
| `utils.ts` | Runtime metadata for JSON to SOAP conversion (attribute mapping, occurrence) |
|
|
309
|
+
| `catalog.json` | (When using `--wsdl-source`) Generated in client directory by default |
|
|
310
|
+
|
|
311
|
+
### Optional Flags
|
|
312
|
+
|
|
313
|
+
All flags from `compile` command, plus:
|
|
314
|
+
|
|
315
|
+
| Flag | Default | Description |
|
|
316
|
+
|---------------------------------|----------------|-------------------------------------|
|
|
317
|
+
| `--import-extensions` | `js` | Import style: `js`, `ts`, or `bare` |
|
|
318
|
+
| `--client-attributes-key` | `$attributes` | Attribute bag key |
|
|
319
|
+
| `--client-class-name` | (derived) | Override client class name |
|
|
320
|
+
| `--client-int64-as` | `string` | Map 64-bit integers |
|
|
321
|
+
| `--client-bigint-as` | `string` | Map arbitrary-size integers |
|
|
322
|
+
| `--client-decimal-as` | `string` | Map `xs:decimal` |
|
|
323
|
+
| `--client-date-as` | `string` | Map date/time types |
|
|
324
|
+
| `--client-choice-mode` | `all-optional` | Choice element strategy |
|
|
325
|
+
| `--client-fail-on-unresolved` | `false` | Fail on unresolved references |
|
|
326
|
+
| `--client-nillable-as-optional` | `false` | Treat nillable as optional |
|
|
327
|
+
|
|
328
|
+
### Examples
|
|
329
|
+
|
|
330
|
+
#### Basic Generation (Default Catalog Location)
|
|
331
|
+
|
|
332
|
+
```bash
|
|
333
|
+
npx wsdl-tsc client \
|
|
334
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
335
|
+
--client-dir tmp/client
|
|
336
|
+
```
|
|
337
|
+
|
|
338
|
+
**Output**: Generates client files and catalog at `tmp/client/catalog.json`.
|
|
339
|
+
|
|
340
|
+
#### With Custom Catalog Path
|
|
341
|
+
|
|
342
|
+
```bash
|
|
343
|
+
npx wsdl-tsc client \
|
|
344
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
345
|
+
--client-dir tmp/client \
|
|
346
|
+
--catalog-file build/shared-catalog.json
|
|
347
|
+
```
|
|
348
|
+
|
|
349
|
+
#### With Custom Numeric Mappings
|
|
350
|
+
|
|
351
|
+
```bash
|
|
352
|
+
npx wsdl-tsc client \
|
|
353
|
+
--wsdl-source https://example.com/Hotel.wsdl \
|
|
354
|
+
--client-dir ./src/integrations/soap/hotel \
|
|
355
|
+
--client-int64-as number \
|
|
356
|
+
--client-decimal-as string \
|
|
357
|
+
--client-date-as string
|
|
358
|
+
```
|
|
359
|
+
|
|
360
|
+
**Output**: Catalog generated at `./src/integrations/soap/hotel/catalog.json`.
|
|
361
|
+
|
|
362
|
+
#### From Pre-compiled Catalog
|
|
363
|
+
|
|
364
|
+
```bash
|
|
365
|
+
# First compile the catalog
|
|
366
|
+
npx wsdl-tsc compile --wsdl-source https://example.com/Hotel.wsdl --catalog-file build/hotel-catalog.json
|
|
367
|
+
|
|
368
|
+
# Then generate client from catalog
|
|
369
|
+
npx wsdl-tsc client \
|
|
370
|
+
--catalog-file build/hotel-catalog.json \
|
|
371
|
+
--client-dir ./src/services/hotel
|
|
372
|
+
```
|
|
373
|
+
|
|
374
|
+
### Key Modeling Rules
|
|
375
|
+
|
|
376
|
+
- **Attributes & elements** become peer properties (flattened)
|
|
377
|
+
- **Text content** becomes `$value` property
|
|
378
|
+
- **Required attributes**: `use!="optional"`; elements `minOccurs>=1`
|
|
379
|
+
- **Multiplicity**: `maxOccurs>1` or `unbounded` become arrays
|
|
380
|
+
- **Nillable**: `nillable="true"` preserved (optionally model as optional with `--client-nillable-as-optional`)
|
|
381
|
+
- **Inheritance**: extensions merged or emitted as `extends`; simpleContent base collapsed logically
|
|
382
|
+
|
|
383
|
+
---
|
|
384
|
+
|
|
385
|
+
## 7. Command: `openapi`
|
|
386
|
+
|
|
387
|
+
**Purpose**: Generate OpenAPI 3.1 specification from WSDL or a pre-compiled catalog, mirroring the exact TypeScript type structure.
|
|
388
|
+
|
|
389
|
+
**When to use**:
|
|
390
|
+
- Creating REST API documentation for SOAP services
|
|
391
|
+
- Building API gateways or proxies
|
|
392
|
+
- Enabling REST-style access to SOAP operations
|
|
393
|
+
- Generating client SDKs in other languages
|
|
394
|
+
|
|
395
|
+
### Usage
|
|
396
|
+
|
|
397
|
+
```bash
|
|
398
|
+
npx wsdl-tsc openapi --wsdl-source <file|url> --openapi-file <path> [options]
|
|
399
|
+
# OR
|
|
400
|
+
npx wsdl-tsc openapi --catalog-file <path> --openapi-file <path> [options]
|
|
401
|
+
```
|
|
402
|
+
|
|
403
|
+
### Required Flags
|
|
404
|
+
|
|
405
|
+
| Flag | Description |
|
|
406
|
+
|---------------------|----------------------------------------------------|
|
|
407
|
+
| `--openapi-file` | Output path for OpenAPI specification |
|
|
408
|
+
|
|
409
|
+
### Input Source Flags (Mutually Exclusive)
|
|
410
|
+
|
|
411
|
+
| Flag | Default | Description |
|
|
412
|
+
|---------------------|--------------------------------------|----------------------------------------------------|
|
|
413
|
+
| `--wsdl-source` | (none) | Path or URL to WSDL file |
|
|
414
|
+
| `--catalog-file` | `{openapi-file-dir}/catalog.json` | Path to pre-compiled `catalog.json` |
|
|
188
415
|
|
|
189
|
-
|
|
416
|
+
**Note**: Provide **either** `--wsdl-source` **or** `--catalog-file`. When neither is provided, defaults to reading from the OpenAPI output directory. When using `--wsdl-source`, the catalog is automatically written to the OpenAPI output directory unless overridden.
|
|
190
417
|
|
|
191
|
-
|
|
192
|
-
|-----------|----------------------|-------------------------------------------------------------------|
|
|
193
|
-
| `status` | string | High‑level machine status (e.g. `SUCCESS`, `FAILURE`, `PENDING`). |
|
|
194
|
-
| `message` | string \| null | Diagnostic / log message (not for end‑user UI). |
|
|
195
|
-
| `data` | any \| null | Operation payload (per‑operation extension specializes this). |
|
|
196
|
-
| `error` | Error object \| null | Populated on failures; null on success. |
|
|
418
|
+
### Core Optional Flags
|
|
197
419
|
|
|
198
|
-
|
|
420
|
+
| Flag | Default | Description |
|
|
421
|
+
|-------------------------------|-----------|----------------------------------------------------------|
|
|
422
|
+
| `--openapi-format` | `json` | Output format: `json`, `yaml`, or `both` |
|
|
423
|
+
| `--openapi-title` | (derived) | API title in `info` section |
|
|
424
|
+
| `--openapi-version` | `0.0.0` | API version in `info.version` |
|
|
425
|
+
| `--openapi-description` | (empty) | API description in `info` section |
|
|
426
|
+
| `--openapi-servers` | `/` | Comma-separated server URLs |
|
|
427
|
+
| `--openapi-base-path` | (empty) | Base path prefix (e.g., `/v1/soap`) |
|
|
428
|
+
| `--openapi-validate` | `true` | Validate spec with `swagger-parser` |
|
|
199
429
|
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
|
203
|
-
|
|
204
|
-
| `
|
|
430
|
+
### Path & Schema Customization
|
|
431
|
+
|
|
432
|
+
| Flag | Default | Description |
|
|
433
|
+
|----------------------------------|-----------|--------------------------------------------------|
|
|
434
|
+
| `--openapi-path-style` | `kebab` | Path transformation: `kebab`, `asis`, or `lower` |
|
|
435
|
+
| `--openapi-method` | `post` | Default HTTP method for operations |
|
|
436
|
+
| `--openapi-tag-style` | `default` | Tag inference: `default`, `service`, or `first` |
|
|
437
|
+
| `--openapi-closed-schemas` | `false` | Add `additionalProperties: false` to all schemas |
|
|
438
|
+
| `--openapi-prune-unused-schemas` | `false` | Emit only schemas referenced by operations |
|
|
439
|
+
|
|
440
|
+
### Response Envelope Customization
|
|
441
|
+
|
|
442
|
+
| Flag | Default | Description |
|
|
443
|
+
|--------------------------------|--------------------|---------------------------------------------|
|
|
444
|
+
| `--openapi-envelope-namespace` | `ResponseEnvelope` | Override envelope component name suffix |
|
|
445
|
+
| `--openapi-error-namespace` | `ErrorObject` | Override error object component name suffix |
|
|
446
|
+
|
|
447
|
+
### Configuration Files
|
|
448
|
+
|
|
449
|
+
| Flag | Description |
|
|
450
|
+
|-----------------------------------|-------------------------------------------------------|
|
|
451
|
+
| `--openapi-security-config-file` | Path to `security.json` (schemes, headers, overrides) |
|
|
452
|
+
| `--openapi-tags-file` | Path to `tags.json` (explicit operation → tag map) |
|
|
453
|
+
| `--openapi-ops-file` | Path to `ops.json` (per-operation overrides) |
|
|
454
|
+
|
|
455
|
+
### Examples
|
|
456
|
+
|
|
457
|
+
#### Basic JSON Output
|
|
458
|
+
|
|
459
|
+
```bash
|
|
460
|
+
npx wsdl-tsc openapi \
|
|
461
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
462
|
+
--openapi-file ./docs/weather-api.json
|
|
463
|
+
```
|
|
464
|
+
|
|
465
|
+
#### Multi-Format with Validation
|
|
466
|
+
|
|
467
|
+
```bash
|
|
468
|
+
npx wsdl-tsc openapi \
|
|
469
|
+
--wsdl-source https://example.com/Hotel.wsdl \
|
|
470
|
+
--openapi-file ./docs/hotel-api \
|
|
471
|
+
--openapi-format both \
|
|
472
|
+
--openapi-servers https://api.example.com/v1,https://api-staging.example.com/v1 \
|
|
473
|
+
--openapi-base-path /soap
|
|
474
|
+
```
|
|
475
|
+
|
|
476
|
+
#### From Pre-compiled Catalog
|
|
477
|
+
|
|
478
|
+
```bash
|
|
479
|
+
npx wsdl-tsc openapi \
|
|
480
|
+
--catalog-file ./artifacts/hotel-catalog.json \
|
|
481
|
+
--openapi-file ./docs/hotel-api.json \
|
|
482
|
+
--openapi-format json
|
|
483
|
+
```
|
|
484
|
+
|
|
485
|
+
#### With Custom Configuration
|
|
486
|
+
|
|
487
|
+
```bash
|
|
488
|
+
npx wsdl-tsc openapi \
|
|
489
|
+
--wsdl-source ./wsdl/Booking.wsdl \
|
|
490
|
+
--openapi-file ./docs/booking-api.yaml \
|
|
491
|
+
--openapi-format yaml \
|
|
492
|
+
--openapi-title "Hotel Booking API" \
|
|
493
|
+
--openapi-version "1.2.0" \
|
|
494
|
+
--openapi-description "REST API for hotel booking SOAP service" \
|
|
495
|
+
--openapi-security-config-file ./config/security.json \
|
|
496
|
+
--openapi-tags-file ./config/tags.json \
|
|
497
|
+
--openapi-path-style kebab \
|
|
498
|
+
--openapi-method post \
|
|
499
|
+
--openapi-tag-style service
|
|
500
|
+
```
|
|
501
|
+
|
|
502
|
+
### Standard Response Envelope
|
|
503
|
+
|
|
504
|
+
All responses are wrapped in a **standard envelope** for consistency and debuggability (always-on since 0.7.1):
|
|
505
|
+
|
|
506
|
+
#### Base Envelope Structure
|
|
507
|
+
|
|
508
|
+
```typescript
|
|
509
|
+
{
|
|
510
|
+
status: string; // e.g., "SUCCESS", "FAILURE", "PENDING"
|
|
511
|
+
message: string | null; // diagnostic message (not for end-user UI)
|
|
512
|
+
data: T | null; // operation payload (typed per operation)
|
|
513
|
+
error: ErrorObject | null; // populated on failures
|
|
514
|
+
}
|
|
515
|
+
```
|
|
516
|
+
|
|
517
|
+
#### Error Object Structure
|
|
518
|
+
|
|
519
|
+
```typescript
|
|
520
|
+
{
|
|
521
|
+
code: string; // stable machine error code
|
|
522
|
+
message: string; // brief description
|
|
523
|
+
details: object | null; // arbitrary extra info
|
|
524
|
+
}
|
|
525
|
+
```
|
|
205
526
|
|
|
206
527
|
#### Naming Rules
|
|
207
|
-
* Base envelope component: `${serviceName}ResponseEnvelope` (override with `--envelope-namespace`).
|
|
208
|
-
* Error object component: `${serviceName}ErrorObject` (override with `--error-namespace`).
|
|
209
|
-
* Per operation extension: `<PayloadType|OperationName><EnvelopeNamespace>` (alphabetically sorted for stable diffs) which refines `data` to that operation's output type.
|
|
210
|
-
* When you pass an explicit namespace flag its value is used verbatim (no service name prefix).
|
|
211
528
|
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
529
|
+
- **Base envelope**: `${serviceName}ResponseEnvelope` (override with `--openapi-envelope-namespace`)
|
|
530
|
+
- **Error object**: `${serviceName}ErrorObject` (override with `--openapi-error-namespace`)
|
|
531
|
+
- **Per-operation extension**: `<PayloadType|OperationName><EnvelopeNamespace>` (refines `data` field)
|
|
532
|
+
|
|
533
|
+
#### Collision Avoidance
|
|
534
|
+
|
|
535
|
+
If the payload type already ends with the namespace prefix, an underscore is inserted:
|
|
536
|
+
|
|
537
|
+
- Payload `WeatherResponse` + default `ResponseEnvelope` → `WeatherResponse_ResponseEnvelope`
|
|
538
|
+
- Payload `Booking` + default `ResponseEnvelope` → `BookingResponseEnvelope`
|
|
217
539
|
|
|
218
540
|
#### Example
|
|
541
|
+
|
|
219
542
|
```bash
|
|
220
543
|
npx wsdl-tsc openapi \
|
|
221
|
-
--wsdl ./wsdl/Hotel.wsdl \
|
|
222
|
-
--
|
|
223
|
-
--
|
|
224
|
-
--
|
|
225
|
-
--error-namespace ApiError
|
|
544
|
+
--wsdl-source ./wsdl/Hotel.wsdl \
|
|
545
|
+
--openapi-file ./docs/hotel-api.json \
|
|
546
|
+
--openapi-envelope-namespace ApiEnvelope \
|
|
547
|
+
--openapi-error-namespace ApiError
|
|
226
548
|
```
|
|
227
|
-
|
|
549
|
+
|
|
550
|
+
Produces components:
|
|
228
551
|
1. `HotelApiEnvelope` (base)
|
|
229
|
-
2. `<Payload
|
|
552
|
+
2. `<Payload>ApiEnvelope` extension schemas (alphabetically sorted)
|
|
230
553
|
3. `HotelApiError` (error object)
|
|
231
|
-
4.
|
|
554
|
+
4. Domain schemas
|
|
555
|
+
|
|
556
|
+
### Tag Inference Strategies
|
|
557
|
+
|
|
558
|
+
| Strategy | Behavior |
|
|
559
|
+
|-----------|------------------------------------------------------------------------------------|
|
|
560
|
+
| `default` | Single tag = service name (fallback `SOAP`) |
|
|
561
|
+
| `service` | Always service name (even if operation prefix differs) |
|
|
562
|
+
| `first` | First lexical segment of CamelCase operation (e.g., `GetCityWeatherByZIP` → `Get`) |
|
|
563
|
+
|
|
564
|
+
Use `--openapi-tags-file` for explicit mapping when heuristics are insufficient.
|
|
565
|
+
|
|
566
|
+
### Output Determinism
|
|
567
|
+
|
|
568
|
+
All generated OpenAPI specs have **deterministic ordering**:
|
|
569
|
+
- Path keys (alphabetically sorted)
|
|
570
|
+
- HTTP methods within paths (alphabetically sorted)
|
|
571
|
+
- Component schema names (alphabetically sorted)
|
|
572
|
+
- Security schemes (alphabetically sorted)
|
|
573
|
+
- Parameters (alphabetically sorted)
|
|
574
|
+
- Operation tag arrays (alphabetically sorted)
|
|
575
|
+
|
|
576
|
+
This ensures diff-friendly output for version control.
|
|
232
577
|
|
|
233
578
|
---
|
|
234
|
-
|
|
235
|
-
|
|
579
|
+
|
|
580
|
+
## 8. Command: `gateway`
|
|
581
|
+
|
|
582
|
+
**Purpose**: Generate Fastify gateway scaffolding (routes and schemas) from an OpenAPI 3.1 specification. This provides the foundation for building a REST API layer over your SOAP client.
|
|
583
|
+
|
|
584
|
+
> **Current Status (v0.8.0)**: The gateway generator produces basic scaffolding including route registration, JSON Schema validation setup, and handler stubs. Full code generation with complete handler implementations is planned for future releases. You will need to implement the business logic that calls your SOAP client and transforms responses.
|
|
585
|
+
|
|
586
|
+
**When to use**:
|
|
587
|
+
- Building a REST API gateway for legacy SOAP services
|
|
588
|
+
- Creating a modern HTTP/JSON interface for SOAP operations
|
|
589
|
+
- Setting up request/response validation with JSON Schema
|
|
590
|
+
- Establishing Fastify routing structure for SOAP operations
|
|
591
|
+
|
|
592
|
+
**What it generates**:
|
|
593
|
+
- Fastify route registration files
|
|
594
|
+
- JSON Schema models with URN-based IDs
|
|
595
|
+
- Operation schemas (request/response validation)
|
|
596
|
+
- Schema and route registration modules
|
|
597
|
+
- Handler stubs (require manual implementation)
|
|
598
|
+
- Full handler implementations (coming in future versions)
|
|
599
|
+
|
|
600
|
+
### Usage
|
|
601
|
+
|
|
236
602
|
```bash
|
|
237
|
-
npx wsdl-tsc
|
|
603
|
+
npx wsdl-tsc gateway \
|
|
604
|
+
--openapi-file <path> \
|
|
605
|
+
--client-dir <path> \
|
|
606
|
+
--gateway-dir <path> \
|
|
607
|
+
--gateway-service-name <slug> \
|
|
608
|
+
--gateway-version-prefix <slug> \
|
|
609
|
+
[options]
|
|
238
610
|
```
|
|
239
611
|
|
|
240
|
-
|
|
241
|
-
|----------------------------|----------|---------------------------------------|
|
|
242
|
-
| All SOAP flags | — | Same semantics as base generation. |
|
|
243
|
-
| All OpenAPI flags | — | Same semantics as standalone openapi. |
|
|
244
|
-
| `--openapi-out` | derived | Override OpenAPI base file. |
|
|
245
|
-
| `--format` | json | Multi-format control. |
|
|
246
|
-
| `--validate/--no-validate` | validate | Spec validation toggle. |
|
|
247
|
-
| `--tag-style` | default | Tag inference. |
|
|
612
|
+
### Required Flags
|
|
248
613
|
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
614
|
+
| Flag | Description |
|
|
615
|
+
|----------------------------|--------------------------------------------------------------------------|
|
|
616
|
+
| `--openapi-file` | Path to OpenAPI 3.1 JSON or YAML file |
|
|
617
|
+
| `--client-dir` | Path to client directory (where `client.ts` is located) |
|
|
618
|
+
| `--gateway-dir` | Output directory for generated gateway code |
|
|
619
|
+
| `--gateway-service-name` | Service identifier for URN generation (e.g., `weather`, `booking`) |
|
|
620
|
+
| `--gateway-version-prefix` | Version prefix for URN generation (e.g., `v1`, `v2`, `urn:1.0.2:schema`) |
|
|
621
|
+
|
|
622
|
+
### Optional Flags
|
|
623
|
+
|
|
624
|
+
| Flag | Default | Description |
|
|
625
|
+
|----------------------------------|---------------------------------------------------|------------------------------------------|
|
|
626
|
+
| `--import-extensions` | `js` | Import style: `js`, `ts`, or `bare` |
|
|
627
|
+
| `--gateway-default-status-codes` | `200,400,401,403,404,409,422,429,500,502,503,504` | Comma-separated status codes to backfill |
|
|
628
|
+
|
|
629
|
+
### Generated Output Structure
|
|
630
|
+
|
|
631
|
+
```
|
|
632
|
+
{gateway-dir}/
|
|
633
|
+
├── schemas/
|
|
634
|
+
│ ├── models/ # JSON Schema components with URN IDs
|
|
635
|
+
│ │ ├── <schema1>.json
|
|
636
|
+
│ │ ├── <schema2>.json
|
|
637
|
+
│ │ └── ...
|
|
638
|
+
│ └── operations/ # Fastify operation schemas
|
|
639
|
+
│ ├── <operation1>.json
|
|
640
|
+
│ ├── <operation2>.json
|
|
641
|
+
│ └── ...
|
|
642
|
+
├── routes/ # Individual route registration files
|
|
643
|
+
│ ├── <route1>.ts
|
|
644
|
+
│ ├── <route2>.ts
|
|
645
|
+
│ └── ...
|
|
646
|
+
├── schemas.ts # Schema registration module
|
|
647
|
+
└── routes.ts # Route aggregator module
|
|
648
|
+
```
|
|
649
|
+
|
|
650
|
+
### URN-Based Schema IDs
|
|
651
|
+
|
|
652
|
+
All generated JSON Schemas use deterministic URN identifiers:
|
|
653
|
+
|
|
654
|
+
```
|
|
655
|
+
urn:services:{serviceSlug}:{versionSlug}:schemas:{models|operations}:{schemaSlug}
|
|
656
|
+
```
|
|
657
|
+
|
|
658
|
+
**Example**: `urn:services:weather:v1:schemas:models:getcityweatherbyzipresponse`
|
|
659
|
+
|
|
660
|
+
### Contract Assumptions
|
|
661
|
+
|
|
662
|
+
The gateway generator enforces strict OpenAPI contract validation:
|
|
663
|
+
|
|
664
|
+
- All request/response bodies must use `$ref` to `components.schemas` (no inline schemas)
|
|
665
|
+
- Every operation must have a default response with `application/json` content
|
|
666
|
+
- All schemas referenced by operations must exist in `components.schemas`
|
|
667
|
+
|
|
668
|
+
### Examples
|
|
669
|
+
|
|
670
|
+
#### Basic Gateway Generation
|
|
671
|
+
|
|
672
|
+
```bash
|
|
673
|
+
npx wsdl-tsc gateway \
|
|
674
|
+
--openapi-file ./docs/weather-api.json \
|
|
675
|
+
--client-dir ./src/services/weather \
|
|
676
|
+
--gateway-dir ./src/gateway/weather \
|
|
677
|
+
--gateway-service-name weather \
|
|
678
|
+
--gateway-version-prefix v1
|
|
679
|
+
```
|
|
680
|
+
|
|
681
|
+
#### With Custom Status Codes
|
|
682
|
+
|
|
683
|
+
```bash
|
|
684
|
+
npx wsdl-tsc gateway \
|
|
685
|
+
--openapi-file ./docs/hotel-api.json \
|
|
686
|
+
--client-dir ./src/services/hotel \
|
|
687
|
+
--gateway-dir ./src/gateway/hotel \
|
|
688
|
+
--gateway-service-name hotel \
|
|
689
|
+
--gateway-version-prefix v2 \
|
|
690
|
+
--gateway-default-status-codes 200,400,401,404,500
|
|
691
|
+
```
|
|
692
|
+
|
|
693
|
+
#### From YAML OpenAPI
|
|
694
|
+
|
|
695
|
+
```bash
|
|
696
|
+
npx wsdl-tsc gateway \
|
|
697
|
+
--openapi-file ./docs/booking-api.yaml \
|
|
698
|
+
--client-dir ./src/services/booking \
|
|
699
|
+
--gateway-dir ./src/gateway/booking \
|
|
700
|
+
--gateway-service-name booking \
|
|
701
|
+
--gateway-version-prefix v1
|
|
702
|
+
```
|
|
703
|
+
|
|
704
|
+
### Integration Pattern
|
|
705
|
+
|
|
706
|
+
The generated gateway scaffolding provides the foundation for your Fastify application:
|
|
707
|
+
|
|
708
|
+
```typescript
|
|
709
|
+
import Fastify from 'fastify';
|
|
710
|
+
import { registerSchemas } from './gateway/schemas.js';
|
|
711
|
+
import { registerRoutes } from './gateway/routes.js';
|
|
712
|
+
|
|
713
|
+
const app = Fastify({ logger: true });
|
|
714
|
+
|
|
715
|
+
// Register JSON Schemas (validation setup)
|
|
716
|
+
await registerSchemas(app);
|
|
717
|
+
|
|
718
|
+
// Register routes (with handler stubs)
|
|
719
|
+
await registerRoutes(app, {
|
|
720
|
+
prefix: '/api/v1',
|
|
721
|
+
// Pass any route-level options
|
|
722
|
+
});
|
|
723
|
+
|
|
724
|
+
await app.listen({ port: 3000 });
|
|
725
|
+
```
|
|
726
|
+
|
|
727
|
+
> **Note**: The registered routes contain handler stubs that throw "Not implemented" errors. You must implement the handler logic in each route file before the gateway becomes functional.
|
|
728
|
+
|
|
729
|
+
### Handler Implementation
|
|
730
|
+
|
|
731
|
+
> ** Manual Implementation Required**: Currently, the gateway generator produces handler stubs that you must implement. Future versions will include full code generation for handler logic.
|
|
732
|
+
|
|
733
|
+
Each generated route file contains handler stubs that you need to implement:
|
|
734
|
+
|
|
735
|
+
```typescript
|
|
736
|
+
// Example: routes/get-weather.ts
|
|
737
|
+
export async function handler(request, reply) {
|
|
738
|
+
// TODO: Implement handler logic
|
|
739
|
+
// 1. Extract validated input from request.body
|
|
740
|
+
// 2. Call SOAP client
|
|
741
|
+
// 3. Transform response
|
|
742
|
+
// 4. Return standard envelope
|
|
743
|
+
|
|
744
|
+
throw new Error('Not implemented');
|
|
745
|
+
}
|
|
746
|
+
```
|
|
747
|
+
|
|
748
|
+
**Current workflow**:
|
|
749
|
+
1. Generate gateway scaffolding with `wsdl-tsc gateway`
|
|
750
|
+
2. Implement handler functions manually in each route file
|
|
751
|
+
3. Import and call your SOAP client
|
|
752
|
+
4. Transform SOAP responses to match OpenAPI schemas
|
|
753
|
+
5. Return responses in the standard envelope format
|
|
754
|
+
|
|
755
|
+
**Future enhancement**: Automated handler generation will include SOAP client calls, response transformation, error handling, and envelope wrapping.
|
|
756
|
+
|
|
757
|
+
---
|
|
758
|
+
|
|
759
|
+
## 9. Command: `pipeline`
|
|
760
|
+
|
|
761
|
+
**Purpose**: Run the complete generation pipeline in a single pass: WSDL parsing → TypeScript client → OpenAPI spec → Fastify gateway.
|
|
762
|
+
|
|
763
|
+
**When to use**:
|
|
764
|
+
- CI/CD automation
|
|
765
|
+
- Complete stack generation
|
|
766
|
+
- Ensuring all artifacts are generated from the same WSDL parse
|
|
767
|
+
- One-command development workflows
|
|
768
|
+
|
|
769
|
+
### Usage
|
|
770
|
+
|
|
771
|
+
```bash
|
|
772
|
+
npx wsdl-tsc pipeline \
|
|
773
|
+
--wsdl-source <file|url> \
|
|
774
|
+
[--catalog-file <path>] \
|
|
775
|
+
[--client-dir <path>] \
|
|
776
|
+
[--openapi-file <path>] \
|
|
777
|
+
[--gateway-dir <path>] \
|
|
778
|
+
[options]
|
|
779
|
+
```
|
|
780
|
+
|
|
781
|
+
### Required Flags
|
|
782
|
+
|
|
783
|
+
| Flag | Description |
|
|
784
|
+
|---------------------|----------------------------------------------------------------------|
|
|
785
|
+
| `--wsdl-source` | Path or URL to WSDL file |
|
|
786
|
+
|
|
787
|
+
### Output Flags
|
|
788
|
+
|
|
789
|
+
| Flag | Default | Description |
|
|
790
|
+
|---------------------|---------------------------------------------|---------------------------------------------------|
|
|
791
|
+
| `--catalog-file` | Co-located with first output (see below) | Output path for `catalog.json` (always generated) |
|
|
792
|
+
|
|
793
|
+
**Catalog Default Location**: The catalog is automatically placed alongside the first available output:
|
|
794
|
+
- With `--client-dir`: `{client-dir}/catalog.json`
|
|
795
|
+
- With `--openapi-file` only: `{openapi-file-dir}/catalog.json`
|
|
796
|
+
- With `--gateway-dir` only: `{gateway-dir}/catalog.json`
|
|
797
|
+
|
|
798
|
+
**Note**: At least one of `--client-dir`, `--openapi-file`, or `--gateway-dir` must be provided.
|
|
799
|
+
|
|
800
|
+
### Generation Control Flags
|
|
801
|
+
|
|
802
|
+
| Flag | Description |
|
|
803
|
+
|-------------------------|------------------------------------------------|
|
|
804
|
+
| `--client-dir` | Generate TypeScript client in this directory |
|
|
805
|
+
| `--openapi-file` | Generate OpenAPI spec at this path |
|
|
806
|
+
| `--gateway-dir` | Generate Fastify gateway in this directory |
|
|
807
|
+
|
|
808
|
+
### Optional Flags
|
|
809
|
+
|
|
810
|
+
All flags from `client`, `openapi`, and `gateway` commands are supported. Key flags:
|
|
811
|
+
|
|
812
|
+
#### Client Flags
|
|
813
|
+
- `--import-extensions` (default: `js`)
|
|
814
|
+
- `--client-attributes-key` (default: `$attributes`)
|
|
815
|
+
- `--client-class-name`
|
|
816
|
+
- `--client-int64-as` (default: `string`)
|
|
817
|
+
- `--client-bigint-as` (default: `string`)
|
|
818
|
+
- `--client-decimal-as` (default: `string`)
|
|
819
|
+
- `--client-date-as` (default: `string`)
|
|
820
|
+
- `--client-choice-mode` (default: `all-optional`)
|
|
821
|
+
- `--client-fail-on-unresolved` (default: `false`)
|
|
822
|
+
- `--client-nillable-as-optional` (default: `false`)
|
|
823
|
+
|
|
824
|
+
#### OpenAPI Flags
|
|
825
|
+
- `--openapi-format` (default: `json`)
|
|
826
|
+
- `--openapi-title`
|
|
827
|
+
- `--openapi-version` (default: `0.0.0`)
|
|
828
|
+
- `--openapi-description`
|
|
829
|
+
- `--openapi-servers` (default: `/`)
|
|
830
|
+
- `--openapi-base-path`
|
|
831
|
+
- `--openapi-path-style` (default: `kebab`)
|
|
832
|
+
- `--openapi-method` (default: `post`)
|
|
833
|
+
- `--openapi-tag-style` (default: `default`)
|
|
834
|
+
- `--openapi-closed-schemas` (default: `false`)
|
|
835
|
+
- `--openapi-prune-unused-schemas` (default: `false`)
|
|
836
|
+
- `--openapi-envelope-namespace` (default: `ResponseEnvelope`)
|
|
837
|
+
- `--openapi-error-namespace` (default: `ErrorObject`)
|
|
838
|
+
- `--openapi-validate` (default: `true`)
|
|
839
|
+
- `--openapi-security-config-file`
|
|
840
|
+
- `--openapi-tags-file`
|
|
841
|
+
- `--openapi-ops-file`
|
|
842
|
+
|
|
843
|
+
#### Gateway Flags
|
|
844
|
+
- `--gateway-service-name` (required if `--gateway-dir` provided)
|
|
845
|
+
- `--gateway-version-prefix` (required if `--gateway-dir` provided)
|
|
846
|
+
- `--gateway-default-status-codes`
|
|
847
|
+
|
|
848
|
+
### Examples
|
|
849
|
+
|
|
850
|
+
#### Complete Stack Generation (Using Default Catalog Location)
|
|
851
|
+
|
|
852
|
+
```bash
|
|
853
|
+
npx wsdl-tsc pipeline \
|
|
854
|
+
--wsdl-source examples/minimal/weather.wsdl \
|
|
855
|
+
--client-dir tmp/client \
|
|
856
|
+
--openapi-file tmp/openapi.json \
|
|
857
|
+
--gateway-dir tmp/gateway \
|
|
858
|
+
--gateway-service-name weather \
|
|
859
|
+
--gateway-version-prefix v1
|
|
860
|
+
```
|
|
861
|
+
|
|
862
|
+
**Output**: Catalog at `tmp/client/catalog.json`.
|
|
863
|
+
|
|
864
|
+
#### Client + OpenAPI Only
|
|
865
|
+
|
|
866
|
+
```bash
|
|
867
|
+
npx wsdl-tsc pipeline \
|
|
868
|
+
--wsdl-source https://example.com/Hotel.wsdl \
|
|
869
|
+
--client-dir ./build/client \
|
|
870
|
+
--openapi-file ./docs/hotel-api.json \
|
|
871
|
+
--openapi-format both
|
|
872
|
+
```
|
|
873
|
+
|
|
874
|
+
**Output**: Catalog at `./build/client/catalog.json`.
|
|
875
|
+
|
|
876
|
+
#### OpenAPI + Gateway Only
|
|
877
|
+
|
|
878
|
+
```bash
|
|
879
|
+
npx wsdl-tsc pipeline \
|
|
880
|
+
--wsdl-source ./wsdl/Booking.wsdl \
|
|
881
|
+
--openapi-file ./docs/booking-api.json \
|
|
882
|
+
--gateway-dir ./build/gateway \
|
|
883
|
+
--gateway-service-name booking \
|
|
884
|
+
--gateway-version-prefix v1
|
|
885
|
+
```
|
|
886
|
+
|
|
887
|
+
**Output**: Catalog at `./docs/catalog.json`.
|
|
888
|
+
|
|
889
|
+
#### With Custom Catalog Path
|
|
890
|
+
|
|
891
|
+
```bash
|
|
892
|
+
npx wsdl-tsc pipeline \
|
|
893
|
+
--wsdl-source ./wsdl/Booking.wsdl \
|
|
894
|
+
--catalog-file ./build/shared/catalog.json \
|
|
895
|
+
--client-dir ./build/client \
|
|
896
|
+
--openapi-file ./docs/booking-api.json \
|
|
897
|
+
--gateway-dir ./build/gateway \
|
|
898
|
+
--gateway-service-name booking \
|
|
899
|
+
--gateway-version-prefix v1
|
|
900
|
+
```
|
|
901
|
+
|
|
902
|
+
#### With Full Configuration
|
|
903
|
+
|
|
904
|
+
```bash
|
|
905
|
+
npx wsdl-tsc pipeline \
|
|
906
|
+
--wsdl-source ./wsdl/Booking.wsdl \
|
|
907
|
+
--client-dir ./build/client \
|
|
908
|
+
--openapi-file ./docs/booking-api \
|
|
909
|
+
--gateway-dir ./build/gateway \
|
|
910
|
+
--openapi-format both \
|
|
911
|
+
--openapi-servers https://api.example.com/v1 \
|
|
912
|
+
--openapi-base-path /booking \
|
|
913
|
+
--openapi-security-config-file ./config/security.json \
|
|
914
|
+
--gateway-service-name booking \
|
|
915
|
+
--gateway-version-prefix v1 \
|
|
916
|
+
--client-int64-as number \
|
|
917
|
+
--client-decimal-as string
|
|
918
|
+
```
|
|
919
|
+
|
|
920
|
+
**Output**: Catalog at `./build/client/catalog.json`.
|
|
921
|
+
|
|
922
|
+
### Pipeline Workflow
|
|
923
|
+
|
|
924
|
+
The pipeline command executes these steps in order:
|
|
925
|
+
|
|
926
|
+
1. **Parse WSDL** → Load and validate WSDL document
|
|
927
|
+
2. **Compile Catalog** → Generate intermediate representation
|
|
928
|
+
3. **Emit Catalog** → Write `catalog.json` (always)
|
|
929
|
+
4. **Generate Client** → Emit TypeScript client files (if `--client-dir`)
|
|
930
|
+
5. **Generate OpenAPI** → Create OpenAPI spec (if `--openapi-file`)
|
|
931
|
+
6. **Generate Gateway** → Create Fastify gateway code (if `--gateway-dir`)
|
|
932
|
+
|
|
933
|
+
All steps share the same parsed WSDL and compiled catalog, ensuring consistency.
|
|
934
|
+
|
|
935
|
+
---
|
|
936
|
+
|
|
937
|
+
## 10. Working With Generated Clients
|
|
938
|
+
|
|
939
|
+
### Client Construction
|
|
940
|
+
|
|
941
|
+
```typescript
|
|
942
|
+
import soap from "soap";
|
|
943
|
+
import { Weather } from "./src/services/weather/client.js";
|
|
944
|
+
|
|
945
|
+
const client = new Weather({
|
|
946
|
+
source: "https://example.com/WeatherService?wsdl",
|
|
947
|
+
security: new soap.WSSecurity("username", "password")
|
|
948
|
+
});
|
|
949
|
+
```
|
|
950
|
+
|
|
951
|
+
### Calling Operations
|
|
952
|
+
|
|
953
|
+
```typescript
|
|
954
|
+
// Operation with input
|
|
955
|
+
const forecast = await client.GetCityForecastByZIP({
|
|
956
|
+
ZIP: "10001"
|
|
256
957
|
});
|
|
958
|
+
|
|
959
|
+
console.log(forecast.GetCityForecastByZIPResult.Success);
|
|
960
|
+
console.log(forecast.GetCityForecastByZIPResult.ForecastResult);
|
|
961
|
+
|
|
962
|
+
// Operation without input
|
|
963
|
+
const info = await client.GetWeatherInformation({});
|
|
964
|
+
console.log(info.GetWeatherInformationResult.WeatherDescriptions);
|
|
965
|
+
```
|
|
966
|
+
|
|
967
|
+
### Attributes & Text Content
|
|
968
|
+
|
|
969
|
+
When an element has both attributes and text content, use the `$value` convention:
|
|
970
|
+
|
|
971
|
+
```typescript
|
|
972
|
+
const price = {
|
|
973
|
+
currencyCode: "USD", // attribute
|
|
974
|
+
$value: "123.45" // text content
|
|
975
|
+
};
|
|
976
|
+
```
|
|
977
|
+
|
|
978
|
+
### Working With Arrays
|
|
979
|
+
|
|
980
|
+
Repeated elements are automatically typed as arrays:
|
|
981
|
+
|
|
982
|
+
```typescript
|
|
983
|
+
interface ForecastReturn {
|
|
984
|
+
Forecast: Forecast[]; // maxOccurs > 1
|
|
985
|
+
}
|
|
986
|
+
```
|
|
987
|
+
|
|
988
|
+
### Type Safety
|
|
989
|
+
|
|
990
|
+
All operations and types are fully typed:
|
|
991
|
+
|
|
992
|
+
```typescript
|
|
993
|
+
// TypeScript knows the exact shape
|
|
994
|
+
const result: GetCityWeatherByZIPResponse = await client.GetCityWeatherByZIP({
|
|
995
|
+
ZIP: "10001"
|
|
996
|
+
});
|
|
997
|
+
|
|
998
|
+
// Autocomplete and type checking work
|
|
999
|
+
result.GetCityWeatherByZIPResult.Temperature; // number | string (depends on mapping)
|
|
257
1000
|
```
|
|
258
1001
|
|
|
259
1002
|
---
|
|
260
|
-
|
|
261
|
-
|
|
1003
|
+
|
|
1004
|
+
## 11. OpenAPI Configuration
|
|
1005
|
+
|
|
1006
|
+
### Security Configuration (`security.json`)
|
|
1007
|
+
|
|
1008
|
+
Define security schemes, headers, and per-operation overrides:
|
|
1009
|
+
|
|
262
1010
|
```json
|
|
263
1011
|
{
|
|
264
1012
|
"global": {
|
|
265
1013
|
"scheme": "bearer",
|
|
266
1014
|
"bearer": { "bearerFormat": "JWT" },
|
|
267
|
-
"headers": [
|
|
1015
|
+
"headers": [
|
|
1016
|
+
{
|
|
1017
|
+
"name": "X-Correlation-Id",
|
|
1018
|
+
"required": false,
|
|
1019
|
+
"schema": { "type": "string" }
|
|
1020
|
+
}
|
|
1021
|
+
]
|
|
268
1022
|
},
|
|
269
1023
|
"overrides": {
|
|
270
1024
|
"CancelBooking": { "scheme": "apiKey" }
|
|
271
1025
|
}
|
|
272
1026
|
}
|
|
273
1027
|
```
|
|
274
|
-
Supported `scheme`: `none|basic|bearer|apiKey|oauth2`.
|
|
275
1028
|
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|-----------|------------------------------------------------------------------------------------|
|
|
280
|
-
| `default` | Single tag = service name (fallback `SOAP`). |
|
|
281
|
-
| `service` | Always service name (even if operation prefix differs). |
|
|
282
|
-
| `first` | First lexical segment of CamelCase operation (e.g. `GetCityWeatherByZIP` → `Get`). |
|
|
1029
|
+
**Supported schemes**: `none`, `basic`, `bearer`, `apiKey`, `oauth2`
|
|
1030
|
+
|
|
1031
|
+
### Tags Configuration (`tags.json`)
|
|
283
1032
|
|
|
284
|
-
|
|
1033
|
+
Explicit operation → tag mapping:
|
|
1034
|
+
|
|
1035
|
+
```json
|
|
1036
|
+
{
|
|
1037
|
+
"GetCityWeatherByZIP": ["Weather", "Forecast"],
|
|
1038
|
+
"GetWeatherInformation": ["Weather", "Info"],
|
|
1039
|
+
"CancelBooking": ["Booking", "Cancellation"]
|
|
1040
|
+
}
|
|
1041
|
+
```
|
|
1042
|
+
|
|
1043
|
+
### Operations Configuration (`ops.json`)
|
|
1044
|
+
|
|
1045
|
+
Per-operation overrides for method, summary, description, and deprecation:
|
|
1046
|
+
|
|
1047
|
+
```json
|
|
1048
|
+
{
|
|
1049
|
+
"GetCityWeatherByZIP": {
|
|
1050
|
+
"method": "get",
|
|
1051
|
+
"summary": "Get weather forecast by ZIP code",
|
|
1052
|
+
"description": "Returns a detailed weather forecast for the specified US ZIP code",
|
|
1053
|
+
"deprecated": false
|
|
1054
|
+
},
|
|
1055
|
+
"LegacyOperation": {
|
|
1056
|
+
"deprecated": true
|
|
1057
|
+
}
|
|
1058
|
+
}
|
|
1059
|
+
```
|
|
285
1060
|
|
|
286
1061
|
---
|
|
287
|
-
## 9. Working With the Generated Client
|
|
288
|
-
### 9.1 SOAP Client Construction
|
|
289
|
-
```ts
|
|
290
|
-
import soap from "soap";
|
|
291
|
-
import { Hotel } from "./src/integrations/soap/hotel/client.js";
|
|
292
1062
|
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
1063
|
+
## 12. Programmatic API
|
|
1064
|
+
|
|
1065
|
+
All CLI commands are available as TypeScript functions for programmatic usage.
|
|
1066
|
+
|
|
1067
|
+
### `compileWsdlToProject`
|
|
1068
|
+
|
|
1069
|
+
Generate TypeScript SOAP client from WSDL.
|
|
1070
|
+
|
|
1071
|
+
```typescript
|
|
1072
|
+
import { compileWsdlToProject } from "@techspokes/typescript-wsdl-client";
|
|
1073
|
+
|
|
1074
|
+
await compileWsdlToProject({
|
|
1075
|
+
wsdl: "./wsdl/Hotel.wsdl",
|
|
1076
|
+
outDir: "./src/services/hotel",
|
|
1077
|
+
options: {
|
|
1078
|
+
imports: "js",
|
|
1079
|
+
catalog: true,
|
|
1080
|
+
primitive: {
|
|
1081
|
+
int64As: "number",
|
|
1082
|
+
bigIntegerAs: "string",
|
|
1083
|
+
decimalAs: "string",
|
|
1084
|
+
dateAs: "string"
|
|
1085
|
+
},
|
|
1086
|
+
choice: "all-optional",
|
|
1087
|
+
clientName: "HotelClient",
|
|
1088
|
+
nillableAsOptional: false
|
|
1089
|
+
}
|
|
296
1090
|
});
|
|
1091
|
+
```
|
|
1092
|
+
|
|
1093
|
+
**Type Signature**:
|
|
1094
|
+
|
|
1095
|
+
```typescript
|
|
1096
|
+
// noinspection JSAnnotator
|
|
1097
|
+
function compileWsdlToProject(input: {
|
|
1098
|
+
wsdl: string;
|
|
1099
|
+
outDir: string;
|
|
1100
|
+
options?: Partial<CompilerOptions>;
|
|
1101
|
+
}): Promise<void>;
|
|
1102
|
+
```
|
|
1103
|
+
|
|
1104
|
+
**Options** (`CompilerOptions`):
|
|
1105
|
+
|
|
1106
|
+
```typescript
|
|
1107
|
+
interface CompilerOptions {
|
|
1108
|
+
wsdl: string;
|
|
1109
|
+
out: string;
|
|
1110
|
+
imports: "js" | "ts" | "bare";
|
|
1111
|
+
catalog: boolean;
|
|
1112
|
+
primitive: PrimitiveOptions;
|
|
1113
|
+
choice?: "all-optional" | "union";
|
|
1114
|
+
failOnUnresolved?: boolean;
|
|
1115
|
+
attributesKey?: string;
|
|
1116
|
+
clientName?: string;
|
|
1117
|
+
nillableAsOptional?: boolean;
|
|
1118
|
+
}
|
|
297
1119
|
|
|
298
|
-
|
|
299
|
-
|
|
1120
|
+
interface PrimitiveOptions {
|
|
1121
|
+
int64As?: "string" | "number" | "bigint";
|
|
1122
|
+
bigIntegerAs?: "string" | "number";
|
|
1123
|
+
decimalAs?: "string" | "number";
|
|
1124
|
+
dateAs?: "string" | "Date";
|
|
1125
|
+
}
|
|
1126
|
+
```
|
|
1127
|
+
|
|
1128
|
+
### `generateOpenAPI`
|
|
1129
|
+
|
|
1130
|
+
Generate OpenAPI 3.1 specification from WSDL or catalog.
|
|
1131
|
+
|
|
1132
|
+
```typescript
|
|
1133
|
+
import { generateOpenAPI } from "@techspokes/typescript-wsdl-client";
|
|
1134
|
+
|
|
1135
|
+
const { doc, jsonPath, yamlPath } = await generateOpenAPI({
|
|
1136
|
+
wsdl: "./wsdl/Hotel.wsdl",
|
|
1137
|
+
outFile: "./docs/hotel-api",
|
|
1138
|
+
format: "both",
|
|
1139
|
+
title: "Hotel Booking API",
|
|
1140
|
+
version: "1.0.0",
|
|
1141
|
+
servers: ["https://api.example.com/v1"],
|
|
1142
|
+
basePath: "/booking",
|
|
1143
|
+
pathStyle: "kebab",
|
|
1144
|
+
tagStyle: "service",
|
|
1145
|
+
validate: true
|
|
300
1146
|
});
|
|
301
1147
|
```
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
1148
|
+
|
|
1149
|
+
**Type Signature**:
|
|
1150
|
+
|
|
1151
|
+
```typescript
|
|
1152
|
+
// noinspection JSAnnotator
|
|
1153
|
+
function generateOpenAPI(opts: GenerateOpenAPIOptions): Promise<{
|
|
1154
|
+
doc: any;
|
|
1155
|
+
jsonPath?: string;
|
|
1156
|
+
yamlPath?: string;
|
|
1157
|
+
}>;
|
|
1158
|
+
```
|
|
1159
|
+
|
|
1160
|
+
**Options** (`GenerateOpenAPIOptions`):
|
|
1161
|
+
|
|
1162
|
+
```typescript
|
|
1163
|
+
interface GenerateOpenAPIOptions {
|
|
1164
|
+
// Input sources (mutually exclusive)
|
|
1165
|
+
wsdl?: string;
|
|
1166
|
+
catalogFile?: string;
|
|
1167
|
+
compiledCatalog?: CompiledCatalog;
|
|
1168
|
+
|
|
1169
|
+
// Output
|
|
1170
|
+
outFile?: string;
|
|
1171
|
+
format?: "json" | "yaml" | "both";
|
|
1172
|
+
|
|
1173
|
+
// Metadata
|
|
1174
|
+
title?: string;
|
|
1175
|
+
version?: string;
|
|
1176
|
+
description?: string;
|
|
1177
|
+
servers?: string[];
|
|
1178
|
+
|
|
1179
|
+
// Path configuration
|
|
1180
|
+
basePath?: string;
|
|
1181
|
+
pathStyle?: "kebab" | "asis" | "lower";
|
|
1182
|
+
defaultMethod?: string;
|
|
1183
|
+
|
|
1184
|
+
// Schema configuration
|
|
1185
|
+
closedSchemas?: boolean;
|
|
1186
|
+
pruneUnusedSchemas?: boolean;
|
|
1187
|
+
|
|
1188
|
+
// Tag configuration
|
|
1189
|
+
tagStyle?: "default" | "first" | "service";
|
|
1190
|
+
tagsFile?: string;
|
|
1191
|
+
|
|
1192
|
+
// Security & operations
|
|
1193
|
+
securityConfigFile?: string;
|
|
1194
|
+
opsFile?: string;
|
|
1195
|
+
|
|
1196
|
+
// Envelope customization
|
|
1197
|
+
envelopeNamespace?: string;
|
|
1198
|
+
errorNamespace?: string;
|
|
1199
|
+
|
|
1200
|
+
// Validation
|
|
1201
|
+
validate?: boolean;
|
|
1202
|
+
skipValidate?: boolean;
|
|
1203
|
+
|
|
1204
|
+
// Deprecated
|
|
1205
|
+
asYaml?: boolean;
|
|
1206
|
+
}
|
|
1207
|
+
```
|
|
1208
|
+
|
|
1209
|
+
### `generateGateway`
|
|
1210
|
+
|
|
1211
|
+
Generate Fastify gateway code from OpenAPI specification.
|
|
1212
|
+
|
|
1213
|
+
```typescript
|
|
1214
|
+
import { generateGateway } from "@techspokes/typescript-wsdl-client";
|
|
1215
|
+
|
|
1216
|
+
await generateGateway({
|
|
1217
|
+
openapiFile: "./docs/hotel-api.json",
|
|
1218
|
+
outDir: "./src/gateway/hotel",
|
|
1219
|
+
clientDir: "./src/services/hotel",
|
|
1220
|
+
versionSlug: "v1",
|
|
1221
|
+
serviceSlug: "hotel",
|
|
1222
|
+
defaultResponseStatusCodes: [200, 400, 401, 403, 404, 409, 422, 429, 500, 502, 503, 504],
|
|
1223
|
+
imports: "js"
|
|
1224
|
+
});
|
|
1225
|
+
```
|
|
1226
|
+
|
|
1227
|
+
**Type Signature**:
|
|
1228
|
+
|
|
1229
|
+
```typescript
|
|
1230
|
+
// noinspection JSAnnotator
|
|
1231
|
+
function generateGateway(opts: GenerateGatewayOptions): Promise<void>;
|
|
1232
|
+
```
|
|
1233
|
+
|
|
1234
|
+
**Options** (`GenerateGatewayOptions`):
|
|
1235
|
+
|
|
1236
|
+
```typescript
|
|
1237
|
+
interface GenerateGatewayOptions {
|
|
1238
|
+
// Input sources (mutually exclusive)
|
|
1239
|
+
openapiFile?: string;
|
|
1240
|
+
openapiDocument?: any;
|
|
1241
|
+
|
|
1242
|
+
// Output
|
|
1243
|
+
outDir: string;
|
|
1244
|
+
|
|
1245
|
+
// Client integration
|
|
1246
|
+
clientDir?: string;
|
|
1247
|
+
|
|
1248
|
+
// URN configuration
|
|
1249
|
+
versionSlug?: string;
|
|
1250
|
+
serviceSlug?: string;
|
|
1251
|
+
|
|
1252
|
+
// Schema configuration
|
|
1253
|
+
defaultResponseStatusCodes?: number[];
|
|
1254
|
+
|
|
1255
|
+
// Import style
|
|
1256
|
+
imports?: "js" | "ts" | "bare";
|
|
1257
|
+
}
|
|
1258
|
+
```
|
|
1259
|
+
|
|
1260
|
+
### `runGenerationPipeline`
|
|
1261
|
+
|
|
1262
|
+
Run complete pipeline: client + OpenAPI + gateway in one pass.
|
|
1263
|
+
|
|
1264
|
+
```typescript
|
|
1265
|
+
import { runGenerationPipeline } from "@techspokes/typescript-wsdl-client";
|
|
1266
|
+
|
|
1267
|
+
const { compiled, openapiDoc } = await runGenerationPipeline({
|
|
1268
|
+
wsdl: "./wsdl/Hotel.wsdl",
|
|
1269
|
+
catalogOut: "./build/hotel-catalog.json",
|
|
1270
|
+
clientOutDir: "./src/services/hotel",
|
|
1271
|
+
compiler: {
|
|
1272
|
+
imports: "js",
|
|
1273
|
+
primitive: {
|
|
1274
|
+
int64As: "number",
|
|
1275
|
+
decimalAs: "string"
|
|
1276
|
+
}
|
|
1277
|
+
},
|
|
1278
|
+
openapi: {
|
|
1279
|
+
outFile: "./docs/hotel-api.json",
|
|
1280
|
+
format: "both",
|
|
1281
|
+
servers: ["https://api.example.com/v1"],
|
|
1282
|
+
tagStyle: "service"
|
|
1283
|
+
},
|
|
1284
|
+
gateway: {
|
|
1285
|
+
outDir: "./src/gateway/hotel",
|
|
1286
|
+
versionSlug: "v1",
|
|
1287
|
+
serviceSlug: "hotel"
|
|
1288
|
+
}
|
|
1289
|
+
});
|
|
1290
|
+
```
|
|
1291
|
+
|
|
1292
|
+
**Type Signature**:
|
|
1293
|
+
|
|
1294
|
+
```typescript
|
|
1295
|
+
// noinspection JSAnnotator
|
|
1296
|
+
function runGenerationPipeline(opts: PipelineOptions): Promise<{
|
|
1297
|
+
compiled: CompiledCatalog;
|
|
1298
|
+
openapiDoc?: any;
|
|
1299
|
+
}>;
|
|
1300
|
+
```
|
|
1301
|
+
|
|
1302
|
+
**Options** (`PipelineOptions`):
|
|
1303
|
+
|
|
1304
|
+
```typescript
|
|
1305
|
+
interface PipelineOptions {
|
|
1306
|
+
// Input
|
|
1307
|
+
wsdl: string;
|
|
1308
|
+
|
|
1309
|
+
// Catalog (always generated)
|
|
1310
|
+
catalogOut: string;
|
|
1311
|
+
|
|
1312
|
+
// Client generation (optional)
|
|
1313
|
+
clientOutDir?: string;
|
|
1314
|
+
compiler?: Partial<CompilerOptions>;
|
|
1315
|
+
|
|
1316
|
+
// OpenAPI generation (optional)
|
|
1317
|
+
openapi?: Omit<GenerateOpenAPIOptions, "wsdl" | "catalogFile" | "compiledCatalog"> & {
|
|
1318
|
+
outFile?: string;
|
|
1319
|
+
};
|
|
1320
|
+
|
|
1321
|
+
// Gateway generation (optional, requires openapi)
|
|
1322
|
+
gateway?: Omit<GenerateGatewayOptions, "openapiFile" | "openapiDocument"> & {
|
|
1323
|
+
outDir?: string;
|
|
1324
|
+
};
|
|
1325
|
+
}
|
|
309
1326
|
```
|
|
310
1327
|
|
|
311
1328
|
---
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
|
1329
|
+
|
|
1330
|
+
## 13. Advanced Topics
|
|
1331
|
+
|
|
1332
|
+
### Primitive Mapping Philosophy
|
|
1333
|
+
|
|
1334
|
+
**Default: String-first safety** — Prevents precision loss and parsing errors at the cost of convenience.
|
|
1335
|
+
|
|
1336
|
+
| XSD Type | Default | Alternatives | Recommendation |
|
|
1337
|
+
|---------------|----------|--------------------|-------------------------------------------------|
|
|
1338
|
+
| `xs:long` | `string` | `number`, `bigint` | Use `number` if values fit safely in JS range |
|
|
1339
|
+
| `xs:integer` | `string` | `number` | Use `string` for arbitrary-size integers |
|
|
1340
|
+
| `xs:decimal` | `string` | `number` | Use `string` for precise decimal representation |
|
|
1341
|
+
| `xs:dateTime` | `string` | `Date` | Use `Date` if runtime parsing is acceptable |
|
|
1342
|
+
|
|
1343
|
+
### Choice Element Handling
|
|
1344
|
+
|
|
1345
|
+
**Current strategy**: `all-optional` — All choice branches are emitted as optional properties.
|
|
1346
|
+
|
|
1347
|
+
```typescript
|
|
1348
|
+
// WSDL: <xs:choice>
|
|
1349
|
+
interface MyType {
|
|
1350
|
+
optionA?: string;
|
|
1351
|
+
optionB?: number;
|
|
1352
|
+
}
|
|
1353
|
+
```
|
|
1354
|
+
|
|
1355
|
+
**Future**: Discriminated unions for type-safe choice validation.
|
|
1356
|
+
|
|
1357
|
+
### Array Wrapper Flattening
|
|
1358
|
+
|
|
1359
|
+
Single repeated child without attributes collapses to array schema in OpenAPI:
|
|
1360
|
+
|
|
1361
|
+
```xml
|
|
1362
|
+
<xs:complexType name="ArrayOfForecast">
|
|
1363
|
+
<xs:sequence>
|
|
1364
|
+
<xs:element name="Forecast" type="tns:Forecast" maxOccurs="unbounded"/>
|
|
1365
|
+
</xs:sequence>
|
|
1366
|
+
</xs:complexType>
|
|
1367
|
+
```
|
|
1368
|
+
|
|
1369
|
+
**OpenAPI Schema**:
|
|
1370
|
+
|
|
1371
|
+
```json
|
|
1372
|
+
{
|
|
1373
|
+
"ArrayOfForecast": {
|
|
1374
|
+
"type": "array",
|
|
1375
|
+
"items": { "$ref": "#/components/schemas/Forecast" }
|
|
1376
|
+
}
|
|
1377
|
+
}
|
|
1378
|
+
```
|
|
1379
|
+
|
|
1380
|
+
### Inheritance Flattening
|
|
1381
|
+
|
|
1382
|
+
**Extension (`xs:extension`)**:
|
|
1383
|
+
- Base properties merged into derived type
|
|
1384
|
+
- TypeScript: `extends` when possible
|
|
1385
|
+
|
|
1386
|
+
**Restriction (`xs:restriction`)**:
|
|
1387
|
+
- Treated as base type with constraints
|
|
1388
|
+
|
|
1389
|
+
**SimpleContent**:
|
|
1390
|
+
- Base value collapsed into `$value` property
|
|
1391
|
+
- Attributes remain as peer properties
|
|
1392
|
+
|
|
1393
|
+
### Validation
|
|
1394
|
+
|
|
1395
|
+
OpenAPI validation uses `@apidevtools/swagger-parser`:
|
|
1396
|
+
- Validates schema structure
|
|
1397
|
+
- Resolves all `$ref` references
|
|
1398
|
+
- Catches missing schemas
|
|
1399
|
+
- Detects circular dependencies
|
|
1400
|
+
|
|
1401
|
+
Disable with `--openapi-validate false` or `validate: false` in API.
|
|
320
1402
|
|
|
321
1403
|
---
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
|
328
|
-
|
|
329
|
-
|
|
|
330
|
-
|
|
|
331
|
-
|
|
332
|
-
|
|
1404
|
+
|
|
1405
|
+
## 14. Troubleshooting
|
|
1406
|
+
|
|
1407
|
+
### Common Issues
|
|
1408
|
+
|
|
1409
|
+
| Symptom | Resolution |
|
|
1410
|
+
|-----------------------------------|---------------------------------------------------------------------------------------------------------------------------|
|
|
1411
|
+
| **WSDL fetch fails** | Curl the URL, check TLS/proxy settings, retry with local copy |
|
|
1412
|
+
| **Unresolved type references** | Re-run with `--client-fail-on-unresolved=false` to inspect partial graph |
|
|
1413
|
+
| **Missing schema in OpenAPI** | Ensure the global element exists (catalog shows compiled symbols) |
|
|
1414
|
+
| **Wrong array modeling** | Check `maxOccurs` in WSDL; tool only arrays when `maxOccurs>1` or `unbounded` |
|
|
1415
|
+
| **Authentication errors** | Provide proper `soap.ISecurity` instance (`WSSecurity`, `BasicAuthSecurity`) |
|
|
1416
|
+
| **Date/time confusion** | Use `--client-date-as Date` for runtime Date objects |
|
|
1417
|
+
| **TypeScript compilation errors** | Check `--import-extensions` matches your tsconfig `moduleResolution` |
|
|
1418
|
+
| **Gateway validation failures** | Ensure OpenAPI has valid `$ref` paths and all schemas in `components.schemas` |
|
|
1419
|
+
| **Catalog file not found** | Catalog defaults to output directory (e.g., `{client-dir}/catalog.json`); use `--catalog-file` to specify custom location |
|
|
1420
|
+
|
|
1421
|
+
### Enable SOAP Wire Logging
|
|
1422
|
+
|
|
1423
|
+
Debug SOAP requests/responses:
|
|
1424
|
+
|
|
333
1425
|
```bash
|
|
334
1426
|
NODE_DEBUG=soap node app.js
|
|
335
1427
|
```
|
|
336
1428
|
|
|
1429
|
+
### Verify Installation
|
|
1430
|
+
|
|
1431
|
+
```bash
|
|
1432
|
+
npx wsdl-tsc --help
|
|
1433
|
+
npm run smoke:compile # Test catalog generation
|
|
1434
|
+
npm run smoke:client # Test client generation
|
|
1435
|
+
npm run smoke:openapi # Test OpenAPI generation
|
|
1436
|
+
npm run smoke:gateway # Test gateway generation
|
|
1437
|
+
npm run smoke:pipeline # Test complete pipeline
|
|
1438
|
+
```
|
|
1439
|
+
|
|
1440
|
+
### TypeScript Configuration
|
|
1441
|
+
|
|
1442
|
+
Ensure your `tsconfig.json` is compatible:
|
|
1443
|
+
|
|
1444
|
+
```json
|
|
1445
|
+
{
|
|
1446
|
+
"compilerOptions": {
|
|
1447
|
+
"target": "ES2022",
|
|
1448
|
+
"module": "NodeNext",
|
|
1449
|
+
"moduleResolution": "NodeNext",
|
|
1450
|
+
"strict": true,
|
|
1451
|
+
"esModuleInterop": true,
|
|
1452
|
+
"skipLibCheck": true
|
|
1453
|
+
}
|
|
1454
|
+
}
|
|
1455
|
+
```
|
|
1456
|
+
|
|
1457
|
+
### Catalog Inspection
|
|
1458
|
+
|
|
1459
|
+
Examine the compiled catalog to understand type resolution:
|
|
1460
|
+
|
|
1461
|
+
```bash
|
|
1462
|
+
# Compile to specific location
|
|
1463
|
+
npx wsdl-tsc compile \
|
|
1464
|
+
--wsdl-source ./wsdl/Hotel.wsdl \
|
|
1465
|
+
--catalog-file build/hotel-catalog.json
|
|
1466
|
+
|
|
1467
|
+
# Inspect types, operations, and metadata
|
|
1468
|
+
cat build/hotel-catalog.json | jq '.types'
|
|
1469
|
+
cat build/hotel-catalog.json | jq '.operations'
|
|
1470
|
+
```
|
|
1471
|
+
|
|
1472
|
+
Or inspect catalog from client generation:
|
|
1473
|
+
|
|
1474
|
+
```bash
|
|
1475
|
+
npx wsdl-tsc client \
|
|
1476
|
+
--wsdl-source ./wsdl/Hotel.wsdl \
|
|
1477
|
+
--client-dir ./src/services/hotel
|
|
1478
|
+
|
|
1479
|
+
cat ./src/services/hotel/catalog.json | jq '.types'
|
|
1480
|
+
```
|
|
1481
|
+
|
|
1482
|
+
The catalog is automatically placed at `./src/services/hotel/catalog.json`.
|
|
1483
|
+
|
|
337
1484
|
---
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
1485
|
+
|
|
1486
|
+
## 15. Contributing
|
|
1487
|
+
|
|
1488
|
+
We welcome contributions! Here's how to get started:
|
|
1489
|
+
|
|
1490
|
+
### Development Setup
|
|
1491
|
+
|
|
1492
|
+
```bash
|
|
1493
|
+
# Clone repository
|
|
1494
|
+
git clone https://github.com/techspokes/typescript-wsdl-client.git
|
|
1495
|
+
cd typescript-wsdl-client
|
|
1496
|
+
|
|
1497
|
+
# Install dependencies
|
|
1498
|
+
npm install
|
|
1499
|
+
|
|
1500
|
+
# Build
|
|
1501
|
+
npm run build
|
|
1502
|
+
|
|
1503
|
+
# Type check
|
|
1504
|
+
npm run typecheck
|
|
1505
|
+
|
|
1506
|
+
# Run smoke tests
|
|
1507
|
+
npm run smoke:compile
|
|
1508
|
+
npm run smoke:client
|
|
1509
|
+
npm run smoke:openapi
|
|
1510
|
+
npm run smoke:gateway
|
|
1511
|
+
npm run smoke:pipeline
|
|
1512
|
+
|
|
1513
|
+
# Run full CI suite
|
|
1514
|
+
npm run ci
|
|
1515
|
+
```
|
|
1516
|
+
|
|
1517
|
+
### Making Changes
|
|
1518
|
+
|
|
1519
|
+
1. **Fork & branch** — Create a feature branch from `main`
|
|
1520
|
+
2. **Make changes** — Implement your feature or fix
|
|
1521
|
+
3. **Test** — Run smoke tests and verify functionality
|
|
1522
|
+
4. **Update CHANGELOG** — Add entry under `## [Unreleased]` section
|
|
1523
|
+
5. **Commit** — Use conventional commit format: `feat:`, `fix:`, `docs:`, etc.
|
|
1524
|
+
6. **Submit PR** — Create pull request with clear description
|
|
1525
|
+
|
|
1526
|
+
### Commit Message Format
|
|
1527
|
+
|
|
1528
|
+
```
|
|
1529
|
+
Version: <version> <type>(<optional-scope>): <imperative summary>
|
|
1530
|
+
|
|
1531
|
+
[optional body with details, rationale, breaking changes]
|
|
1532
|
+
|
|
1533
|
+
[optional footer with refs: Closes #123]
|
|
1534
|
+
```
|
|
1535
|
+
|
|
1536
|
+
**Types**: `feat`, `fix`, `docs`, `refactor`, `test`, `chore`
|
|
1537
|
+
|
|
1538
|
+
**Example**:
|
|
1539
|
+
```
|
|
1540
|
+
Version: 0.8.0 feat(gateway): add support for YAML OpenAPI input
|
|
1541
|
+
|
|
1542
|
+
Gateway command now accepts both JSON and YAML OpenAPI files,
|
|
1543
|
+
determined by file extension (.json, .yaml, .yml).
|
|
1544
|
+
|
|
1545
|
+
Closes #456
|
|
1546
|
+
```
|
|
1547
|
+
|
|
1548
|
+
### Guidelines
|
|
1549
|
+
|
|
1550
|
+
- Follow existing code style and conventions
|
|
1551
|
+
- Keep PRs focused and scoped
|
|
1552
|
+
- Update documentation for user-visible changes
|
|
1553
|
+
- Add tests where applicable
|
|
1554
|
+
- Ensure CI passes
|
|
1555
|
+
|
|
1556
|
+
See also: [CONTRIBUTING.md](CONTRIBUTING.md), [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md)
|
|
344
1557
|
|
|
345
1558
|
---
|
|
346
|
-
## 13. Contributing
|
|
347
|
-
1. Fork & branch.
|
|
348
|
-
2. `npm i && npm run build`.
|
|
349
|
-
3. Use `npm run smoke:gen`, `npm run smoke:pipeline`.
|
|
350
|
-
- Pipeline smoke validates envelope, ordering & validation.
|
|
351
|
-
4. Add a bullet under **Unreleased** in `CHANGELOG.md`.
|
|
352
1559
|
|
|
353
|
-
|
|
1560
|
+
## 16. License
|
|
1561
|
+
|
|
1562
|
+
MIT © TechSpokes
|
|
1563
|
+
|
|
1564
|
+
Generated artifacts are fully yours with no restrictions or attribution required.
|
|
1565
|
+
|
|
1566
|
+
See [LICENSE](LICENSE) for full text.
|
|
354
1567
|
|
|
355
1568
|
---
|
|
356
|
-
|
|
357
|
-
|
|
1569
|
+
|
|
1570
|
+
## 17. Sponsors
|
|
1571
|
+
|
|
1572
|
+
Support ongoing development and maintenance:
|
|
1573
|
+
|
|
1574
|
+
**GitHub Sponsors**: https://github.com/sponsors/TechSpokes
|
|
1575
|
+
|
|
1576
|
+
### Current Sponsors
|
|
1577
|
+
|
|
1578
|
+
*Your organization could be featured here!*
|
|
1579
|
+
|
|
1580
|
+
### Why Sponsor?
|
|
1581
|
+
|
|
1582
|
+
- Priority support for issues and feature requests
|
|
1583
|
+
- Early access to new features
|
|
1584
|
+
- Recognition in README and release notes
|
|
1585
|
+
- Direct influence on roadmap priorities
|
|
1586
|
+
- Support open source sustainability
|
|
1587
|
+
|
|
1588
|
+
Thank you for considering sponsorship!
|
|
358
1589
|
|
|
359
1590
|
---
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
1591
|
+
|
|
1592
|
+
## Links
|
|
1593
|
+
|
|
1594
|
+
- **Documentation**: [README.md](README.md) (you are here)
|
|
1595
|
+
- **Contributing Guide**: [CONTRIBUTING.md](CONTRIBUTING.md)
|
|
1596
|
+
- **Roadmap**: [ROADMAP.md](ROADMAP.md)
|
|
1597
|
+
- **Changelog**: [CHANGELOG.md](CHANGELOG.md)
|
|
1598
|
+
- **Security Policy**: [SECURITY.md](SECURITY.md)
|
|
1599
|
+
- **Support**: [SUPPORT.md](SUPPORT.md)
|
|
1600
|
+
- **Issues**: https://github.com/techspokes/typescript-wsdl-client/issues
|
|
1601
|
+
- **Discussions**: https://github.com/techspokes/typescript-wsdl-client/discussions
|
|
1602
|
+
- **npm Package**: https://www.npmjs.com/package/@techspokes/typescript-wsdl-client
|
|
1603
|
+
|