diff --git a/core/clickhouse_schema.ts b/core/clickhouse_schema.ts index 8e3a47a..dc2f585 100644 --- a/core/clickhouse_schema.ts +++ b/core/clickhouse_schema.ts @@ -1,6 +1,6 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' -export interface SchemaValue { type: ChDataType, default?: any } +export interface SchemaValue { type: ChDataType } export type ChSchemaDefinition = Record /** * ChSchemaOptions is used to define the options for a clickhouse table schema. @@ -58,10 +58,10 @@ export class ClickhouseSchema imple const columns = Object.entries(this.schema as ChSchemaDefinition) .map(([name, field]) => { // Check if default is defined and a string, add single quotes; otherwise, just use the value - const defaultValue = field.default !== undefined - ? (typeof field.default === 'string' ? `'${field.default}'` : field.default) + const defaultValue = field.type.default !== undefined + ? (typeof field.type.default === 'string' ? `'${field.type.default}'` : field.type.default) : '' - return `${name} ${field.type}${field.default !== undefined ? ` DEFAULT ${defaultValue}` : ''}` + return `${name} ${field.type}${field.type.default !== undefined ? ` DEFAULT ${defaultValue}` : ''}` } ) .join(',\n') diff --git a/core/infer_schema_type.ts b/core/infer_schema_type.ts index 2726a8f..c0c6131 100644 --- a/core/infer_schema_type.ts +++ b/core/infer_schema_type.ts @@ -1,24 +1,8 @@ import { type ClickhouseSchema } from '@clickhouse-schema-core/clickhouse_schema' -import { type ChArray } from '@clickhouse-schema-data-types/ch_array' -import { type ChJSON } from '@clickhouse-schema-data-types/ch_json' -import { type ChEnum, type ChLowCardinality } from '@clickhouse-schema-data-types/ch_low_ cardinality' -import { type ChNullable } from '@clickhouse-schema-data-types/ch_nullable' import { type ChDataType } from '@clickhouse-schema-data-types/index' -import { type InferTypeFromMap } from '@clickhouse-schema-utils/util' -/** InferSchemaClickhouseSchemaType is a type that takes a ClickhouseSchema and returns the typescript that it represents */ -export type InferClickhouseSchemaType> = { [K in keyof T['schema']]: InferType } +/** Infer is a type that takes a ChDataType and returns the typescript that it represents */ +type Infer = T['typeScriptType'] -/** InferType is a type that takes a ChDataType and returns the typescript that it represents */ -export type InferType = - T extends ChNullable - ? InferTypeFromMap | null - : T extends ChArray - ? Array> - : T extends ChEnum - ? keyof EnumType - : T extends ChJSON - ? { [K in keyof Schema]: InferType } - : T extends ChLowCardinality - ? InferTypeFromMap - : InferTypeFromMap +/** InferSchemaClickhouseSchemaType is a type that takes a ClickhouseSchema and returns the typescript that it represents */ +export type InferClickhouseSchemaType> = { [K in keyof T['schema']]: Infer } diff --git a/data_types/ch_array.ts b/data_types/ch_array.ts index 273fcef..acf0f44 100644 --- a/data_types/ch_array.ts +++ b/data_types/ch_array.ts @@ -7,8 +7,11 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' export class ChArray> implements ChDataType { readonly innerType: T readonly typeStr: string + readonly typeScriptType!: Array + readonly default?: Array - constructor (t: T) { + constructor (t: T, defaultVal?: Array) { + this.default = defaultVal if (t instanceof ChArray) { this.innerType = new ChArray(t.innerType) as T } else { diff --git a/data_types/ch_boolean.ts b/data_types/ch_boolean.ts index 42782dc..ccd2c63 100644 --- a/data_types/ch_boolean.ts +++ b/data_types/ch_boolean.ts @@ -5,6 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChBoolean implements ChDataType { readonly typeStr: 'Boolean' = 'Boolean' as const + readonly typeScriptType!: boolean + readonly default?: boolean + + constructor (defaultValue?: boolean) { + this.default = defaultValue + } toString (): string { return this.typeStr diff --git a/data_types/ch_date.ts b/data_types/ch_date.ts index ce4ba34..0057340 100644 --- a/data_types/ch_date.ts +++ b/data_types/ch_date.ts @@ -5,6 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChDate implements ChDataType { readonly typeStr: 'Date' = 'Date' as const + readonly typeScriptType!: Date + readonly default?: Date + + constructor (defaultValue?: Date) { + this.default = defaultValue + } toString (): string { return this.typeStr @@ -16,6 +22,11 @@ export class ChDate implements ChDataType { */ export class ChDate32 implements ChDataType { readonly typeStr: 'Date32' = 'Date32' as const + readonly typeScriptType!: Date + readonly default?: Date + constructor (defaultValue?: Date) { + this.default = defaultValue + } toString (): string { return this.typeStr @@ -27,9 +38,12 @@ export class ChDate32 implements ChDataType { */ export class ChDateTime implements ChDataType { readonly typeStr: `DateTime('${T}')` + readonly typeScriptType!: Date + readonly defaultValue?: Date - constructor (readonly timezone: T) { + constructor (readonly timezone: T, defaultValue?: Date) { this.typeStr = `DateTime('${timezone}')` + this.defaultValue = defaultValue } toString (): string { @@ -44,9 +58,12 @@ export class ChDateTime implements ChDataType { */ export class ChDateTime64 implements ChDataType { readonly typeStr: `DateTime64(${T}, '${V}')` + readonly typeScriptType!: Date + readonly defaultValue?: Date - constructor (readonly precision: T, readonly timezone: V) { + constructor (readonly precision: T, readonly timezone: V, defaultValue?: Date) { this.typeStr = `DateTime64(${precision}, '${timezone}')` + this.defaultValue = defaultValue } toString (): string { diff --git a/data_types/ch_decimal.ts b/data_types/ch_decimal.ts index 8be2bbd..900cc47 100644 --- a/data_types/ch_decimal.ts +++ b/data_types/ch_decimal.ts @@ -7,9 +7,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChDecimal

implements ChDataType { readonly typeStr: `Decimal(${P},${S})` + readonly typeScriptType!: number + readonly default?: number - constructor (readonly precision: P, readonly scale: S) { + constructor (readonly precision: P, readonly scale: S, defaultVal?: number) { this.typeStr = `Decimal(${precision},${scale})` + this.default = defaultVal } toString (): string { diff --git a/data_types/ch_float.ts b/data_types/ch_float.ts index ae8d3f4..cd0194f 100644 --- a/data_types/ch_float.ts +++ b/data_types/ch_float.ts @@ -5,6 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChFloat32 implements ChDataType { readonly typeStr: 'Float32' = 'Float32' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.default = defaultValue + } toString (): string { return this.typeStr @@ -15,6 +21,12 @@ export class ChFloat32 implements ChDataType { */ export class ChFloat64 implements ChDataType { readonly typeStr: 'Float64' = 'Float64' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.default = defaultValue + } toString (): string { return this.typeStr diff --git a/data_types/ch_integer.ts b/data_types/ch_integer.ts index ed4baff..39f0bb8 100644 --- a/data_types/ch_integer.ts +++ b/data_types/ch_integer.ts @@ -5,9 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChUInt8 implements ChDataType { readonly typeStr: 'UInt8' = 'UInt8' as const + readonly typeScriptType!: number + readonly default?: number - constructor () { + constructor (defaultValue?: number) { this.typeStr = 'UInt8' + this.default = defaultValue } toString (): string { @@ -20,9 +23,12 @@ export class ChUInt8 implements ChDataType { */ export class ChUInt16 implements ChDataType { readonly typeStr: 'UInt16' = 'UInt16' as const + readonly typeScriptType!: number + readonly default?: number - constructor () { + constructor (defaultValue?: number) { this.typeStr = 'UInt16' + this.default = defaultValue } toString (): string { @@ -35,6 +41,13 @@ export class ChUInt16 implements ChDataType { */ export class ChUInt32 implements ChDataType { readonly typeStr: 'UInt32' = 'UInt32' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'UInt32' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -46,6 +59,13 @@ export class ChUInt32 implements ChDataType { */ export class ChUInt64 implements ChDataType { readonly typeStr: 'UInt64' = 'UInt64' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'UInt64' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -57,6 +77,13 @@ export class ChUInt64 implements ChDataType { */ export class ChUInt128 implements ChDataType { readonly typeStr: 'UInt128' = 'UInt128' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'UInt128' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -68,6 +95,13 @@ export class ChUInt128 implements ChDataType { */ export class ChUInt256 implements ChDataType { readonly typeStr: 'UInt256' = 'UInt256' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'UInt256' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -79,6 +113,13 @@ export class ChUInt256 implements ChDataType { */ export class ChInt8 implements ChDataType { readonly typeStr: 'Int8' = 'Int8' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int8' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -91,6 +132,13 @@ export class ChInt8 implements ChDataType { */ export class ChInt16 implements ChDataType { readonly typeStr: 'Int16' = 'Int16' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int16' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -102,6 +150,13 @@ export class ChInt16 implements ChDataType { */ export class ChInt32 implements ChDataType { readonly typeStr: 'Int32' = 'Int32' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int32' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -113,6 +168,13 @@ export class ChInt32 implements ChDataType { */ export class ChInt64 implements ChDataType { readonly typeStr: 'Int64' = 'Int64' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int64' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -124,6 +186,13 @@ export class ChInt64 implements ChDataType { */ export class ChInt128 implements ChDataType { readonly typeStr: 'Int128' = 'Int128' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int128' + this.default = defaultValue + } toString (): string { return this.typeStr @@ -135,6 +204,13 @@ export class ChInt128 implements ChDataType { */ export class ChInt256 implements ChDataType { readonly typeStr: 'Int256' = 'Int256' as const + readonly typeScriptType!: number + readonly default?: number + + constructor (defaultValue?: number) { + this.typeStr = 'Int256' + this.default = defaultValue + } toString (): string { return this.typeStr diff --git a/data_types/ch_ip_address.ts b/data_types/ch_ip_address.ts index 71675c4..80e443e 100644 --- a/data_types/ch_ip_address.ts +++ b/data_types/ch_ip_address.ts @@ -5,6 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChIPv4 implements ChDataType { readonly typeStr: 'IPv4' = 'IPv4' as const + readonly typeScriptType!: string + readonly default?: string + + constructor (defaultValue?: string) { + this.default = defaultValue + } toString (): string { return this.typeStr @@ -15,7 +21,13 @@ export class ChIPv4 implements ChDataType { * ChIPv6 is a class that represents a Clickhouse IPv6 data type */ export class ChIPv6 implements ChDataType { + readonly typeScriptType!: string readonly typeStr: 'IPv6' = 'IPv6' as const + readonly default?: string + + constructor (defaultValue?: string) { + this.default = defaultValue + } toString (): string { return this.typeStr diff --git a/data_types/ch_json.ts b/data_types/ch_json.ts index f9978f7..4e94966 100644 --- a/data_types/ch_json.ts +++ b/data_types/ch_json.ts @@ -7,10 +7,13 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' export class ChJSON implements ChDataType { readonly typeStr: 'JSON' readonly innerType: T + readonly typeScriptType!: { [K in keyof T]: T[K]['type']['typeScriptType'] } + readonly default?: { [K in keyof T]: T[K]['type']['typeScriptType'] } - constructor (innerType: T) { + constructor (innerType: T, defaultValue?: { [K in keyof T]: T[K]['type']['typeScriptType'] }) { this.typeStr = 'JSON' this.innerType = innerType + this.default = defaultValue } toString (): string { diff --git a/data_types/ch_low_ cardinality.ts b/data_types/ch_low_ cardinality.ts index 61a7cf7..2278782 100644 --- a/data_types/ch_low_ cardinality.ts +++ b/data_types/ch_low_ cardinality.ts @@ -7,10 +7,13 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' export class ChEnum> implements ChDataType { readonly typeStr: string readonly innerType: T + readonly typeScriptType!: keyof T + readonly default?: keyof T - constructor (enumObj: T) { + constructor (enumObj: T, defaultValue?: keyof T) { this.innerType = enumObj this.typeStr = this.toString() + this.default = defaultValue } toString (): string { @@ -23,9 +26,12 @@ export class ChEnum> implements ChDataType { */ export class ChLowCardinality implements ChDataType { readonly typeStr + readonly typeScriptType!: T['typeScriptType'] + readonly default?: T['typeScriptType'] - constructor (readonly innerType: T) { - this.typeStr = `LowCardinality(${innerType.typeStr})` + constructor (readonly innerType: T, defaultValue?: T['typeScriptType']) { + this.default = defaultValue + this.typeStr = `LowCardinality(${innerType.typeStr.toString()})` } toString (): string { diff --git a/data_types/ch_nullable.ts b/data_types/ch_nullable.ts index e795a43..7dabb18 100644 --- a/data_types/ch_nullable.ts +++ b/data_types/ch_nullable.ts @@ -4,13 +4,16 @@ import { type ChPrimitiveType, type ChDataType } from '@clickhouse-schema-data-t * ChNullable is a class that represents a Clickhouse Nullable data type * @param T - The inner type of the Nullable. Must be a primitive type */ -export class ChNullable implements ChDataType { +export class ChNullable implements ChDataType { readonly typeStr readonly innerType: T + readonly typeScriptType!: T['typeScriptType'] + readonly default?: T['typeScriptType'] - constructor (t: T) { + constructor (t: T, defaultVal?: T['typeScriptType']) { this.innerType = t - this.typeStr = `Nullable(${this.innerType})` + this.typeStr = `Nullable(${this.innerType.toString()})` + this.default = defaultVal } toString (): string { diff --git a/data_types/ch_string.ts b/data_types/ch_string.ts index 398937b..76abab0 100644 --- a/data_types/ch_string.ts +++ b/data_types/ch_string.ts @@ -5,6 +5,12 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' */ export class ChString implements ChDataType { readonly typeStr: 'String' = 'String' as const + readonly typeScriptType!: string + readonly default?: string + + constructor (defaultValue?: string) { + this.default = defaultValue + } toString (): string { return this.typeStr @@ -17,9 +23,12 @@ export class ChString implements ChDataType { */ export class ChFixedString implements ChDataType { readonly typeStr: `FixedString(${T})` + readonly typeScriptType!: string + readonly default?: string - constructor (readonly length: T) { + constructor (readonly length: T, defaultVal?: string) { this.typeStr = `FixedString(${length})` + this.default = defaultVal } toString (): string { diff --git a/data_types/ch_uuid.ts b/data_types/ch_uuid.ts index 27101dc..d16c90d 100644 --- a/data_types/ch_uuid.ts +++ b/data_types/ch_uuid.ts @@ -4,7 +4,13 @@ import { type ChDataType } from '@clickhouse-schema-data-types/index' * ChUUID is a class that represents a Clickhouse UUID data type */ export class ChUUID implements ChDataType { + typeScriptType!: string readonly typeStr: 'UUID' = 'UUID' as const + readonly default?: string + + constructor (defaultValue?: string) { + this.default = defaultValue + } toString (): string { return this.typeStr diff --git a/data_types/index.ts b/data_types/index.ts index ff3aaf7..9342cfa 100644 --- a/data_types/index.ts +++ b/data_types/index.ts @@ -4,7 +4,6 @@ import { ChBoolean } from '@clickhouse-schema-data-types/ch_boolean' import { ChDate, ChDate32, ChDateTime, ChDateTime64 } from '@clickhouse-schema-data-types/ch_date' import { ChDecimal } from '@clickhouse-schema-data-types/ch_decimal' import { ChFloat32, ChFloat64 } from '@clickhouse-schema-data-types/ch_float' -import { ChInt128, ChInt16, ChInt256, ChInt32, ChInt64, ChInt8, ChUInt128, ChUInt16, ChUInt256, ChUInt32, ChUInt64, ChUInt8 } from '@clickhouse-schema-data-types/ch_integer' import { ChIPv4, ChIPv6 } from '@clickhouse-schema-data-types/ch_ip_address' import { ChJSON } from '@clickhouse-schema-data-types/ch_json' @@ -12,45 +11,145 @@ import { ChEnum, ChLowCardinality } from '@clickhouse-schema-data-types/ch_low_ import { ChNullable } from '@clickhouse-schema-data-types/ch_nullable' import { ChFixedString, ChString } from '@clickhouse-schema-data-types/ch_string' import { ChUUID } from '@clickhouse-schema-data-types/ch_uuid' +import { ChUInt8, ChUInt16, ChUInt32, ChUInt64, ChUInt128, ChUInt256, ChInt8, ChInt16, ChInt32, ChInt64, ChInt128, ChInt256 } from '@clickhouse-schema-data-types/ch_integer' /** * ChDataType is an interface that represents a Clickhouse data type */ export interface ChDataType { typeStr: string + default?: any + innerType?: any + typeScriptType: any toString: () => string } -// Integer types unsigned -export const CHUInt8 = new ChUInt8() -export const CHUInt16 = new ChUInt16() -export const CHUInt32 = new ChUInt32() -export const CHUInt64 = new ChUInt64() -export const CHUInt128 = new ChUInt128() -export const CHUInt256 = new ChUInt256() -// Integer types signed -export const CHInt8 = new ChInt8() -export const CHInt16 = new ChInt16() -export const CHInt32 = new ChInt32() -export const CHInt64 = new ChInt64() -export const CHInt128 = new ChInt128() -export const CHInt256 = new ChInt256() -// Float types -export const CHFloat32 = new ChFloat32() -export const CHFloat64 = new ChFloat64() -// Boolean type -export const CHBoolean = new ChBoolean() -// String type -export const CHString = new ChString() -// UUID type -export const CHUUID = new ChUUID() -// Date types -export const CHDate = new ChDate() -export const CHDate32 = new ChDate32() - -// IP Address types -export const CHIPv4 = new ChIPv4() -export const CHIPv6 = new ChIPv6() +/** + * + * @param df default value of the UInt8 + * @returns a new ChUInt8 object + */ +export const CHUInt8 = (df?: T): ChUInt8 => new ChUInt8(df) +/** + * + * @param df default value of the UInt16 + * @returns a new ChUInt16 object + */ +export const CHUInt16 = (df?: T): ChUInt16 => new ChUInt16(df) +/** + * + * @param df default value of the UInt32 + * @returns a new ChUInt32 object + */ +export const CHUInt32 = (df?: T): ChUInt32 => new ChUInt32(df) +/** + * + * @param df default value of the UInt64 + * @returns a new ChUInt64 object + */ +export const CHUInt64 = (df?: T): ChUInt64 => new ChUInt64(df) +/** + * + * @param df default value of the UInt128 + * @returns a new ChUInt128 object + */ +export const CHUInt128 = (df?: T): ChUInt128 => new ChUInt128(df) +/** + * + * @param df default value of the UInt256 + * @returns a new ChUInt256 object + */ +export const CHUInt256 = (df?: T): ChUInt256 => new ChUInt256(df) +/** + * + * @param df default value of the Int8 + * @returns a new ChInt8 object + */ +export const CHInt8 = (df?: T): ChInt8 => new ChInt8(df) +/** + * + * @param df default value of the Int16 + * @returns a new ChInt16 object + */ +export const CHInt16 = (df?: T): ChInt16 => new ChInt16(df) +/** + * + * @param df default value of the Int32 + * @returns a new ChInt32 object + */ +export const CHInt32 = (df?: T): ChInt32 => new ChInt32(df) +/** + * + * @param df default value of the Int64 + * @returns a new ChInt64 object + */ +export const CHInt64 = (df?: T): ChInt64 => new ChInt64(df) +/** + * + * @param df default value of the Int128 + * @returns a new ChInt128 object + */ +export const CHInt128 = (df?: T): ChInt128 => new ChInt128(df) +/** + * + * @param df default value of the Int256 + * @returns a new ChInt256 object + */ +export const CHInt256 = (df?: T): ChInt256 => new ChInt256(df) +/** + * + * @param df default value of the Float32 + * @returns a new ChFloat32 object + */ +export const CHFloat32 = (df?: T): ChFloat32 => new ChFloat32(df) +/** + * + * @param df default value of the Float64 + * @returns a new ChFloat64 object + */ +export const CHFloat64 = (df?: T): ChFloat64 => new ChFloat64(df) +/** + * + * @param df default value of the Boolean + * @returns a new ChBoolean object + */ +export const CHBoolean = (df?: T): ChBoolean => new ChBoolean(df) +/** + * + * @param df default value of the String + * @returns a new ChString object + */ +export const CHString = (df?: T): ChString => new ChString(df) +/** + * + * @param df default value of the UUID + * @returns a new ChUUID object + */ +export const CHUUID = (df?: T): ChUUID => new ChUUID(df) +/** + * + * @param df default value of the Date + * @returns a new ChDate object + */ +export const CHDate = (df?: T): ChDate => new ChDate(df) +/** + * + * @param df default value of the Date32 + * @returns a new ChDate32 object + */ +export const CHDate32 = (df?: T): ChDate32 => new ChDate32(df) +/** + * + * @param df default value of the IPv4 + * @returns a new ChIPv4 object + */ +export const CHIPv4 = (df?: T): ChIPv4 => new ChIPv4(df) +/** + * + * @param df default value of the IPv6 + * @returns a new ChIPv6 object + */ +export const CHIPv6 = (df?: T): ChIPv6 => new ChIPv6(df) /** * @@ -58,58 +157,58 @@ export const CHIPv6 = new ChIPv6() * @param scale scale of the decimal * @returns a new ChDecimal object */ -export const CHDecimal =

(precision: P, scale: S): ChDecimal => new ChDecimal(precision, scale) +export const CHDecimal =

['typeScriptType']>(precision: P, scale: S, df?: T): ChDecimal => new ChDecimal(precision, scale, df) /** * * @param length length of the fixed string * @returns a new ChFixedString object */ -export const CHFixedString = (length: T): ChFixedString => new ChFixedString(length) +export const CHFixedString = ['typeScriptType']>(length: L, df?: T): ChFixedString => new ChFixedString(length, df) /** * * @param timezone timezone of the DateTime * @returns a new ChDateTime object */ -export const CHDateTime = (timezone: TZ): ChDateTime => new ChDateTime(timezone) +export const CHDateTime = ['typeScriptType']>(timezone: TZ, df?: T): ChDateTime => new ChDateTime(timezone, df) /** * * @param precision precision of the DateTime64 * @param timezone timezone of the DateTime64 * @returns a new ChDateTime64 object */ -export const CHDateTime64 =

(precision: P, timezone: TZ): ChDateTime64 => new ChDateTime64(precision, timezone) +export const CHDateTime64 =

['typeScriptType'] >(precision: P, timezone: TZ, df?: T): ChDateTime64 => new ChDateTime64(precision, timezone, df) /** * * @param schema schema definition for the JSON * @returns a new ChJSON object */ -export const CHJSON = (schema: T): ChJSON => new ChJSON(schema) +export const CHJSON = ['typeScriptType']>(schema: SD, df?: T): ChJSON => new ChJSON(schema, df) /** * * @param t type of the array * @returns a new ChArray object */ -export const CHArray = (t: T): ChArray => new ChArray(t) +export const CHArray = ['typeScriptType']>(t: IN, df?: T): ChArray => new ChArray(t, df) /** * * @param enumObj enum object. The keys are the enum names and the values are the enum values * @returns a new ChEnum object */ -export const CHEnum = >(enumObj: T): ChEnum => new ChEnum(enumObj) +export const CHEnum = , T extends ChEnum['typeScriptType']>(enumObj: IN, df?: T): ChEnum => new ChEnum(enumObj, df) /** * * @param type type of the low cardinality. Must be a string or fixed string * @returns a new ChLowCardinality object */ -export const CHLowCardinality = >(type: T): ChLowCardinality => new ChLowCardinality(type) +export const CHLowCardinality = , T extends ChLowCardinality['typeScriptType']>(type: IN, df?: T): ChLowCardinality => new ChLowCardinality(type, df) /** * * @param type type of the nullable. Must be a primitive type * @returns a new ChNullable object */ -export const CHNullable = (type: T): ChNullable => new ChNullable(type) +export const CHNullable = ['typeScriptType']>(type: IN, df?: T): ChNullable => new ChNullable(type, df) export const ClickhouseTypes = { CHUInt8, @@ -143,33 +242,6 @@ export const ClickhouseTypes = { CHLowCardinality, CHNullable } -export interface MapChSchemaTypes { - UInt8: number - UInt16: number - UInt32: number - UInt64: number - UInt128: number - UInt256: number - Int8: number - Int16: number - Int32: number - Int64: number - Int128: number - Int256: number - Float32: number - Float64: number - Decimal: number - Boolean: boolean - String: string - UUID: string - Date: Date - Date32: Date - DateTime: Date - DateTime64: Date - FixedString: string - IPv4: string - IPv6: string -} export type ChPrimitiveType = ChUInt8 | ChUInt16 | ChUInt32 | ChUInt64 | ChUInt128 | ChUInt256 | diff --git a/index.ts b/index.ts index 27e75cb..87f4db2 100644 --- a/index.ts +++ b/index.ts @@ -3,5 +3,6 @@ export type { InferClickhouseSchemaType } from '@clickhouse-schema-core/infer_sc export { CHArray, CHBoolean, CHDate, CHDate32, CHDateTime, CHDateTime64, CHDecimal, CHEnum, CHFixedString, CHFloat32, CHFloat64, CHIPv4, - CHIPv6, CHInt128, CHInt16, CHInt256, CHInt32, CHInt64, CHInt8, CHJSON, CHLowCardinality, CHNullable, CHString, CHUInt128, CHUInt16, CHUInt256, CHUInt32, CHUInt64, CHUInt8, CHUUID, ClickhouseTypes + CHIPv6, CHInt128, CHInt16, CHInt256, CHInt32, CHInt64, CHInt8, CHJSON, CHLowCardinality, CHNullable, + CHString, CHUInt128, CHUInt16, CHUInt256, CHUInt32, CHUInt64, CHUInt8, CHUUID, ClickhouseTypes } from '@clickhouse-schema-data-types/index' diff --git a/tests/unit/clickhouse_schema.test.ts b/tests/unit/clickhouse_schema.test.ts index 5990c3d..ae9f308 100644 --- a/tests/unit/clickhouse_schema.test.ts +++ b/tests/unit/clickhouse_schema.test.ts @@ -5,24 +5,9 @@ import { ClickhouseTypes } from '@clickhouse-schema-data-types/index' describe('ClickhouseSchema Tests', () => { it('should correctly store schema definitions and options', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUInt128 }, - name: { type: ClickhouseTypes.CHString }, - email: { type: ClickhouseTypes.CHString }, - age: { type: ClickhouseTypes.CHUInt8 }, - score: { type: ClickhouseTypes.CHDecimal(10, 2) }, - fixed_cardinality: { type: ClickhouseTypes.CHLowCardinality(ClickhouseTypes.CHFixedString(2)) }, - a: { type: ClickhouseTypes.CHArray(ClickhouseTypes.CHEnum({ aaaa: 1, b: 10 })) }, - enum: { type: ClickhouseTypes.CHEnum({ a: 1, b: 2 }) }, - ch_date: { type: ClickhouseTypes.CHDate }, - ch_datetime: { type: ClickhouseTypes.CHDateTime('UTC') }, - ch_uuid: { type: ClickhouseTypes.CHUUID }, - ch_datetime64: { type: ClickhouseTypes.CHDateTime64(3, 'UTC') }, - ch_date32: { type: ClickhouseTypes.CHDate32 }, - ch_nullable: { type: ClickhouseTypes.CHNullable(ClickhouseTypes.CHFloat32) }, - ch_decimal32: { type: ClickhouseTypes.CHDecimal(2, 2) }, - ch_json: { type: ClickhouseTypes.CHJSON({ k: { type: ClickhouseTypes.CHString }, arr: { type: ClickhouseTypes.CHArray(ClickhouseTypes.CHJSON({ nested: { type: ClickhouseTypes.CHString } })) } }) }, - ch_IPv6: { type: ClickhouseTypes.CHIPv6 }, - ch_IPv4: { type: ClickhouseTypes.CHIPv4 } + id: { type: ClickhouseTypes.CHUInt128() }, + + ch_json: { type: ClickhouseTypes.CHJSON({ k: { type: ClickhouseTypes.CHString() }, arr: { type: ClickhouseTypes.CHArray(ClickhouseTypes.CHJSON({ nested: { type: ClickhouseTypes.CHString() } })) } }) } } const options: ChSchemaOptions = { primary_key: 'id', @@ -39,10 +24,10 @@ describe('ClickhouseSchema Tests', () => { it('should correctly throw an error if schema is missing both primary_key and order_by fields', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString }, - email: { type: ClickhouseTypes.CHString }, - age: { type: ClickhouseTypes.CHUInt8 } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString() }, + email: { type: ClickhouseTypes.CHString() }, + age: { type: ClickhouseTypes.CHUInt8() } } const options: ChSchemaOptions = { table_name: 'users_table' @@ -55,10 +40,10 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query without a default value for any fields', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString }, - email: { type: ClickhouseTypes.CHString }, - age: { type: ClickhouseTypes.CHUInt8 } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString() }, + email: { type: ClickhouseTypes.CHString() }, + age: { type: ClickhouseTypes.CHUInt8() } } const options: ChSchemaOptions = { primary_key: 'id', @@ -73,10 +58,10 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with a default value for some fields', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString, default: 'john@gmail.com' }, - age: { type: ClickhouseTypes.CHUInt8 } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString('john@gmail.com') }, + age: { type: ClickhouseTypes.CHUInt8() } } const options: ChSchemaOptions = { primary_key: 'id', @@ -91,10 +76,10 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with additional options', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString, default: 'john@gmail.com' }, - age: { type: ClickhouseTypes.CHUInt8, default: 18 } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString('john@gmail.com') }, + age: { type: ClickhouseTypes.CHUInt8(18) } } const options: ChSchemaOptions = { primary_key: 'id', @@ -109,9 +94,9 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with a specified order_by field', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { table_name: 'users_table', @@ -125,9 +110,9 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with a specified on_cluster field', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { table_name: 'users_table', @@ -142,9 +127,9 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with a specified engine', () => { const schema = new ClickhouseSchema({ - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } }, { table_name: 'users_table', primary_key: 'id', @@ -157,9 +142,9 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query with a specified database', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { database: 'users_db', @@ -174,9 +159,9 @@ describe('ClickhouseSchema Tests', () => { it('should correctly generate a create table query list', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { table_name: 'users_table', @@ -204,9 +189,9 @@ describe('ClickhouseSchema Tests', () => { it('should generate a create table query when to string is called', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { table_name: 'users_table', @@ -219,14 +204,15 @@ describe('ClickhouseSchema Tests', () => { const expectedQuery = 'CREATE TABLE IF NOT EXISTS users_table ON CLUSTER users_cluster\n(\nid UUID,\nname String DEFAULT \'John Doe\',\nemail String\n)\nENGINE = MergeTree()\nORDER BY id\nPRIMARY KEY id\nCOMMENT \'This table provides user details\'' // eslint-disable-next-line @typescript-eslint/no-base-to-string const query = schema.toString() + expect(query).toEqual(expectedQuery) }) it('should not throw if on_cluster is specified but primary_key or order_by is not', () => { const schemaDefinition = { - id: { type: ClickhouseTypes.CHUUID }, - name: { type: ClickhouseTypes.CHString, default: 'John Doe' }, - email: { type: ClickhouseTypes.CHString } + id: { type: ClickhouseTypes.CHUUID() }, + name: { type: ClickhouseTypes.CHString('John Doe') }, + email: { type: ClickhouseTypes.CHString() } } const options: ChSchemaOptions = { table_name: 'users_table', diff --git a/tests/unit/data_types.test.ts b/tests/unit/data_types.test.ts index 097eb46..54ededa 100644 --- a/tests/unit/data_types.test.ts +++ b/tests/unit/data_types.test.ts @@ -1,28 +1,19 @@ -import { ChArray } from '@clickhouse-schema-data-types/ch_array' -import { ChBoolean } from '@clickhouse-schema-data-types/ch_boolean' -import { ChDate, ChDate32, ChDateTime, ChDateTime64 } from '@clickhouse-schema-data-types/ch_date' -import { ChEnum } from '@clickhouse-schema-data-types/ch_low_ cardinality' -import { ChFloat32, ChFloat64 } from '@clickhouse-schema-data-types/ch_float' -import { ChUInt8, ChUInt16, ChUInt32, ChUInt64, ChInt8, ChInt16, ChInt128, ChInt256, ChInt32, ChInt64, ChUInt128, ChUInt256 } from '@clickhouse-schema-data-types/ch_integer' -import { ChJSON } from '@clickhouse-schema-data-types/ch_json' -import { ChFixedString, ChString } from '@clickhouse-schema-data-types/ch_string' -import { ChUUID } from '@clickhouse-schema-data-types/ch_uuid' import { ClickhouseTypes } from '@clickhouse-schema-data-types/index' describe('Data Types Tests', () => { it('should correctly create integer data types with the correct typeStr', () => { - const uint8 = new ChUInt8() - const uint16 = new ChUInt16() - const uint32 = new ChUInt32() - const uint64 = new ChUInt64() - const uint128 = new ChUInt128() - const uint256 = new ChUInt256() - const int8 = new ChInt8() - const int16 = new ChInt16() - const int32 = new ChInt32() - const int64 = new ChInt64() - const int128 = new ChInt128() - const int256 = new ChInt256() + const uint8 = ClickhouseTypes.CHUInt8(2) + const uint16 = ClickhouseTypes.CHUInt16(2) + const uint32 = ClickhouseTypes.CHUInt32(2) + const uint64 = ClickhouseTypes.CHUInt64(2) + const uint128 = ClickhouseTypes.CHUInt128(2) + const uint256 = ClickhouseTypes.CHUInt256(2) + const int8 = ClickhouseTypes.CHInt8(2) + const int16 = ClickhouseTypes.CHInt16(2) + const int32 = ClickhouseTypes.CHInt32(2) + const int64 = ClickhouseTypes.CHInt64(2) + const int128 = ClickhouseTypes.CHInt128(2) + const int256 = ClickhouseTypes.CHInt256(2) expect(uint8.toString()).toEqual('UInt8') expect(uint16.toString()).toEqual('UInt16') @@ -41,31 +32,31 @@ describe('Data Types Tests', () => { }) it('should correctly create float data types with the correct typeStr', () => { - const float32 = new ChFloat32() - const float64 = new ChFloat64() + const float32 = ClickhouseTypes.CHFloat32(2) + const float64 = ClickhouseTypes.CHFloat64(2) expect(float32.toString()).toEqual('Float32') expect(float64.toString()).toEqual('Float64') }) it('should correctly create boolean data type with the correct typeStr', () => { - const bool = new ChBoolean() + const bool = ClickhouseTypes.CHBoolean(true) expect(bool.toString()).toEqual('Boolean') }) it('should correctly create array data type with the correct typeStr', () => { - const stringArray = new ChArray(new ChString()) - const nestedArray = new ChArray(new ChArray(new ChString())) + const stringArray = ClickhouseTypes.CHArray(ClickhouseTypes.CHString('arr')) + const nestedArray = ClickhouseTypes.CHArray(ClickhouseTypes.CHArray(ClickhouseTypes.CHString('arr'))) expect(stringArray.toString()).toEqual('Array(String)') expect(nestedArray.toString()).toEqual('Array(Array(String))') }) it('should correctly create date data types with the correct typeStr', () => { - const date = new ChDate() - const date32 = new ChDate32() - const dateTime64 = new ChDateTime64(3, 'UTC') - const dateTime = new ChDateTime('UTC') + const date = ClickhouseTypes.CHDate(new Date()) + const date32 = ClickhouseTypes.CHDate32(new Date()) + const dateTime64 = ClickhouseTypes.CHDateTime64(3, 'UTC', new Date()) + const dateTime = ClickhouseTypes.CHDateTime('UTC', new Date()) expect(dateTime.toString()).toEqual('DateTime(\'UTC\')') expect(dateTime64.toString()).toEqual('DateTime64(3, \'UTC\')') @@ -75,53 +66,53 @@ describe('Data Types Tests', () => { }) it('should correctly create a string data types with the correct typeStr', () => { - const string = new ChString() - const fixedString = new ChFixedString(10) + const string = ClickhouseTypes.CHString() + const fixedString = ClickhouseTypes.CHFixedString(10) expect(string.toString()).toEqual('String') expect(fixedString.toString()).toEqual('FixedString(10)') }) it('should correctly create a uuid data type with the correct typeStr', () => { - const uuid = new ChUUID() + const uuid = ClickhouseTypes.CHUUID('123') expect(uuid.toString()).toEqual('UUID') }) it('should correctly create a json data type with the correct typeStr', () => { - const json = new ChJSON({ + const json = ClickhouseTypes.CHJSON({ dateTime64: { type: ClickhouseTypes.CHDateTime64(3, 'UTC') }, dateTime: { type: ClickhouseTypes.CHDateTime('UTC') }, enum: { type: ClickhouseTypes.CHEnum({ POST: 1, PUT: 2, DELETE: 3, GET: 4 }) }, - array: { type: ClickhouseTypes.CHArray(ClickhouseTypes.CHString) }, + array: { type: ClickhouseTypes.CHArray(ClickhouseTypes.CHString()) }, fixedString: { type: ClickhouseTypes.CHFixedString(10) }, - json: { type: ClickhouseTypes.CHJSON({ k: { type: ClickhouseTypes.CHString } }) } - }) + json: { type: ClickhouseTypes.CHJSON({ k: { type: ClickhouseTypes.CHString() } }) } + }, { array: [''], dateTime: new Date(), dateTime64: new Date(), enum: 'DELETE', fixedString: '', json: { k: '' } }) expect(json.toString()).toEqual('JSON') }) it('should correctly create a enum data type with the correct typeStr', () => { - const enumType = new ChEnum({ POST: 1, PUT: 2, DELETE: 3, GET: 4 }) + const enumType = ClickhouseTypes.CHEnum({ POST: 1, PUT: 2, DELETE: 3, GET: 4 }, 'POST') expect(enumType.toString()).toEqual('Enum(\'POST\' = 1,\'PUT\' = 2,\'DELETE\' = 3,\'GET\' = 4)') }) it('should correctly create a nullable data type with the correct typeStr', () => { - const nullableString = ClickhouseTypes.CHNullable(ClickhouseTypes.CHString) + const nullableString = ClickhouseTypes.CHNullable(ClickhouseTypes.CHString('nullable')) expect(nullableString.toString()).toEqual('Nullable(String)') }) it('should correctly create a decimal data type with the correct typeStr', () => { - const decimal = ClickhouseTypes.CHDecimal(10, 2) + const decimal = ClickhouseTypes.CHDecimal(10, 2, 10.2) expect(decimal.toString()).toEqual('Decimal(10,2)') }) it('should correctly create a low cardinality data type with the correct typeStr', () => { - const lowCardinality = ClickhouseTypes.CHLowCardinality(ClickhouseTypes.CHString) + const lowCardinality = ClickhouseTypes.CHLowCardinality(ClickhouseTypes.CHString('lowCardinality')) expect(lowCardinality.toString()).toEqual('LowCardinality(String)') }) it('should correctly create a ip address data types with the correct typeStr', () => { - const ipv4 = ClickhouseTypes.CHIPv4 - const ipv6 = ClickhouseTypes.CHIPv6 + const ipv4 = ClickhouseTypes.CHIPv4('192.122.0.0') + const ipv6 = ClickhouseTypes.CHIPv6('2001:0db8:85a3:0000:0000:8a2e:0370:7334') expect(ipv4.toString()).toEqual('IPv4') expect(ipv6.toString()).toEqual('IPv6') }) diff --git a/utils/util.ts b/utils/util.ts deleted file mode 100644 index 1d59f9c..0000000 --- a/utils/util.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { type MapChSchemaTypes } from '@clickhouse-schema-data-types/index' - -/* eslint-disable @typescript-eslint/no-unused-vars */ -export type ExtractInnerType = T extends `${infer _BeforeBracket}(${infer Rest})` - ? ExtractInnerType - : T - -export type ExtractOuterType = T extends `${infer BeforeBracket}(${infer _Rest})` - ? BeforeBracket - : T - -/** InferTypeFromMap is a type that takes a string and returns the typescript that it represents */ -export type InferTypeFromMap = ExtractInnerType extends keyof MapChSchemaTypes - ? MapChSchemaTypes[ExtractInnerType] - : ExtractOuterType extends keyof MapChSchemaTypes ? - MapChSchemaTypes[ExtractOuterType] - : any