@cloudbase/database 0.11.0 → 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.
Files changed (59) hide show
  1. package/dist/commonjs/transaction/query.d.ts +39 -1
  2. package/dist/commonjs/transaction/query.js +251 -1
  3. package/dist/esm/transaction/query.d.ts +39 -1
  4. package/dist/esm/transaction/query.js +251 -1
  5. package/package.json +1 -1
  6. package/src/transaction/query.ts +355 -2
  7. package/tests/transaction-query.test.ts +657 -0
  8. package/coverage/lcov-report/base.css +0 -224
  9. package/coverage/lcov-report/block-navigation.js +0 -87
  10. package/coverage/lcov-report/favicon.png +0 -0
  11. package/coverage/lcov-report/index.html +0 -101
  12. package/coverage/lcov-report/prettify.css +0 -1
  13. package/coverage/lcov-report/prettify.js +0 -2
  14. package/coverage/lcov-report/sort-arrow-sprite.png +0 -0
  15. package/coverage/lcov-report/sorter.js +0 -210
  16. package/coverage/lcov.info +0 -0
  17. package/dist/esm/aggregate.d.ts.map +0 -1
  18. package/dist/esm/collection.d.ts.map +0 -1
  19. package/dist/esm/command.d.ts.map +0 -1
  20. package/dist/esm/commands/logic.d.ts.map +0 -1
  21. package/dist/esm/commands/query.d.ts.map +0 -1
  22. package/dist/esm/commands/update.d.ts.map +0 -1
  23. package/dist/esm/config/app.config.d.ts.map +0 -1
  24. package/dist/esm/config/error.config.d.ts.map +0 -1
  25. package/dist/esm/const/code.d.ts.map +0 -1
  26. package/dist/esm/constant.d.ts.map +0 -1
  27. package/dist/esm/document.d.ts.map +0 -1
  28. package/dist/esm/geo/index.d.ts.map +0 -1
  29. package/dist/esm/geo/interface.d.ts.map +0 -1
  30. package/dist/esm/geo/lineString.d.ts.map +0 -1
  31. package/dist/esm/geo/multiLineString.d.ts.map +0 -1
  32. package/dist/esm/geo/multiPoint.d.ts.map +0 -1
  33. package/dist/esm/geo/multiPolygon.d.ts.map +0 -1
  34. package/dist/esm/geo/point.d.ts.map +0 -1
  35. package/dist/esm/geo/polygon.d.ts.map +0 -1
  36. package/dist/esm/helper/symbol.d.ts.map +0 -1
  37. package/dist/esm/index.d.ts.map +0 -1
  38. package/dist/esm/lib/util.d.ts.map +0 -1
  39. package/dist/esm/operator-map.d.ts.map +0 -1
  40. package/dist/esm/query.d.ts.map +0 -1
  41. package/dist/esm/regexp/index.d.ts.map +0 -1
  42. package/dist/esm/serializer/common.d.ts.map +0 -1
  43. package/dist/esm/serializer/datatype.d.ts.map +0 -1
  44. package/dist/esm/serializer/query.d.ts.map +0 -1
  45. package/dist/esm/serializer/update.d.ts.map +0 -1
  46. package/dist/esm/serverDate/index.d.ts.map +0 -1
  47. package/dist/esm/transaction/collection.d.ts.map +0 -1
  48. package/dist/esm/transaction/document.d.ts.map +0 -1
  49. package/dist/esm/transaction/index.d.ts.map +0 -1
  50. package/dist/esm/transaction/query.d.ts.map +0 -1
  51. package/dist/esm/typings/index.d.ts.map +0 -1
  52. package/dist/esm/typings/realtime.d.ts.map +0 -1
  53. package/dist/esm/util.d.ts.map +0 -1
  54. package/dist/esm/utils/error.d.ts.map +0 -1
  55. package/dist/esm/utils/msg.d.ts.map +0 -1
  56. package/dist/esm/utils/symbol.d.ts.map +0 -1
  57. package/dist/esm/utils/type.d.ts.map +0 -1
  58. package/dist/esm/utils/utils.d.ts.map +0 -1
  59. package/dist/esm/validate.d.ts.map +0 -1
