#26401Medium

JSON Schema to TypeScript

Implement the generic type JSONSchema2TS which will return the TypeScript type corresponding to the given JSON schema. Master advanced TypeScript type manipulation in this medium-level challenge on TypeScriptPro.

In this medium-level challenge, you'll implement the generic type JSONSchema2TS which converts a JSON Schema definition into its corresponding TypeScript type, handling primitives, enums, objects with required/optional properties, and arrays.

Challenge Instructions: JSON Schema to TypeScript

Medium

Implement the generic type JSONSchema2TS which will return the TypeScript type corresponding to the given JSON schema.

Additional challenges to handle: additionalProperties oneOf, anyOf, allOf minLength and maxLength

Change the following code to make the test cases pass (no type check errors).

ChallengeSolution
// + Primitive types
type Type1 = JSONSchema2TS<{
  type: 'string'
}>
type Expected1 = string
type Result1 = Expect<Equal<Type1, Expected1>>

type Type2 = JSONSchema2TS<{
  type: 'number'
}>
type Expected2 = number
type Result2 = Expect<Equal<Type2, Expected2>>

type Type3 = JSONSchema2TS<{
  type: 'boolean'
}>
type Expected3 = boolean
type Result3 = Expect<Equal<Type3, Expected3>>
// - Primitive types

// + Enums
type Type4 = JSONSchema2TS<{
  type: 'string'
  enum: ['a', 'b', 'c']
}>
type Expected4 = 'a' | 'b' | 'c'
type Result4 = Expect<Equal<Type4, Expected4>>

type Type5 = JSONSchema2TS<{

Pro Challenge

Unlock 102+ medium, hard, and extreme challenges to master advanced TypeScript.

One-time payment. Lifetime access.

Detailed Explanation

type JSONSchema2TS<T> =
  T extends { type: 'string'; enum: infer E extends string[] }
    ? E[number]
    : T extends { type: 'number'; enum: infer E extends number[] }
      ? E[number]
      : T extends { type: 'string' }
        ? string
        : T extends { type: 'number' }
          ? number
          : T extends { type: 'boolean' }
            ? boolean
            : T extends { type: 'object'; properties: infer P; required: infer R extends string[] }
              ? {
                  [K in keyof P as K extends R[number] ? K : never]: JSONSchema2TS<P[K]>
                } & {
                  [K in keyof P as K extends R[number] ? never : K]?: JSONSchema2TS<P[K]>
                } extends infer O
                  ? { [K in keyof O]: O[K] }
                  : never
              : T extends { type: 'object'; properties: infer P }
                ? { [K in keyof P]?: JSONSchema2TS<P[K]> }
                : T extends { type: 'object' }
                  ? Record<string, unknown>
                  : T extends { type: 'array'; items: infer I }
                    ? JSONSchema2TS<I>[]
                    : T extends { type: 'array' }
                      ? unknown[]
                      : never;

How it works:

This challenge helps you understand recursive conditional types and JSON Schema modeling, and how to apply these concepts in real-world scenarios.

This challenge is originally from here.

Share this challenge

Learn the Concepts