@cli-forge/parser 0.10.1 → 0.12.0
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.md +5 -0
- package/README.md +202 -6
- package/dist/index.js.map +1 -0
- package/dist/lib/config-files/configuration-loader.js.map +1 -0
- package/dist/lib/config-files/index.d.ts +3 -0
- package/dist/lib/config-files/index.js +7 -0
- package/dist/lib/config-files/index.js.map +1 -0
- package/{src → dist}/lib/config-files/json-file-loader.d.ts +1 -1
- package/{src → dist}/lib/config-files/json-file-loader.js +2 -2
- package/dist/lib/config-files/json-file-loader.js.map +1 -0
- package/{src → dist}/lib/config-files/package-json-loader.d.ts +1 -1
- package/{src → dist}/lib/config-files/package-json-loader.js +2 -2
- package/dist/lib/config-files/package-json-loader.js.map +1 -0
- package/dist/lib/config-files/utils.js.map +1 -0
- package/dist/lib/helpers.js.map +1 -0
- package/dist/lib/option-types/array.js.map +1 -0
- package/dist/lib/option-types/boolean.js.map +1 -0
- package/{src → dist}/lib/option-types/common.d.ts +1 -1
- package/dist/lib/option-types/common.js.map +1 -0
- package/dist/lib/option-types/index.d.ts +15 -0
- package/{src → dist}/lib/option-types/index.js +1 -0
- package/dist/lib/option-types/index.js.map +1 -0
- package/dist/lib/option-types/number.js.map +1 -0
- package/dist/lib/option-types/object.d.ts +75 -0
- package/dist/lib/option-types/object.js.map +1 -0
- package/dist/lib/option-types/option-config-to-type.d.ts +9 -0
- package/dist/lib/option-types/option-config-to-type.js.map +1 -0
- package/dist/lib/option-types/option-config.d.ts +24 -0
- package/dist/lib/option-types/option-config.js.map +1 -0
- package/dist/lib/option-types/string.js.map +1 -0
- package/dist/lib/option-types/type-resolution.d.ts +132 -0
- package/dist/lib/option-types/type-resolution.js +7 -0
- package/dist/lib/option-types/type-resolution.js.map +1 -0
- package/dist/lib/parser.d.ts +218 -0
- package/{src → dist}/lib/parser.js +84 -13
- package/dist/lib/parser.js.map +1 -0
- package/dist/lib/parsers/array.js.map +1 -0
- package/dist/lib/parsers/boolean.js.map +1 -0
- package/dist/lib/parsers/number.js.map +1 -0
- package/{src → dist}/lib/parsers/object.d.ts +1 -1
- package/{src → dist}/lib/parsers/object.js +22 -1
- package/dist/lib/parsers/object.js.map +1 -0
- package/dist/lib/parsers/parser-map.js.map +1 -0
- package/dist/lib/parsers/string.js.map +1 -0
- package/dist/lib/parsers/typings.d.ts +11 -0
- package/dist/lib/parsers/typings.js.map +1 -0
- package/dist/lib/utils/case-transformations.js.map +1 -0
- package/dist/lib/utils/chain.d.ts +331 -0
- package/dist/lib/utils/chain.js.map +1 -0
- package/dist/lib/utils/flags.js.map +1 -0
- package/dist/lib/utils/get-configured-key.d.ts +3 -0
- package/dist/lib/utils/get-configured-key.js.map +1 -0
- package/dist/lib/utils/read-default-value.d.ts +2 -0
- package/{src → dist}/lib/utils/read-default-value.js +2 -0
- package/dist/lib/utils/read-default-value.js.map +1 -0
- package/package.json +18 -6
- package/src/lib/config-files/README.md +10 -0
- package/src/index.js.map +0 -1
- package/src/lib/config-files/configuration-loader.js.map +0 -1
- package/src/lib/config-files/index.d.ts +0 -3
- package/src/lib/config-files/index.js +0 -7
- package/src/lib/config-files/index.js.map +0 -1
- package/src/lib/config-files/json-file-loader.js.map +0 -1
- package/src/lib/config-files/package-json-loader.js.map +0 -1
- package/src/lib/config-files/utils.js.map +0 -1
- package/src/lib/helpers.js.map +0 -1
- package/src/lib/option-types/array.js.map +0 -1
- package/src/lib/option-types/boolean.js.map +0 -1
- package/src/lib/option-types/common.js.map +0 -1
- package/src/lib/option-types/index.d.ts +0 -14
- package/src/lib/option-types/index.js.map +0 -1
- package/src/lib/option-types/number.js.map +0 -1
- package/src/lib/option-types/object.d.ts +0 -10
- package/src/lib/option-types/object.js.map +0 -1
- package/src/lib/option-types/option-config-to-type.d.ts +0 -26
- package/src/lib/option-types/option-config-to-type.js.map +0 -1
- package/src/lib/option-types/option-config.d.ts +0 -15
- package/src/lib/option-types/option-config.js.map +0 -1
- package/src/lib/option-types/string.js.map +0 -1
- package/src/lib/parser.d.ts +0 -269
- package/src/lib/parser.js.map +0 -1
- package/src/lib/parsers/array.js.map +0 -1
- package/src/lib/parsers/boolean.js.map +0 -1
- package/src/lib/parsers/number.js.map +0 -1
- package/src/lib/parsers/object.js.map +0 -1
- package/src/lib/parsers/parser-map.js.map +0 -1
- package/src/lib/parsers/string.js.map +0 -1
- package/src/lib/parsers/typings.d.ts +0 -11
- package/src/lib/parsers/typings.js.map +0 -1
- package/src/lib/utils/case-transformations.js.map +0 -1
- package/src/lib/utils/chain.d.ts +0 -397
- package/src/lib/utils/chain.js.map +0 -1
- package/src/lib/utils/flags.js.map +0 -1
- package/src/lib/utils/get-configured-key.d.ts +0 -3
- package/src/lib/utils/get-configured-key.js.map +0 -1
- package/src/lib/utils/read-default-value.d.ts +0 -2
- package/src/lib/utils/read-default-value.js.map +0 -1
- /package/{src → dist}/index.d.ts +0 -0
- /package/{src → dist}/index.js +0 -0
- /package/{src → dist}/lib/config-files/configuration-loader.d.ts +0 -0
- /package/{src → dist}/lib/config-files/configuration-loader.js +0 -0
- /package/{src → dist}/lib/config-files/utils.d.ts +0 -0
- /package/{src → dist}/lib/config-files/utils.js +0 -0
- /package/{src → dist}/lib/helpers.d.ts +0 -0
- /package/{src → dist}/lib/helpers.js +0 -0
- /package/{src → dist}/lib/option-types/array.d.ts +0 -0
- /package/{src → dist}/lib/option-types/array.js +0 -0
- /package/{src → dist}/lib/option-types/boolean.d.ts +0 -0
- /package/{src → dist}/lib/option-types/boolean.js +0 -0
- /package/{src → dist}/lib/option-types/common.js +0 -0
- /package/{src → dist}/lib/option-types/number.d.ts +0 -0
- /package/{src → dist}/lib/option-types/number.js +0 -0
- /package/{src → dist}/lib/option-types/object.js +0 -0
- /package/{src → dist}/lib/option-types/option-config-to-type.js +0 -0
- /package/{src → dist}/lib/option-types/option-config.js +0 -0
- /package/{src → dist}/lib/option-types/string.d.ts +0 -0
- /package/{src → dist}/lib/option-types/string.js +0 -0
- /package/{src → dist}/lib/parsers/array.d.ts +0 -0
- /package/{src → dist}/lib/parsers/array.js +0 -0
- /package/{src → dist}/lib/parsers/boolean.d.ts +0 -0
- /package/{src → dist}/lib/parsers/boolean.js +0 -0
- /package/{src → dist}/lib/parsers/number.d.ts +0 -0
- /package/{src → dist}/lib/parsers/number.js +0 -0
- /package/{src → dist}/lib/parsers/parser-map.d.ts +0 -0
- /package/{src → dist}/lib/parsers/parser-map.js +0 -0
- /package/{src → dist}/lib/parsers/string.d.ts +0 -0
- /package/{src → dist}/lib/parsers/string.js +0 -0
- /package/{src → dist}/lib/parsers/typings.js +0 -0
- /package/{src → dist}/lib/utils/case-transformations.d.ts +0 -0
- /package/{src → dist}/lib/utils/case-transformations.js +0 -0
- /package/{src → dist}/lib/utils/chain.js +0 -0
- /package/{src → dist}/lib/utils/flags.d.ts +0 -0
- /package/{src → dist}/lib/utils/flags.js +0 -0
- /package/{src → dist}/lib/utils/get-configured-key.js +0 -0
package/LICENSE.md
ADDED
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
Copyright 2024 Craigory Coppola
|
|
2
|
+
|
|
3
|
+
Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted, provided that the above copyright notice and this permission notice appear in all copies.
|
|
4
|
+
|
|
5
|
+
THE SOFTWARE IS PROVIDED “AS IS” AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
package/README.md
CHANGED
|
@@ -1,11 +1,207 @@
|
|
|
1
|
-
# parser
|
|
1
|
+
# @cli-forge/parser
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
**A type-safe argument parser for Node.js with full TypeScript inference.**
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
This is the low-level parsing engine that powers [cli-forge](https://www.npmjs.com/package/cli-forge). Use this package directly if you need fine-grained control over argument parsing without the higher-level command management features.
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
## Installation
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
```bash
|
|
10
|
+
npm install @cli-forge/parser
|
|
11
|
+
```
|
|
10
12
|
|
|
11
|
-
|
|
13
|
+
## Quick Start
|
|
14
|
+
|
|
15
|
+
```typescript
|
|
16
|
+
import { parser } from '@cli-forge/parser';
|
|
17
|
+
|
|
18
|
+
const args = parser()
|
|
19
|
+
.option('name', { type: 'string', required: true })
|
|
20
|
+
.option('port', { type: 'number', default: 3000 })
|
|
21
|
+
.option('verbose', { type: 'boolean', alias: ['v'] })
|
|
22
|
+
.parse(['--name', 'my-app', '--port', '8080', '-v']);
|
|
23
|
+
|
|
24
|
+
// args is fully typed:
|
|
25
|
+
// { name: string; port: number; verbose: boolean }
|
|
26
|
+
console.log(args.name); // 'my-app'
|
|
27
|
+
console.log(args.port); // 8080
|
|
28
|
+
console.log(args.verbose); // true
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
## Features
|
|
32
|
+
|
|
33
|
+
- **Full TypeScript inference** - Types accumulate as you chain `.option()` calls
|
|
34
|
+
- **Multiple option types** - `string`, `number`, `boolean`, `array`, `object`
|
|
35
|
+
- **Value sources** - CLI args, environment variables, config files, defaults
|
|
36
|
+
- **Validation** - `choices`, `validate`, `required`, `conflicts`, `implies`
|
|
37
|
+
- **Config file support** - JSON/YAML with inheritance via `extends`
|
|
38
|
+
- **Coercion** - Transform values during parsing
|
|
39
|
+
|
|
40
|
+
## Option Types
|
|
41
|
+
|
|
42
|
+
### String
|
|
43
|
+
|
|
44
|
+
```typescript
|
|
45
|
+
parser().option('name', {
|
|
46
|
+
type: 'string',
|
|
47
|
+
description: 'User name',
|
|
48
|
+
default: 'anonymous',
|
|
49
|
+
});
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
### Number
|
|
53
|
+
|
|
54
|
+
```typescript
|
|
55
|
+
parser().option('port', {
|
|
56
|
+
type: 'number',
|
|
57
|
+
description: 'Port number',
|
|
58
|
+
default: 3000,
|
|
59
|
+
});
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
### Boolean
|
|
63
|
+
|
|
64
|
+
```typescript
|
|
65
|
+
parser().option('verbose', {
|
|
66
|
+
type: 'boolean',
|
|
67
|
+
alias: ['v'],
|
|
68
|
+
description: 'Enable verbose output',
|
|
69
|
+
});
|
|
70
|
+
// Supports: --verbose, --verbose true, --no-verbose
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
### Array
|
|
74
|
+
|
|
75
|
+
```typescript
|
|
76
|
+
parser().option('files', {
|
|
77
|
+
type: 'array',
|
|
78
|
+
items: 'string',
|
|
79
|
+
description: 'Input files',
|
|
80
|
+
});
|
|
81
|
+
// Supports: --files a b c, --files a,b,c, --files a --files b
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
### Object
|
|
85
|
+
|
|
86
|
+
```typescript
|
|
87
|
+
parser().option('config', {
|
|
88
|
+
type: 'object',
|
|
89
|
+
properties: {
|
|
90
|
+
host: { type: 'string', default: 'localhost' },
|
|
91
|
+
port: { type: 'number', required: true },
|
|
92
|
+
ssl: { type: 'boolean' },
|
|
93
|
+
},
|
|
94
|
+
});
|
|
95
|
+
// Supports: --config.host example.com --config.port 443 --config.ssl
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
## Positional Arguments
|
|
99
|
+
|
|
100
|
+
```typescript
|
|
101
|
+
parser()
|
|
102
|
+
.positional('input', { type: 'string', required: true })
|
|
103
|
+
.positional('output', { type: 'string' })
|
|
104
|
+
.parse(['input.txt', 'output.txt']);
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
## Validation
|
|
108
|
+
|
|
109
|
+
### Choices
|
|
110
|
+
|
|
111
|
+
```typescript
|
|
112
|
+
parser().option('level', {
|
|
113
|
+
type: 'string',
|
|
114
|
+
choices: ['debug', 'info', 'warn', 'error'],
|
|
115
|
+
});
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
### Custom Validation
|
|
119
|
+
|
|
120
|
+
```typescript
|
|
121
|
+
parser().option('port', {
|
|
122
|
+
type: 'number',
|
|
123
|
+
validate: (value) => {
|
|
124
|
+
if (value < 1 || value > 65535) {
|
|
125
|
+
throw new Error('Port must be between 1 and 65535');
|
|
126
|
+
}
|
|
127
|
+
return true;
|
|
128
|
+
},
|
|
129
|
+
});
|
|
130
|
+
```
|
|
131
|
+
|
|
132
|
+
### Conflicts and Implies
|
|
133
|
+
|
|
134
|
+
```typescript
|
|
135
|
+
parser()
|
|
136
|
+
.option('quiet', { type: 'boolean' })
|
|
137
|
+
.option('verbose', {
|
|
138
|
+
type: 'boolean',
|
|
139
|
+
conflicts: ['quiet'],
|
|
140
|
+
})
|
|
141
|
+
.option('output', {
|
|
142
|
+
type: 'string',
|
|
143
|
+
implies: { format: 'json' },
|
|
144
|
+
});
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
## Environment Variables
|
|
148
|
+
|
|
149
|
+
```typescript
|
|
150
|
+
parser().option('apiKey', {
|
|
151
|
+
type: 'string',
|
|
152
|
+
env: 'API_KEY',
|
|
153
|
+
});
|
|
154
|
+
// Will read from process.env.API_KEY if --apiKey not provided
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
## Configuration Files
|
|
158
|
+
|
|
159
|
+
```typescript
|
|
160
|
+
parser()
|
|
161
|
+
.configFile('myapp.config.json')
|
|
162
|
+
.option('port', { type: 'number' })
|
|
163
|
+
.parse([]);
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
Config files support inheritance:
|
|
167
|
+
|
|
168
|
+
```json
|
|
169
|
+
{
|
|
170
|
+
"extends": "./base-config.json",
|
|
171
|
+
"port": 8080
|
|
172
|
+
}
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
## Coercion
|
|
176
|
+
|
|
177
|
+
Transform values during parsing:
|
|
178
|
+
|
|
179
|
+
```typescript
|
|
180
|
+
parser().option('date', {
|
|
181
|
+
type: 'string',
|
|
182
|
+
coerce: (value) => new Date(value),
|
|
183
|
+
});
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
## Type Inference
|
|
187
|
+
|
|
188
|
+
The parser tracks types as options are added:
|
|
189
|
+
|
|
190
|
+
```typescript
|
|
191
|
+
const p = parser()
|
|
192
|
+
.option('name', { type: 'string' }) // { name?: string }
|
|
193
|
+
.option('port', { type: 'number' }) // { name?: string; port?: number }
|
|
194
|
+
.option('required', { type: 'string', required: true }); // { name?: string; port?: number; required: string }
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
## Related Packages
|
|
198
|
+
|
|
199
|
+
- [`cli-forge`](https://www.npmjs.com/package/cli-forge) - High-level CLI builder with commands, middleware, and documentation generation
|
|
200
|
+
|
|
201
|
+
## Documentation
|
|
202
|
+
|
|
203
|
+
Full documentation available at: https://craigory.dev/cli-forge/
|
|
204
|
+
|
|
205
|
+
## License
|
|
206
|
+
|
|
207
|
+
ISC
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;AAAA,uDAA6B;AAC7B,2EAAiD;AACjD,wDAA8B;AAC9B,6DAAmC;AACnC,yEAA+C;AAC/C,4DAAkC;AAElC;;GAEG;AACH,iFAAyD"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"configuration-loader.js","sourceRoot":"","sources":["../../../src/lib/config-files/configuration-loader.ts"],"names":[],"mappings":";;AAwBA,oDAgCC;AAxDD,+BAA4B;AAsB5B,iFAAiF;AACjF,yEAAyE;AACzE,SAAgB,oBAAoB,CAClC,iBAAyB,EACzB,OAAmC;IAEnC,SAAS,iBAAiB,CACxB,QAAgB,EAChB,QAAkC;QAElC,MAAM,MAAM,GAAG,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACvC,IAAI,MAAM,CAAC,OAAO,EAAE,CAAC;YACnB,MAAM,QAAQ,GAAG,oBAAoB,CACnC,MAAM,CAAC,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC;gBAC5B,CAAC,CAAC,IAAA,WAAI,EAAC,iBAAiB,EAAE,MAAM,CAAC,OAAO,CAAC;gBACzC,CAAC,CAAC,MAAM,CAAC,OAAO,EAClB,OAAO,CACR,CAAC;YACF,OAAO,EAAE,GAAG,QAAQ,EAAE,GAAG,MAAM,EAAE,CAAC;QACpC,CAAC;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,IAAI,QAAQ,GAAM,EAAO,CAAC;IAC1B,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;QAC7B,MAAM,QAAQ,GAAG,MAAM,CAAC,OAAO,CAAC,iBAAiB,CAAC,CAAC;QACnD,IAAI,QAAQ,EAAE,CAAC;YACb,QAAQ,GAAG;gBACT,GAAG,iBAAiB,CAAC,QAAQ,EAAE,MAAM,CAAC;gBACtC,GAAG,QAAQ;aACZ,CAAC;QACJ,CAAC;IACH,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const tslib_1 = require("tslib");
|
|
4
|
+
tslib_1.__exportStar(require("./configuration-loader.js"), exports);
|
|
5
|
+
tslib_1.__exportStar(require("./json-file-loader.js"), exports);
|
|
6
|
+
tslib_1.__exportStar(require("./package-json-loader.js"), exports);
|
|
7
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/config-files/index.ts"],"names":[],"mappings":";;;AAAA,oEAA0C;AAC1C,gEAAsC;AACtC,mEAAyC"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ConfigurationProvider } from './configuration-loader';
|
|
1
|
+
import { ConfigurationProvider } from './configuration-loader.js';
|
|
2
2
|
/**
|
|
3
3
|
* A factory function to create simple configuration providers that load configuration from a JSON file.
|
|
4
4
|
* @param filename The filename of the JSON file to load.
|
|
@@ -3,7 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.getJsonFileConfigLoader = getJsonFileConfigLoader;
|
|
4
4
|
const fs_1 = require("fs");
|
|
5
5
|
const util_1 = require("util");
|
|
6
|
-
const
|
|
6
|
+
const utils_js_1 = require("./utils.js");
|
|
7
7
|
/**
|
|
8
8
|
* A factory function to create simple configuration providers that load configuration from a JSON file.
|
|
9
9
|
* @param filename The filename of the JSON file to load.
|
|
@@ -17,7 +17,7 @@ function getJsonFileConfigLoader(filename, transform) {
|
|
|
17
17
|
class JsonFileConfigLoader {
|
|
18
18
|
seen = new Set();
|
|
19
19
|
resolve(configurationRoot) {
|
|
20
|
-
const nearestFile = (0,
|
|
20
|
+
const nearestFile = (0, utils_js_1.traverseForFile)(filename, configurationRoot);
|
|
21
21
|
if (!nearestFile || !nearestFile.endsWith('.json')) {
|
|
22
22
|
return undefined;
|
|
23
23
|
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"json-file-loader.js","sourceRoot":"","sources":["../../../src/lib/config-files/json-file-loader.ts"],"names":[],"mappings":";;AAYA,0DAuCC;AAnDD,2BAAkC;AAClC,+BAA+B;AAG/B,yCAA6C;AAE7C;;;;;GAKG;AACH,SAAgB,uBAAuB,CACrC,QAAgB,EAChB,SAA4B;IAE5B,SAAS,YAAY,CAAC,QAAgB;QACpC,OAAO,IAAI,CAAC,KAAK,CAAC,IAAA,iBAAY,EAAC,QAAQ,EAAE,OAAO,CAAC,CAAC,CAAC;IACrD,CAAC;IAED,MAAM,oBAAoB;QAChB,IAAI,GAAG,IAAI,GAAG,EAAU,CAAC;QAEjC,OAAO,CAAC,iBAAyB;YAC/B,MAAM,WAAW,GAAG,IAAA,0BAAe,EAAC,QAAQ,EAAE,iBAAiB,CAAC,CAAC;YACjE,IAAI,CAAC,WAAW,IAAI,CAAC,WAAW,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC;gBACnD,OAAO,SAAS,CAAC;YACnB,CAAC;YACD,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,WAAW,CAAC,EAAE,CAAC;gBAC/B,MAAM,IAAI,KAAK,CACb,sDAAsD,WAAW,sHAAsH,CACxL,CAAC;YACJ,CAAC;YACD,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;YAC3B,OAAO,WAAW,CAAC;QACrB,CAAC;QAED,IAAI,CAAC,QAAgB;YACnB,MAAM,IAAI,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;YACpC,IAAI,SAAS,EAAE,CAAC;gBACd,OAAO,SAAS,CAAC,IAAI,CAAC,CAAC;YACzB,CAAC;YACD,OAAO,IAAI,CAAC;QACd,CAAC;QAED,CAAC,cAAO,CAAC,MAAM,CAAC;YACd,OAAO,wBAAwB,GAAG,QAAQ,CAAC;QAC7C,CAAC;KACF;IAED,OAAO,IAAI,oBAAoB,EAAE,CAAC;AACpC,CAAC"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ConfigurationProvider } from './configuration-loader';
|
|
1
|
+
import { ConfigurationProvider } from './configuration-loader.js';
|
|
2
2
|
/**
|
|
3
3
|
* A factory function to create a configuration provider that loads configuration from a package.json file.
|
|
4
4
|
* @param key The key in the package.json file to load as configuration.
|
|
@@ -2,14 +2,14 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.getPackageJsonConfigurationLoader = getPackageJsonConfigurationLoader;
|
|
4
4
|
const node_util_1 = require("node:util");
|
|
5
|
-
const
|
|
5
|
+
const json_file_loader_js_1 = require("./json-file-loader.js");
|
|
6
6
|
/**
|
|
7
7
|
* A factory function to create a configuration provider that loads configuration from a package.json file.
|
|
8
8
|
* @param key The key in the package.json file to load as configuration.
|
|
9
9
|
* @returns A `{@link ConfigurationProvider}` that loads configuration from the specified package.json file.
|
|
10
10
|
*/
|
|
11
11
|
function getPackageJsonConfigurationLoader(key) {
|
|
12
|
-
const loader = (0,
|
|
12
|
+
const loader = (0, json_file_loader_js_1.getJsonFileConfigLoader)('package.json', (json) => json[key]);
|
|
13
13
|
loader[node_util_1.inspect.custom] = () => 'PackageJsonConfigurationLoader: ' + key;
|
|
14
14
|
return loader;
|
|
15
15
|
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"package-json-loader.js","sourceRoot":"","sources":["../../../src/lib/config-files/package-json-loader.ts"],"names":[],"mappings":";;AAUA,8EAUC;AApBD,yCAAoC;AAGpC,+DAAgE;AAEhE;;;;GAIG;AACH,SAAgB,iCAAiC,CAC/C,GAAW;IAEX,MAAM,MAAM,GAAG,IAAA,6CAAuB,EACpC,cAAc,EACd,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CACpB,CAAC;IACD,MAAc,CAAC,mBAAO,CAAC,MAAM,CAAC,GAAG,GAAG,EAAE,CACrC,kCAAkC,GAAG,GAAG,CAAC;IAC3C,OAAO,MAAM,CAAC;AAChB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.js","sourceRoot":"","sources":["../../../src/lib/config-files/utils.ts"],"names":[],"mappings":";;AAGA,0CAiBC;AApBD,qCAAqC;AACrC,yCAA0C;AAE1C,SAAgB,eAAe,CAC7B,cAAsB,EACtB,SAAS,GAAG,OAAO,CAAC,GAAG,EAAE;IAEzB,4CAA4C;IAC5C,IAAI,IAAwB,CAAC;IAC7B,IAAI,OAAO,GAAG,SAAS,CAAC;IACxB,OAAO,IAAI,KAAK,OAAO,EAAE,CAAC;QACxB,IAAI,GAAG,OAAO,CAAC;QACf,MAAM,QAAQ,GAAG,IAAA,gBAAI,EAAC,OAAO,EAAE,cAAc,CAAC,CAAC;QAC/C,IAAI,IAAA,oBAAU,EAAC,QAAQ,CAAC,EAAE,CAAC;YACzB,OAAO,QAAQ,CAAC;QAClB,CAAC;aAAM,CAAC;YACN,OAAO,GAAG,IAAA,mBAAO,EAAC,OAAO,CAAC,CAAC;QAC7B,CAAC;IACH,CAAC;IACD,OAAO,SAAS,CAAC;AACnB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"helpers.js","sourceRoot":"","sources":["../../src/lib/helpers.ts"],"names":[],"mappings":";AAAA,iFAAiF;;AAwBjF,0BAEC;AAED,wBAEC;AA5BD,SAAS,sBAAsB;IAC7B,0DAA0D;IAC1D,qDAAqD;IACrD,IAAI,oBAAoB,EAAE;QAAE,OAAO,CAAC,CAAC;IACrC,mCAAmC;IACnC,0DAA0D;IAC1D,kEAAkE;IAClE,OAAO,CAAC,CAAC;AACX,CAAC;AAED,SAAS,oBAAoB;IAC3B,0FAA0F;IAC1F,oGAAoG;IACpG,OAAO,aAAa,EAAE,IAAI,CAAE,OAA2B,CAAC,UAAU,CAAC;AACrE,CAAC;AAED,SAAS,aAAa;IACpB,oEAAoE;IACpE,0GAA0G;IAC1G,OAAO,CAAC,CAAE,OAA2B,CAAC,QAAQ,CAAC,QAAQ,CAAC;AAC1D,CAAC;AAED,SAAgB,OAAO,CAAC,IAAc;IACpC,OAAO,IAAI,CAAC,KAAK,CAAC,sBAAsB,EAAE,GAAG,CAAC,CAAC,CAAC;AAClD,CAAC;AAED,SAAgB,MAAM,CAAC,IAAc;IACnC,OAAO,IAAI,CAAC,sBAAsB,EAAE,CAAC,CAAC;AACxC,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"array.js","sourceRoot":"","sources":["../../../src/lib/option-types/array.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"boolean.js","sourceRoot":"","sources":["../../../src/lib/option-types/boolean.ts"],"names":[],"mappings":""}
|
|
@@ -26,7 +26,7 @@ export type CommonOptionConfig<T, TCoerce = T, TChoices = T[]> = {
|
|
|
26
26
|
*
|
|
27
27
|
* If the default value is a tuple, the first value will be used as the default value, and the second value will be used as the description.
|
|
28
28
|
*/
|
|
29
|
-
default?: Default<T
|
|
29
|
+
default?: Default<NoInfer<T>>;
|
|
30
30
|
/**
|
|
31
31
|
* Provide a description for the option.
|
|
32
32
|
*/
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.js","sourceRoot":"","sources":["../../../src/lib/option-types/common.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { OptionConfig, UnknownOptionConfig } from './option-config';
|
|
2
|
+
export * from './option-config-to-type';
|
|
3
|
+
export * from './type-resolution';
|
|
4
|
+
export * from './common';
|
|
5
|
+
export * from './array';
|
|
6
|
+
export * from './boolean';
|
|
7
|
+
export * from './number';
|
|
8
|
+
export * from './object';
|
|
9
|
+
export * from './string';
|
|
10
|
+
export type { OptionConfig, UnknownOptionConfig };
|
|
11
|
+
export type Internal<T extends UnknownOptionConfig> = T & InternalOptionConfig;
|
|
12
|
+
export type InternalOptionConfig = UnknownOptionConfig & {
|
|
13
|
+
key: string;
|
|
14
|
+
position?: number;
|
|
15
|
+
};
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
const tslib_1 = require("tslib");
|
|
4
4
|
tslib_1.__exportStar(require("./option-config-to-type"), exports);
|
|
5
|
+
tslib_1.__exportStar(require("./type-resolution"), exports);
|
|
5
6
|
tslib_1.__exportStar(require("./common"), exports);
|
|
6
7
|
tslib_1.__exportStar(require("./array"), exports);
|
|
7
8
|
tslib_1.__exportStar(require("./boolean"), exports);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/option-types/index.ts"],"names":[],"mappings":";;;AAEA,kEAAwC;AACxC,4DAAkC;AAClC,mDAAyB;AACzB,kDAAwB;AACxB,oDAA0B;AAC1B,mDAAyB;AACzB,mDAAyB;AACzB,mDAAyB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"number.js","sourceRoot":"","sources":["../../../src/lib/option-types/number.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
import { CommonOptionConfig, Default } from './common';
|
|
2
|
+
import { ResolveProperties, WithAdditionalProperties } from './type-resolution';
|
|
3
|
+
/**
|
|
4
|
+
* Compute the full value type for an object option.
|
|
5
|
+
* Resolves each property to its final type (respecting optional/required)
|
|
6
|
+
* and adds an index signature if additionalProperties is set.
|
|
7
|
+
*
|
|
8
|
+
* Uses WithAdditionalProperties when additionalProperties is specified,
|
|
9
|
+
* which creates a compatible index signature that doesn't conflict with
|
|
10
|
+
* explicit property types.
|
|
11
|
+
*/
|
|
12
|
+
type ObjectValue<TProperties extends Record<string, {
|
|
13
|
+
type: string;
|
|
14
|
+
}>, TAdditionalProperties extends false | 'string' | 'number' | 'boolean'> = [TAdditionalProperties] extends [false] ? ResolveProperties<TProperties> : WithAdditionalProperties<ResolveProperties<TProperties>, TAdditionalProperties>;
|
|
15
|
+
/**
|
|
16
|
+
* Configuration for object options. Objects are parsed from dot notation
|
|
17
|
+
* or JSON strings.
|
|
18
|
+
*
|
|
19
|
+
* e.g. `--config.host localhost --config.port 3000` or `--config '{"host":"localhost"}'`
|
|
20
|
+
*
|
|
21
|
+
* Note: This type explicitly lists all fields from CommonOptionConfig instead of using
|
|
22
|
+
* Omit<CommonOptionConfig<TValue>, ...> to avoid circular type inference issues.
|
|
23
|
+
* When Omit is used, TypeScript must fully evaluate CommonOptionConfig<TValue> first,
|
|
24
|
+
* which requires computing TValue from TProperties, creating a circular dependency
|
|
25
|
+
* when callbacks reference nested properties.
|
|
26
|
+
*/
|
|
27
|
+
/**
|
|
28
|
+
* Configuration for object options. Objects are parsed from dot notation
|
|
29
|
+
* or JSON strings.
|
|
30
|
+
*
|
|
31
|
+
* e.g. `--config.host localhost --config.port 3000` or `--config '{"host":"localhost"}'`
|
|
32
|
+
*
|
|
33
|
+
* Note: This type explicitly lists all fields from CommonOptionConfig instead of using
|
|
34
|
+
* Omit<CommonOptionConfig<TValue>, ...> to avoid circular type inference issues.
|
|
35
|
+
* When Omit is used, TypeScript must fully evaluate CommonOptionConfig<TValue> first,
|
|
36
|
+
* which requires computing TValue from TProperties, creating a circular dependency
|
|
37
|
+
* when callbacks reference nested properties.
|
|
38
|
+
*/
|
|
39
|
+
/**
|
|
40
|
+
* Compute the validate parameter type for object options.
|
|
41
|
+
* When coerce is provided, validate receives the coerced type (TCoerce).
|
|
42
|
+
* When coerce is not provided, validate receives the computed ObjectValue type.
|
|
43
|
+
*
|
|
44
|
+
* Uses `unknown extends TCoerce` to detect if TCoerce was not explicitly provided,
|
|
45
|
+
* since it defaults to `unknown` when no coerce function is given.
|
|
46
|
+
*/
|
|
47
|
+
type ObjectValidateType<TCoerce, TProperties extends Record<string, {
|
|
48
|
+
type: string;
|
|
49
|
+
}>, TAdditionalProperties extends false | 'string' | 'number' | 'boolean'> = unknown extends TCoerce ? ObjectValue<TProperties, TAdditionalProperties> : TCoerce;
|
|
50
|
+
export type ObjectOptionConfig<TCoerce, TProperties extends Record<string, {
|
|
51
|
+
type: string;
|
|
52
|
+
}>, TAdditionalProperties extends false | 'string' | 'number' | 'boolean' = false> = {
|
|
53
|
+
[key in keyof Omit<CommonOptionConfig<ObjectValue<NoInfer<TProperties>, NoInfer<TAdditionalProperties>>, NoInfer<TCoerce>>, 'choices' | 'coerce' | 'validate' | 'default'>]: CommonOptionConfig<ObjectValue<NoInfer<TProperties>, NoInfer<TAdditionalProperties>>, NoInfer<TCoerce>>[key];
|
|
54
|
+
} & {
|
|
55
|
+
type: 'object';
|
|
56
|
+
properties: TProperties;
|
|
57
|
+
additionalProperties?: TAdditionalProperties;
|
|
58
|
+
/**
|
|
59
|
+
* Provide a default value for the entire object.
|
|
60
|
+
* Uses a permissive type (object) to avoid interfering with TProperties inference.
|
|
61
|
+
* The actual type checking happens at runtime.
|
|
62
|
+
*/
|
|
63
|
+
default?: Default<object>;
|
|
64
|
+
/**
|
|
65
|
+
* Coerce transforms the parsed object value.
|
|
66
|
+
* The return type becomes the final type for this option.
|
|
67
|
+
*/
|
|
68
|
+
coerce?: (value: ObjectValue<TProperties, NoInfer<TAdditionalProperties>>) => TCoerce;
|
|
69
|
+
/**
|
|
70
|
+
* Validate the object value after coercion (or the raw value if no coerce).
|
|
71
|
+
* Receives the coerced type if coerce is provided, otherwise the computed ObjectValue type.
|
|
72
|
+
*/
|
|
73
|
+
validate?: (value: ObjectValidateType<TCoerce, TProperties, TAdditionalProperties>) => boolean | string;
|
|
74
|
+
};
|
|
75
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"object.js","sourceRoot":"","sources":["../../../src/lib/option-types/object.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { ResolveOptionType, WithOptional, ResolveProperties, WithAdditionalProperties } from './type-resolution';
|
|
2
|
+
/**
|
|
3
|
+
* Converts an OptionConfig to the TypeScript type for the parsed value.
|
|
4
|
+
* Uses shared type resolution logic from type-resolution.ts.
|
|
5
|
+
*/
|
|
6
|
+
export type OptionConfigToType<TOptionConfig extends {
|
|
7
|
+
type: string;
|
|
8
|
+
}> = WithOptional<ResolveOptionType<TOptionConfig>, TOptionConfig>;
|
|
9
|
+
export type { ResolveProperties, WithAdditionalProperties };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"option-config-to-type.js","sourceRoot":"","sources":["../../../src/lib/option-types/option-config-to-type.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ArrayOptionConfig } from './array';
|
|
2
|
+
import { BooleanOptionConfig } from './boolean';
|
|
3
|
+
import { NumberOptionConfig } from './number';
|
|
4
|
+
import { ObjectOptionConfig } from './object';
|
|
5
|
+
import { StringOptionConfig } from './string';
|
|
6
|
+
/**
|
|
7
|
+
* Configures an option for the parser. See subtypes for more information.
|
|
8
|
+
* - {@link StringOptionConfig}
|
|
9
|
+
* - {@link NumberOptionConfig}
|
|
10
|
+
* - {@link ArrayOptionConfig}
|
|
11
|
+
* - {@link BooleanOptionConfig}
|
|
12
|
+
*
|
|
13
|
+
* @typeParam TCoerce The return type of the `coerce` function if provided.
|
|
14
|
+
*/
|
|
15
|
+
export type OptionConfig<TCoerce = any, TChoices = any[], TObjectProps extends Record<string, {
|
|
16
|
+
type: string;
|
|
17
|
+
}> = Record<string, any>, TAdditionalProps extends false | 'string' | 'number' | 'boolean' = false> = StringOptionConfig<TCoerce, TChoices> | NumberOptionConfig<TCoerce, TChoices> | ArrayOptionConfig<TCoerce, TChoices> | BooleanOptionConfig<TCoerce, TChoices> | ObjectOptionConfig<TCoerce, TObjectProps, TAdditionalProps>;
|
|
18
|
+
/**
|
|
19
|
+
* An OptionConfig with generic parameters set for maximum compatibility.
|
|
20
|
+
* Uses `any` for all type parameters to allow maximum assignability.
|
|
21
|
+
* The IsAny check in AdditionalPropertiesType handles the case where
|
|
22
|
+
* TAdditionalProps is `any` by returning `unknown` instead of an index signature.
|
|
23
|
+
*/
|
|
24
|
+
export type UnknownOptionConfig = OptionConfig<any, any, any, any>;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"option-config.js","sourceRoot":"","sources":["../../../src/lib/option-types/option-config.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"string.js","sourceRoot":"","sources":["../../../src/lib/option-types/string.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Core type resolution utilities for option configs.
|
|
3
|
+
* Uses structural typing to avoid circular imports.
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* Check if a type is `any`.
|
|
7
|
+
* Uses the property that `1 & any` is `any`, and `0 extends any` is true.
|
|
8
|
+
*/
|
|
9
|
+
type IsAny<T> = 0 extends 1 & T ? true : false;
|
|
10
|
+
/**
|
|
11
|
+
* Force TypeScript to fully expand a type.
|
|
12
|
+
* This helps with deferred type evaluation in recursive types.
|
|
13
|
+
*/
|
|
14
|
+
export type Expand<T> = T extends infer O ? {
|
|
15
|
+
[K in keyof O]: O[K];
|
|
16
|
+
} : never;
|
|
17
|
+
/**
|
|
18
|
+
* Deeply expand a type, including nested objects.
|
|
19
|
+
*/
|
|
20
|
+
export type ExpandDeep<T> = T extends object ? T extends infer O ? {
|
|
21
|
+
[K in keyof O]: ExpandDeep<O[K]>;
|
|
22
|
+
} : never : T;
|
|
23
|
+
/**
|
|
24
|
+
* Infer the choice type from an option config.
|
|
25
|
+
* Choices can be an array (including readonly) or a function returning an array.
|
|
26
|
+
*/
|
|
27
|
+
export type InferChoice<T> = T extends {
|
|
28
|
+
choices: readonly (infer C)[];
|
|
29
|
+
} ? C : T extends {
|
|
30
|
+
choices: () => readonly (infer C)[];
|
|
31
|
+
} ? C : never;
|
|
32
|
+
/**
|
|
33
|
+
* Infer the coerced type. If coerce function exists, use its return type.
|
|
34
|
+
* Otherwise fall back to the provided fallback type.
|
|
35
|
+
*
|
|
36
|
+
* Uses optional property matching `coerce?:` to handle configs where coerce
|
|
37
|
+
* is defined as optional (like ObjectOptionConfig).
|
|
38
|
+
*
|
|
39
|
+
* Special handling:
|
|
40
|
+
* - [R] extends [never]: When coerce is missing/undefined, R infers as never
|
|
41
|
+
* - R extends undefined: When coerce explicitly returns undefined
|
|
42
|
+
*/
|
|
43
|
+
export type InferCoerce<T, TFallback> = T extends {
|
|
44
|
+
coerce?: (v: any) => infer R;
|
|
45
|
+
} ? [R] extends [never] ? TFallback : R extends undefined ? TFallback : R : TFallback;
|
|
46
|
+
/**
|
|
47
|
+
* Map an option config to its base TypeScript type.
|
|
48
|
+
* Uses structural typing to avoid circular imports.
|
|
49
|
+
*/
|
|
50
|
+
export type BaseType<T> = T extends {
|
|
51
|
+
type: 'string';
|
|
52
|
+
} ? string : T extends {
|
|
53
|
+
type: 'number';
|
|
54
|
+
} ? number : T extends {
|
|
55
|
+
type: 'boolean';
|
|
56
|
+
} ? boolean : T extends {
|
|
57
|
+
type: 'array';
|
|
58
|
+
items: 'string';
|
|
59
|
+
} ? string[] : T extends {
|
|
60
|
+
type: 'array';
|
|
61
|
+
items: 'number';
|
|
62
|
+
} ? number[] : T extends {
|
|
63
|
+
type: 'object';
|
|
64
|
+
properties: infer P;
|
|
65
|
+
additionalProperties: infer A;
|
|
66
|
+
} ? P extends Record<string, unknown> ? WithAdditionalProperties<ResolveProperties<P>, A> : never : T extends {
|
|
67
|
+
type: 'object';
|
|
68
|
+
properties: infer P;
|
|
69
|
+
} ? P extends Record<string, unknown> ? ResolveProperties<P> : never : never;
|
|
70
|
+
/**
|
|
71
|
+
* Resolve a single option config to its final type.
|
|
72
|
+
* Priority: choices > coerce > base type
|
|
73
|
+
*/
|
|
74
|
+
export type ResolveOptionType<T> = InferChoice<T> extends never ? InferCoerce<T, BaseType<T>> : InferChoice<T>;
|
|
75
|
+
/**
|
|
76
|
+
* Wrap a resolved type with undefined if the option is optional.
|
|
77
|
+
* Required options or options with defaults are never undefined.
|
|
78
|
+
*
|
|
79
|
+
* Uses `'key' extends keyof TConfig` instead of `TConfig extends { key: unknown }`
|
|
80
|
+
* to properly detect OPTIONAL properties. The latter check fails for optional
|
|
81
|
+
* properties because `{ default?: X }` doesn't guarantee `default` exists.
|
|
82
|
+
*/
|
|
83
|
+
export type WithOptional<TResolved, TConfig> = TConfig extends {
|
|
84
|
+
required: true;
|
|
85
|
+
} ? TResolved : 'default' extends keyof TConfig ? TResolved : TResolved | undefined;
|
|
86
|
+
/**
|
|
87
|
+
* Resolve all properties of an object option to their types.
|
|
88
|
+
* Each property becomes its resolved type, wrapped with optional handling.
|
|
89
|
+
*
|
|
90
|
+
* Special case: when TProperties is `any` (from `OptionConfig<any, any, any, any>`),
|
|
91
|
+
* we return `unknown` to avoid creating an index signature that would hide
|
|
92
|
+
* the actual properties inferred from the value.
|
|
93
|
+
*/
|
|
94
|
+
export type ResolveProperties<TProperties> = IsAny<TProperties> extends true ? unknown : {
|
|
95
|
+
[K in keyof TProperties]: WithOptional<ResolveOptionType<TProperties[K]>, TProperties[K]>;
|
|
96
|
+
};
|
|
97
|
+
type BaseLevelAdditionalProperties<TAdditional> = IsAny<TAdditional> extends true ? unknown : [TAdditional] extends [false] ? never : [TAdditional] extends ['string'] ? string : [TAdditional] extends ['number'] ? number : [TAdditional] extends ['boolean'] ? boolean : never;
|
|
98
|
+
/**
|
|
99
|
+
* Combines explicit properties with an index signature for additional properties.
|
|
100
|
+
*
|
|
101
|
+
* The index signature value is a union of all possible values (explicit + additional)
|
|
102
|
+
* to satisfy TypeScript's constraint that index signatures must be compatible with
|
|
103
|
+
* all explicit properties.
|
|
104
|
+
*
|
|
105
|
+
* This allows:
|
|
106
|
+
* - Explicit properties to keep their exact types via the intersection
|
|
107
|
+
* - Additional string keys to be added with the additionalProperties type
|
|
108
|
+
* - Bracket notation access returns the union of all possible types
|
|
109
|
+
*/
|
|
110
|
+
export type WithAdditionalProperties<TProperties, TAdditionalProperties> = TProperties & {
|
|
111
|
+
[key: string]: // | TProperties[keyof TProperties]
|
|
112
|
+
BaseLevelAdditionalProperties<TAdditionalProperties> | undefined;
|
|
113
|
+
};
|
|
114
|
+
/**
|
|
115
|
+
* Compute the full value type for an object option.
|
|
116
|
+
* Uses WithAdditionalProperties when additionalProperties is specified,
|
|
117
|
+
* which creates a compatible index signature.
|
|
118
|
+
*/
|
|
119
|
+
export type ObjectValueType<TProperties, TAdditionalProperties> = IsAny<TAdditionalProperties> extends true ? ResolveProperties<TProperties> : [TAdditionalProperties] extends [false] ? ResolveProperties<TProperties> : WithAdditionalProperties<ResolveProperties<TProperties>, TAdditionalProperties>;
|
|
120
|
+
/**
|
|
121
|
+
* Makes properties whose type includes `undefined` optional.
|
|
122
|
+
* This allows omitting properties like `{ foo?: string | undefined }` from object literals
|
|
123
|
+
* instead of requiring `{ foo: undefined }`.
|
|
124
|
+
*
|
|
125
|
+
* Uses a simpler mapped type approach that works better with generic keys in .d.ts generation.
|
|
126
|
+
*/
|
|
127
|
+
export type MakeUndefinedPropertiesOptional<T> = {
|
|
128
|
+
[K in keyof T as undefined extends T[K] ? K : never]?: T[K];
|
|
129
|
+
} & {
|
|
130
|
+
[K in keyof T as undefined extends T[K] ? never : K]: T[K];
|
|
131
|
+
};
|
|
132
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"type-resolution.js","sourceRoot":"","sources":["../../../src/lib/option-types/type-resolution.ts"],"names":[],"mappings":";AAAA;;;GAGG"}
|