@@ -1,8 +1,59 @@
1
1
  import { Transaction } from './index'
2
+ import { EJSON } from 'bson'
3
+ import { OrderByDirection, ErrorCode } from '../constant'
4
+ import { Validate } from '../validate'
5
+ import { QuerySerializer } from '../serializer/query'
6
+ import { UpdateSerializer } from '../serializer/update'
7
+ import { Util } from '../util'
8
+
9
+ const GET_DOC = 'database.getInTransaction'
10
+ const UPDATE_DOC = 'database.updateDocInTransaction'
11
+ const DELETE_DOC = 'database.deleteDocInTransaction'
12
+
13
+ interface QueryOrder {
14
+ field?: string
15
+ direction?: 'asc' | 'desc'
16
+ }
17
+
18
+ interface QueryOption {
19
+ limit?: number
20
+ offset?: number
21
+ projection?: Object
22
+ }
23
+
24
+ interface TransactionAPI {
25
+ send(interfaceName: string, param?: any)
26
+ }
27
+
28
+ interface GetResult {
29
+ data: any[]
30
+ requestId: string
31
+ total?: number
32
+ limit?: number
33
+ offset?: number
34
+ }
35
+
36
+ interface UpdateResult {
37
+ requestId: string
38
+ updated: number
39
+ }
40
+
41
+ interface DeleteResult {
42
+ requestId: string
43
+ deleted: number | string
44
+ }
45
+
46
+ interface TcbError {
47
+ requestId: string
48
+ code: string
49
+ message: string
50
+ stack?: string
51
+ }
2
52
 
3
53
  /**
4
- * 查询模块
54
+ * 事务查询模块
5
55
  *
56
+ * 支持 where 条件查询在事务中使用
6
57
  */
