https://github.com/wix-incubator/as-typed
Ambient mapping from JSON schema to typescript
https://github.com/wix-incubator/as-typed
json-schema types typescript
Last synced: about 1 year ago
JSON representation
Ambient mapping from JSON schema to typescript
- Host: GitHub
- URL: https://github.com/wix-incubator/as-typed
- Owner: wix-incubator
- License: mit
- Created: 2018-12-08T13:09:38.000Z (over 7 years ago)
- Default Branch: master
- Last Pushed: 2021-02-05T08:56:29.000Z (over 5 years ago)
- Last Synced: 2025-06-27T07:43:50.860Z (about 1 year ago)
- Topics: json-schema, types, typescript
- Language: TypeScript
- Size: 14.6 KB
- Stars: 100
- Watchers: 70
- Forks: 9
- Open Issues: 2
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# as-typed
Ambient mapping from JSON schema to typescript, without transpilation.
Use JSON schemas as a first-class citizen in Typescript.
## Overview
There are many tools that convert between Typescript and JSON schema. Howewever, all of them do that with a transpilation step.
Ambison uses the deep inference options in typescript 3 to infer the types directly from the JSON schema.
This is not a runtime library - it contains only a single generic type, AsTyped.
AsTyped can take any Json schema and AsTypeds it to a typescript type.
## Example Usage
As-typed is ambient only. To use, simply use the JSON schema as a **type** passed to the `AsTyped` generic type instead of as a value.
For example:
`AsTyped<{type: 'string'}>` will resolve to the typescript type `string`, and `AsTyped<{type: 'object' properties: {foo: {type: 'string'}}}>` will resolve to `{foo: string}` in typescript.
## Conversion Details
Every JSON schema type casts to a particular typescript type, as far as possible by language limitations.
The following is a table of how JSON schema types translate to Typescript types with asTyped
### Primitive types
* `AsTyped<{type: 'string'}>` === `string`
* `AsTyped<{type: 'number'}>` === `number`
* `AsTyped<{type: 'boolean'}>` === `boolean`
* `AsTyped<{type: 'null'}>` === `null`
* `AsTyped<{type: 'undefined'}>` === `undefined`
#### Limitations
* Patterns are not supported.
There is no regex validation in typescript
[Typescript issue 6579](https://github.com/Microsoft/TypeScript/issues/6579)
* Value validation (min, max etc) is not supported
Typescript is not meant for value checking (at least currently).
### Defined objects
* `AsTyped<{type: 'object', properties: {foo: {type: 'number'}}>` === `{foo?: number}`
#### with required properties
* `AsTyped<{type: 'object', properties: {foo: {type: 'number'}, bar: {type: 'string}, required: ['foo']}>` === `{foo: number, bar?: string}`
#### objects with a specific value type
`AsTyped<{type: 'array', items: [{type: 'number'}, {type: 'string'}], additionalItems: {type: 'boolean'}}>` === `[number, string, ...boolean[]]`
### Recursive objects and arrays
* `AsTyped<{type: 'array', items: {type: 'array', items: {type: 'string'}}}>` === `string[][]`
* `AsTyped<{type: 'object', properties: {arr: {type: 'array', items: {type: 'object', additionalProperties: {type: 'string'}}}}}` === `{arr: {[name: string]: string}[]}`
### Simple array
* `AsTyped<{type: 'array', items: {type: 'string`}}>` === `string[]`
### Tuple
* `AsTyped<{type: 'array', items: [{type: 'string'}, {type: 'number'}]}>` === `[string, number]`
#### Limitations
Due to typescript's missing variadic features, the max number of items in a tuple needs to be hardcoded, currently to 10.
[Typescript issue 5453](https://github.com/Microsoft/TypeScript/issues/5453)
### Tuple with additional items
* `AsTyped<{type: 'array', items: [{type: 'string'}, {type: 'number'}], additionalItems: {type: 'string'}}}>` === `[string, number, ...string[]]`
### Recursive reference by $id
#### Simple references:
* `AsTyped<{definitions: {foo: {$id: 'foo', type: 'number'}}, $ref: 'foo'}>` === `number`
#### Deep references:
* `AsTyped<{definitions: {str1: {$id: 'str1', $ref: 'str2'}, str2: {$id: 'str2', type: 'string'}}, $ref: 'str1'}>` === `string`
#### Limitations
Reference by URL ('#/definitions/foo', 'other.json/foo') are not supported.
Typescript doesn't allow inference by partial strings
[Typescript Issue 12754](https://github.com/Microsoft/TypeScript/issues/12754)
### not
`Not` works mainly on primitive types, e.g. `AsTyped<{not: {type: 'string'}}>` will resolve to `number | object | any[] | boolean`
### oneOf
* `AsTyped<{oneOf: [{type: 'string'}, {type: 'number'}]}>` === `string | number`
Currently doesn't work as expected, and resolves the same as anyOf.
See [Typescript issue 20863](https://github.com/Microsoft/TypeScript/issues/20863)
### allOf
* `AsTyped<{allOf: [{type: 'object', properties: {a: {type: 'number'}}}, {type: 'object', properties: {b: {type: 'string'}}}]}>` === `{a?: number, b?: string}`
### anyOf
* `AsTyped<{allOf: [{type: 'object', properties: {a: {type: 'number'}}}, {type: 'object', properties: {b: {type: 'string'}}, required: ['b']}]}>` === `{a?: number, b: string} | {a?: number} | {b: string}`
### If/Then/Else
`If/Then/Else` acts exactly like `{oneOf: [{allOf: [If, Then]}, Else]}`. It's strange to have this sugar in the schema which doesn't reduce the verbosity.
Currently doesn't work as expected, for the same reasons as oneOf. Resolves to `(If & Then) | Else`, which is not an accurate translation.
See [Typescript issue 20863](https://github.com/Microsoft/TypeScript/issues/20863)