@@ -5,6 +5,7 @@ import 'reflect-metadata';
5
5
import { DateTime } from 'luxon' ;
6
6
import { uuidToNative , uuidToValue } from './uuid' ;
7
7
import { fromDecimalString , toDecimalString } from './decimal' ;
8
+ import { emitWarning } from 'process' ;
8
9
import Type = Ydb . Type ;
9
10
import IType = Ydb . IType ;
10
11
import IStructMember = Ydb . IStructMember ;
@@ -17,7 +18,21 @@ import NullValue = google.protobuf.NullValue;
17
18
18
19
export const typeMetadataKey = Symbol ( 'type' ) ;
19
20
21
+ const shownDeprecations = new Set ( ) ;
22
+ function warnDeprecation ( message : string ) {
23
+ if ( ! shownDeprecations . has ( message ) ) {
24
+ shownDeprecations . add ( message ) ;
25
+ emitWarning ( message ) ;
26
+ }
27
+ }
28
+
20
29
export function declareType ( type : IType ) {
30
+ if ( type === Types . STRING ) {
31
+ warnDeprecation (
32
+ 'Types.STRING type is deprecated and will be removed in the next major release. Please migrate ' +
33
+ 'to the newer type Types.BYTES which avoids implicit conversions between Buffer and string types.'
34
+ ) ;
35
+ }
21
36
return Reflect . metadata ( typeMetadataKey , type ) ;
22
37
}
23
38
@@ -48,7 +63,7 @@ export const primitiveTypeToValue: Record<number, string> = {
48
63
[ Type . PrimitiveTypeId . TZ_TIMESTAMP ] : 'textValue' ,
49
64
} ;
50
65
51
- type primitive = boolean | string | number | Long | Date ;
66
+ type primitive = boolean | string | number | Long | Date | Buffer ;
52
67
53
68
export type StructFields = Record < string , IType > ;
54
69
@@ -57,15 +72,17 @@ export class Types {
57
72
static INT8 : IType = { typeId : Ydb . Type . PrimitiveTypeId . INT8 } ;
58
73
static UINT8 : IType = { typeId : Ydb . Type . PrimitiveTypeId . UINT8 } ;
59
74
static INT16 : IType = { typeId : Ydb . Type . PrimitiveTypeId . INT16 } ;
60
- static UINT16 : IType = { typeId : Ydb . Type . PrimitiveTypeId . INT16 } ;
75
+ static UINT16 : IType = { typeId : Ydb . Type . PrimitiveTypeId . UINT16 } ;
61
76
static INT32 : IType = { typeId : Ydb . Type . PrimitiveTypeId . INT32 } ;
62
77
static UINT32 : IType = { typeId : Ydb . Type . PrimitiveTypeId . UINT32 } ;
63
78
static INT64 : IType = { typeId : Ydb . Type . PrimitiveTypeId . INT64 } ;
64
79
static UINT64 : IType = { typeId : Ydb . Type . PrimitiveTypeId . UINT64 } ;
65
80
static FLOAT : IType = { typeId : Ydb . Type . PrimitiveTypeId . FLOAT } ;
66
81
static DOUBLE : IType = { typeId : Ydb . Type . PrimitiveTypeId . DOUBLE } ;
67
82
static STRING : IType = { typeId : Ydb . Type . PrimitiveTypeId . STRING } ;
83
+ static BYTES : IType = { typeId : Ydb . Type . PrimitiveTypeId . STRING } ;
68
84
static UTF8 : IType = { typeId : Ydb . Type . PrimitiveTypeId . UTF8 } ;
85
+ static TEXT : IType = { typeId : Ydb . Type . PrimitiveTypeId . UTF8 } ;
69
86
static YSON : IType = { typeId : Ydb . Type . PrimitiveTypeId . YSON } ;
70
87
static JSON : IType = { typeId : Ydb . Type . PrimitiveTypeId . JSON } ;
71
88
static UUID : IType = { typeId : Ydb . Type . PrimitiveTypeId . UUID } ;
@@ -135,11 +152,10 @@ export class Types {
135
152
}
136
153
137
154
export class TypedValues {
138
- private static primitive ( type : Ydb . Type . PrimitiveTypeId , value : primitive ) : ITypedValue {
139
- const primitiveType = { typeId : type } ;
155
+ private static primitive ( type : IType , value : primitive ) : ITypedValue {
140
156
return {
141
- type : primitiveType ,
142
- value : typeToValue ( primitiveType , value ) ,
157
+ type : type ,
158
+ value : typeToValue ( type , value ) ,
143
159
} ;
144
160
}
145
161
@@ -158,103 +174,115 @@ export class TypedValues {
158
174
}
159
175
160
176
static bool ( value : boolean ) : ITypedValue {
161
- return TypedValues . primitive ( Type . PrimitiveTypeId . BOOL , value ) ;
177
+ return TypedValues . primitive ( Types . BOOL , value ) ;
162
178
}
163
179
164
180
static int8 ( value : number ) : ITypedValue {
165
- return TypedValues . primitive ( Type . PrimitiveTypeId . INT8 , value ) ;
181
+ return TypedValues . primitive ( Types . INT8 , value ) ;
166
182
}
167
183
168
184
static uint8 ( value : number ) : ITypedValue {
169
- return TypedValues . primitive ( Type . PrimitiveTypeId . UINT8 , value ) ;
185
+ return TypedValues . primitive ( Types . UINT8 , value ) ;
170
186
}
171
187
172
188
static int16 ( value : number ) : ITypedValue {
173
- return TypedValues . primitive ( Type . PrimitiveTypeId . INT16 , value ) ;
189
+ return TypedValues . primitive ( Types . INT16 , value ) ;
174
190
}
175
191
176
192
static uint16 ( value : number ) : ITypedValue {
177
- return TypedValues . primitive ( Type . PrimitiveTypeId . UINT16 , value ) ;
193
+ return TypedValues . primitive ( Types . UINT16 , value ) ;
178
194
}
179
195
180
196
static int32 ( value : number ) : ITypedValue {
181
- return TypedValues . primitive ( Type . PrimitiveTypeId . INT32 , value ) ;
197
+ return TypedValues . primitive ( Types . INT32 , value ) ;
182
198
}
183
199
184
200
static uint32 ( value : number ) : ITypedValue {
185
- return TypedValues . primitive ( Type . PrimitiveTypeId . UINT32 , value ) ;
201
+ return TypedValues . primitive ( Types . UINT32 , value ) ;
186
202
}
187
203
188
204
static int64 ( value : number | Long ) : ITypedValue {
189
- return TypedValues . primitive ( Type . PrimitiveTypeId . INT64 , value ) ;
205
+ return TypedValues . primitive ( Types . INT64 , value ) ;
190
206
}
191
207
192
208
static uint64 ( value : number | Long ) : ITypedValue {
193
- return TypedValues . primitive ( Type . PrimitiveTypeId . UINT64 , value ) ;
209
+ return TypedValues . primitive ( Types . UINT64 , value ) ;
194
210
}
195
211
196
212
static float ( value : number ) : ITypedValue {
197
- return TypedValues . primitive ( Type . PrimitiveTypeId . FLOAT , value ) ;
213
+ return TypedValues . primitive ( Types . FLOAT , value ) ;
198
214
}
199
215
200
216
static double ( value : number ) : ITypedValue {
201
- return TypedValues . primitive ( Type . PrimitiveTypeId . DOUBLE , value ) ;
217
+ return TypedValues . primitive ( Types . DOUBLE , value ) ;
202
218
}
203
219
204
220
static string ( value : string ) : ITypedValue {
205
- return TypedValues . primitive ( Type . PrimitiveTypeId . STRING , value ) ;
221
+ warnDeprecation (
222
+ 'string() helper is deprecated and will be removed in the next major release. Please migrate ' +
223
+ 'to the newer helper bytes() which avoids implicit conversions between Buffer and string types.'
224
+ ) ;
225
+ return TypedValues . primitive ( Types . STRING , value ) ;
226
+ }
227
+
228
+ static bytes ( value : Buffer ) : ITypedValue {
229
+ return TypedValues . primitive ( Types . BYTES , value ) ;
206
230
}
207
231
208
232
static utf8 ( value : string ) : ITypedValue {
209
- return TypedValues . primitive ( Type . PrimitiveTypeId . UTF8 , value ) ;
233
+ return TypedValues . primitive ( Types . UTF8 , value ) ;
234
+ }
235
+
236
+ static text ( value : string ) : ITypedValue {
237
+ return TypedValues . primitive ( Types . TEXT , value ) ;
210
238
}
211
239
212
240
static yson ( value : string ) : ITypedValue {
213
- return TypedValues . primitive ( Type . PrimitiveTypeId . YSON , value ) ;
241
+ return TypedValues . primitive ( Types . YSON , value ) ;
214
242
}
215
243
216
244
static json ( value : string ) : ITypedValue {
217
- return TypedValues . primitive ( Type . PrimitiveTypeId . JSON , value ) ;
245
+ return TypedValues . primitive ( Types . JSON , value ) ;
218
246
}
219
247
220
248
static uuid ( value : string ) : ITypedValue {
221
- return TypedValues . primitive ( Type . PrimitiveTypeId . UUID , value ) ;
249
+ return TypedValues . primitive ( Types . UUID , value ) ;
222
250
}
223
251
224
252
static jsonDocument ( value : string ) : ITypedValue {
225
- return TypedValues . primitive ( Type . PrimitiveTypeId . JSON_DOCUMENT , value ) ;
253
+ return TypedValues . primitive ( Types . JSON_DOCUMENT , value ) ;
226
254
}
227
255
228
256
static date ( value : Date ) : ITypedValue {
229
- return TypedValues . primitive ( Type . PrimitiveTypeId . DATE , value ) ;
257
+ return TypedValues . primitive ( Types . DATE , value ) ;
230
258
}
231
259
232
260
static datetime ( value : Date ) : ITypedValue {
233
- return TypedValues . primitive ( Type . PrimitiveTypeId . DATETIME , value ) ;
261
+ return TypedValues . primitive ( Types . DATETIME , value ) ;
234
262
}
235
263
236
264
static timestamp ( value : Date ) : ITypedValue {
237
- return TypedValues . primitive ( Type . PrimitiveTypeId . TIMESTAMP , value ) ;
265
+ return TypedValues . primitive ( Types . TIMESTAMP , value ) ;
238
266
}
239
267
240
268
static interval ( value : number ) : ITypedValue {
241
- return TypedValues . primitive ( Type . PrimitiveTypeId . INTERVAL , value ) ;
269
+ return TypedValues . primitive ( Types . INTERVAL , value ) ;
242
270
}
243
271
244
272
static tzDate ( value : Date ) : ITypedValue {
245
- return TypedValues . primitive ( Type . PrimitiveTypeId . TZ_DATE , value ) ;
273
+ return TypedValues . primitive ( Types . TZ_DATE , value ) ;
246
274
}
247
275
248
276
static tzDatetime ( value : Date ) : ITypedValue {
249
- return TypedValues . primitive ( Type . PrimitiveTypeId . TZ_DATETIME , value ) ;
277
+ return TypedValues . primitive ( Types . TZ_DATETIME , value ) ;
250
278
}
251
279
252
280
static tzTimestamp ( value : Date ) : ITypedValue {
253
- return TypedValues . primitive ( Type . PrimitiveTypeId . TZ_TIMESTAMP , value ) ;
281
+ return TypedValues . primitive ( Types . TZ_TIMESTAMP , value ) ;
254
282
}
255
283
256
284
static dynumber ( value : string ) : ITypedValue {
257
- return TypedValues . primitive ( Type . PrimitiveTypeId . DYNUMBER , value ) ;
285
+ return TypedValues . primitive ( Types . DYNUMBER , value ) ;
258
286
}
259
287
260
288
static optional ( value : Ydb . ITypedValue ) : Ydb . ITypedValue {
@@ -345,7 +373,7 @@ const valueToNativeConverters: Record<string, (input: string|number) => any> = {
345
373
'uint64Value' : ( input ) => parseLong ( input ) ,
346
374
'floatValue' : ( input ) => Number ( input ) ,
347
375
'doubleValue' : ( input ) => Number ( input ) ,
348
- 'bytesValue' : ( input ) => Buffer . from ( input as string , 'base64' ) . toString ( ) ,
376
+ 'bytesValue' : ( input ) => input ,
349
377
'textValue' : ( input ) => input ,
350
378
'nullFlagValue' : ( ) => null ,
351
379
} ;
@@ -360,7 +388,7 @@ function convertYdbValueToNative(type: IType, value: IValue): any {
360
388
throw new Error ( `Unknown PrimitiveTypeId: ${ type . typeId } ` ) ;
361
389
}
362
390
const input = ( value as any ) [ label ] ;
363
- return objectFromValue ( type . typeId , valueToNativeConverters [ label ] ( input ) ) ;
391
+ return objectFromValue ( type , valueToNativeConverters [ label ] ( input ) ) ;
364
392
} else if ( type . decimalType ) {
365
393
const high128 = value . high_128 as number | Long ;
366
394
const low128 = value . low_128 as number | Long ;
@@ -433,8 +461,15 @@ function convertYdbValueToNative(type: IType, value: IValue): any {
433
461
}
434
462
}
435
463
436
- function objectFromValue ( typeId : PrimitiveTypeId , value : unknown ) {
464
+ function objectFromValue ( type : IType , value : unknown ) {
465
+ if ( type === Types . BYTES ) {
466
+ return value as Buffer ;
467
+ }
468
+ const { typeId} = type ;
437
469
switch ( typeId ) {
470
+ case PrimitiveTypeId . YSON :
471
+ case PrimitiveTypeId . STRING :
472
+ return ( value as Buffer ) . toString ( 'utf8' ) ;
438
473
case PrimitiveTypeId . DATE :
439
474
return new Date ( ( value as number ) * 3600 * 1000 * 24 ) ;
440
475
case PrimitiveTypeId . DATETIME :
@@ -452,7 +487,11 @@ function objectFromValue(typeId: PrimitiveTypeId, value: unknown) {
452
487
}
453
488
}
454
489
455
- function preparePrimitiveValue ( typeId : PrimitiveTypeId , value : any ) {
490
+ function preparePrimitiveValue ( type : IType , value : any ) {
491
+ if ( type === Types . BYTES ) {
492
+ return value instanceof Buffer ? value : Buffer . from ( value ) ;
493
+ }
494
+ const typeId = type . typeId ;
456
495
switch ( typeId ) {
457
496
case PrimitiveTypeId . DATE :
458
497
return Number ( value ) / 3600 / 1000 / 24 ;
@@ -484,7 +523,7 @@ function typeToValue(type: IType | null | undefined, value: any): IValue {
484
523
}
485
524
const valueLabel = primitiveTypeToValue [ type . typeId ] ;
486
525
if ( valueLabel ) {
487
- return { [ valueLabel ] : preparePrimitiveValue ( type . typeId , value ) } ;
526
+ return { [ valueLabel ] : preparePrimitiveValue ( type , value ) } ;
488
527
} else {
489
528
throw new Error ( `Unknown PrimitiveTypeId: ${ type . typeId } ` ) ;
490
529
}
0 commit comments