7
58
  export class Query {
8
59
  /**
@@ -14,8 +65,310 @@ export class Query {
14
65
 
15
66
  protected _transaction: Transaction
16
67
 
17
- constructor(transaction: Transaction, coll: string) {
68
+ /**
69
+ * 过滤条件
70
+ *
71
+ * @internal
72
+ */
73
+ private _fieldFilters: Object
74
+
75
+ /**
76
+ * 排序条件
77
+ *
78
+ * @internal
79
+ */
80
+ private _fieldOrders: QueryOrder[]
81
+
82
+ /**
83
+ * 查询条件
84
+ *
85
+ * @internal
86
+ */
87
+ private _queryOptions: QueryOption
88
+
89
+ /**
90
+ * 请求实例
91
+ *
92
+ * @internal
93
+ */
94
+ private _request: TransactionAPI
95
+
96
+ /**
97
+ * 事务ID
98
+ *
99
+ * @internal
100
+ */
101
+ private _transactionId: string
102
+
103
+ constructor(
104
+ transaction: Transaction,
105
+ coll: string,
106
+ fieldFilters?: Object,
107
+ fieldOrders?: QueryOrder[],
108
+ queryOptions?: QueryOption
109
+ ) {
18
110
  this._coll = coll
19
111
  this._transaction = transaction
112
+ this._fieldFilters = fieldFilters
113
+ this._fieldOrders = fieldOrders || []
114
+ this._queryOptions = queryOptions || {}
115
+ this._request = this._transaction.getRequestMethod()
116
+ this._transactionId = this._transaction.getTransactionId()
117
+ }
118
+
119
+ /**
120
+ * 查询条件
121
+ *
122
+ * @param query - 查询条件对象
123
+ */
124
+ public where(query: object): Query {
125
+ if (Object.prototype.toString.call(query).slice(8, -1) !== 'Object') {
126
+ throw Error(ErrorCode.QueryParamTypeError)
127
+ }
128
+
129
+ const keys = Object.keys(query)
130
+ const checkFlag = keys.some(item => {
131
+ return query[item] !== undefined
132
+ })
133
+
134
+ if (keys.length && !checkFlag) {
135
+ throw Error(ErrorCode.QueryParamValueError)
136
+ }
137
+
138
+ return new Query(
139
+ this._transaction,
140
+ this._coll,
141
+ QuerySerializer.encode(query),
142
+ this._fieldOrders,
143
+ this._queryOptions
144
+ )
145
+ }
146
+
147
+ /**
148
+ * 设置排序方式
149
+ *
150
+ * @param fieldPath - 字段路径
151
+ * @param directionStr - 排序方式
152
+ */
153
+ public orderBy(fieldPath: string, directionStr: OrderByDirection): Query {
154
+ Validate.isFieldPath(fieldPath)
155
+ Validate.isFieldOrder(directionStr)
156
+
157
+ const newOrder: QueryOrder = {
158
+ field: fieldPath,
159
+ direction: directionStr
160
+ }
161
+ const combinedOrders = this._fieldOrders.concat(newOrder)
162
+
163
+ return new Query(
164
+ this._transaction,
165
+ this._coll,
166
+ this._fieldFilters,
167
+ combinedOrders,
168
+ this._queryOptions
169
+ )
170
+ }
171
+
172
+ /**
173
+ * 设置查询条数
174
+ *
175
+ * @param limit - 限制条数
176
+ */
177
+ public limit(limit: number): Query {
178
+ Validate.isInteger('limit', limit)
179
+
180
+ let option = { ...this._queryOptions }
181
+ option.limit = limit
182
+
183
+ return new Query(
184
+ this._transaction,
185
+ this._coll,
186
+ this._fieldFilters,
187
+ this._fieldOrders,
188
+ option
189
+ )
190
+ }
191
+
192
+ /**
193
+ * 设置偏移量
194
+ *
195
+ * @param offset - 偏移量
196
+ */
197
+ public skip(offset: number): Query {
198
+ Validate.isInteger('offset', offset)
199
+
200
+ let option = { ...this._queryOptions }
201
+ option.offset = offset
202
+
203
+ return new Query(
204
+ this._transaction,
205
+ this._coll,
206
+ this._fieldFilters,
207
+ this._fieldOrders,
208
+ option
209
+ )
210
+ }
211
+
212
+ /**
213
+ * 指定要返回的字段
214
+ *
215
+ * @param projection
216
+ */
217
+ public field(projection: any): Query {
218
+ for (let k in projection) {
219
+ if (projection[k]) {
220
+ if (typeof projection[k] !== 'object') {
221
+ projection[k] = 1
222
+ }
223
+ } else {
224
+ projection[k] = 0
225
+ }
226
+ }
227
+
228
+ let option = { ...this._queryOptions }
229
+ option.projection = projection
230
+
231
+ return new Query(
232
+ this._transaction,
233
+ this._coll,
234
+ this._fieldFilters,
235
+ this._fieldOrders,
236
+ option
237
+ )
238
+ }
239
+
240
+ /**
241
+ * 发起请求获取文档列表(事务内)
242
+ */
243
+ public async get(): Promise<GetResult> {
244
+ let newOrder = []
245
+ if (this._fieldOrders) {
246
+ this._fieldOrders.forEach(order => {
247
+ newOrder.push(order)
248
+ })
249
+ }
250
+
251
+ let param: any = {
252
+ collectionName: this._coll,
253
+ transactionId: this._transactionId
254
+ }
255
+
256
+ if (this._fieldFilters) {
257
+ param.query = this._fieldFilters
258
+ }
259
+ if (newOrder.length > 0) {
260
+ param.order = newOrder
261
+ }
262
+ if (this._queryOptions.offset) {
263
+ param.offset = this._queryOptions.offset
264
+ }
265
+ if (this._queryOptions.limit) {
266
+ param.limit = this._queryOptions.limit < 1000 ? this._queryOptions.limit : 1000
267
+ } else {
268
+ param.limit = 100
269
+ }
270
+ if (this._queryOptions.projection) {
271
+ param.projection = this._queryOptions.projection
272
+ }
273
+
274
+ const res = await this._request.send(GET_DOC, param)
275
+ if (res.code) throw res
276
+
277
+ const data = res.data !== 'null' ? EJSON.parse(res.data) : null
278
+ const documents = data ? (Array.isArray(data) ? Util.formatResDocumentData(data) : [Util.formatField(data)]) : []
279
+
280
+ const result: GetResult = {
281
+ data: documents,
282
+ requestId: res.requestId
283
+ }
284
+ if (res.total !== undefined) result.total = res.total
285
+ if (res.limit !== undefined) result.limit = res.limit
286
+ if (res.offset !== undefined) result.offset = res.offset
287
+
288
+ return result
289
+ }
290
+
291
+ /**
292
+ * 获取总数(事务内)
293
+ */
294
+ public async count(): Promise<{ requestId: string; total: number }> {
295
+ let param: any = {
296
+ collectionName: this._coll,
297
+ transactionId: this._transactionId
298
+ }
299
+
300
+ if (this._fieldFilters) {
301
+ param.query = this._fieldFilters
302
+ }
303
+
304
+ const res = await this._request.send(GET_DOC, param)
305
+ if (res.code) throw res
306
+
307
+ const data = res.data !== 'null' ? EJSON.parse(res.data) : null
308
+ const total = Array.isArray(data) ? data.length : (data ? 1 : 0)
309
+
310
+ return {
311
+ requestId: res.requestId,
312
+ total: res.total !== undefined ? res.total : total
313
+ }
314
+ }
315
+
316
+ /**
317
+ * 发起请求批量更新文档(事务内)
318
+ *
319
+ * @param data - 更新数据
320
+ */
321
+ public async update(data: Object): Promise<UpdateResult> {
322
+ if (!data || typeof data !== 'object') {
323
+ throw new Error('参数必需是非空对象')
324
+ }
325
+
326
+ if (data.hasOwnProperty('_id')) {
327
+ throw new Error('不能更新_id的值')
328
+ }
329
+
330
+ const param = {
331
+ collectionName: this._coll,
332
+ transactionId: this._transactionId,
333
+ query: this._fieldFilters,
334
+ data: EJSON.stringify(
335
+ UpdateSerializer.encode(data),
336
+ { relaxed: false }
337
+ )
338
+ }
339
+
340
+ const res = await this._request.send(UPDATE_DOC, param)
341
+ if (res.code) throw res
342
+
343
+ return {
344
+ ...res,
345
+ updated: EJSON.parse(res.updated)
346
+ }
347
+ }
348
+
349
+ /**
350
+ * 条件删除文档(事务内)
351
+ */
352
+ public async remove(): Promise<DeleteResult> {
353
+ if (Object.keys(this._queryOptions).length > 0) {
354
+ console.warn('`offset`, `limit` and `projection` are not supported in remove() operation')
355
+ }
356
+ if (this._fieldOrders.length > 0) {
357
+ console.warn('`orderBy` is not supported in remove() operation')
358
+ }
359
+
360
+ const param = {
361
+ collectionName: this._coll,
362
+ transactionId: this._transactionId,
363
+ query: this._fieldFilters
364
+ }
365
+
366
+ const res: DeleteResult | TcbError = await this._request.send(DELETE_DOC, param)
367
+ if ((res as TcbError).code) throw res
368
+
369
+ return {
370
+ ...res,
371
+ deleted: EJSON.parse((res as DeleteResult).deleted as any) as any
372
+ }
20
373
  }
21
374
  }