w-orm-lowdb 1.0.2 → 1.0.4
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.
- package/dist/w-orm-lowdb.umd.js +2 -2
- package/dist/w-orm-lowdb.umd.js.map +1 -1
- package/docs/WOrmLowdb.html +41 -41
- package/docs/WOrmLowdb.mjs.html +388 -335
- package/docs/index.html +2 -2
- package/package.json +1 -2
- package/src/WOrmLowdb.mjs +386 -333
package/src/WOrmLowdb.mjs
CHANGED
|
@@ -2,7 +2,6 @@ import events from 'events'
|
|
|
2
2
|
import { Low } from 'lowdb'
|
|
3
3
|
import { JSONFile } from 'lowdb/node'
|
|
4
4
|
import { Query } from 'mingo' //須指定安裝6.5.6, 若6.6.0無法匯入Query
|
|
5
|
-
import { Mutex } from 'async-mutex'
|
|
6
5
|
import get from 'lodash-es/get.js'
|
|
7
6
|
import each from 'lodash-es/each.js'
|
|
8
7
|
import map from 'lodash-es/map.js'
|
|
@@ -18,6 +17,7 @@ import iseobj from 'wsemi/src/iseobj.mjs'
|
|
|
18
17
|
import isearr from 'wsemi/src/isearr.mjs'
|
|
19
18
|
import haskey from 'wsemi/src/haskey.mjs'
|
|
20
19
|
import arrPullAt from 'wsemi/src/arrPullAt.mjs'
|
|
20
|
+
import waitFun from 'wsemi/src/waitFun.mjs'
|
|
21
21
|
|
|
22
22
|
|
|
23
23
|
/**
|
|
@@ -59,9 +59,6 @@ function WOrmLowdb(opt = {}) {
|
|
|
59
59
|
//lowdb
|
|
60
60
|
let lowdb = new Low(adapter, {})
|
|
61
61
|
|
|
62
|
-
//mutex
|
|
63
|
-
let mutex = new Mutex()
|
|
64
|
-
|
|
65
62
|
// //default, 此處偵測會失效, 因操作函數內會通過lowdb.read()初始化, 預設創建空陣列會被取代
|
|
66
63
|
// if (!haskey(lowdb.data, key)) {
|
|
67
64
|
// lowdb.data[key] = []
|
|
@@ -70,6 +67,10 @@ function WOrmLowdb(opt = {}) {
|
|
|
70
67
|
//ee
|
|
71
68
|
let ee = new events.EventEmitter()
|
|
72
69
|
|
|
70
|
+
//全域鎖, 一次僅能執行一種操作函數, 使各類操作url(db.json)時能為獨占模式
|
|
71
|
+
//select理論上是不用鎖, 但因為操作上db.jon.tmp更名回db.json時似乎非rename而是串流寫入, 導致有機會撈到不完整json數據進而出錯, 故還是得要上鎖以策安全
|
|
72
|
+
let glock = false
|
|
73
|
+
|
|
73
74
|
/**
|
|
74
75
|
* 查詢數據
|
|
75
76
|
*
|
|
@@ -77,7 +78,7 @@ function WOrmLowdb(opt = {}) {
|
|
|
77
78
|
* @param {Object} [find={}] 輸入查詢條件物件
|
|
78
79
|
* @returns {Promise} 回傳Promise,resolve回傳數據,reject回傳錯誤訊息
|
|
79
80
|
*/
|
|
80
|
-
async function
|
|
81
|
+
async function selectCore(find = {}) {
|
|
81
82
|
let isErr = false
|
|
82
83
|
|
|
83
84
|
//res
|
|
@@ -119,6 +120,18 @@ function WOrmLowdb(opt = {}) {
|
|
|
119
120
|
}
|
|
120
121
|
return res
|
|
121
122
|
}
|
|
123
|
+
async function select(find = {}) {
|
|
124
|
+
if (glock) {
|
|
125
|
+
await waitFun(() => {
|
|
126
|
+
return !glock
|
|
127
|
+
})
|
|
128
|
+
}
|
|
129
|
+
glock = true
|
|
130
|
+
return await selectCore(find)
|
|
131
|
+
.finally(() => {
|
|
132
|
+
glock = false
|
|
133
|
+
})
|
|
134
|
+
}
|
|
122
135
|
|
|
123
136
|
/**
|
|
124
137
|
* 插入數據,插入同樣數據會自動產生不同_id,故insert前需自行判斷有無重複
|
|
@@ -127,97 +140,107 @@ function WOrmLowdb(opt = {}) {
|
|
|
127
140
|
* @param {Object|Array} data 輸入數據物件或陣列
|
|
128
141
|
* @returns {Promise} 回傳Promise,resolve回傳插入結果,reject回傳錯誤訊息
|
|
129
142
|
*/
|
|
130
|
-
async function
|
|
131
|
-
|
|
132
|
-
let isErr = false
|
|
133
|
-
|
|
134
|
-
//check
|
|
135
|
-
if (!iseobj(data) && !isearr(data)) {
|
|
136
|
-
return Promise.reject(`data is not an effective object or array`)
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
//cloneDeep, 與外部數據脫勾
|
|
140
|
-
data = cloneDeep(data)
|
|
143
|
+
async function insertCore(data) {
|
|
144
|
+
let isErr = false
|
|
141
145
|
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
146
|
+
//check
|
|
147
|
+
if (!iseobj(data) && !isearr(data)) {
|
|
148
|
+
return Promise.reject(`data is not an effective object or array`)
|
|
149
|
+
}
|
|
145
150
|
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
data = [data]
|
|
149
|
-
}
|
|
151
|
+
//cloneDeep, 與外部數據脫勾
|
|
152
|
+
data = cloneDeep(data)
|
|
150
153
|
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
v.id = genID()
|
|
155
|
-
}
|
|
156
|
-
return v
|
|
157
|
-
})
|
|
154
|
+
//res
|
|
155
|
+
let res = null
|
|
156
|
+
try {
|
|
158
157
|
|
|
159
|
-
|
|
160
|
-
|
|
158
|
+
//check
|
|
159
|
+
if (!isarr(data)) {
|
|
160
|
+
data = [data]
|
|
161
|
+
}
|
|
161
162
|
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
163
|
+
//check id
|
|
164
|
+
data = map(data, function(v) {
|
|
165
|
+
if (!isestr(v.id)) {
|
|
166
|
+
v.id = genID()
|
|
165
167
|
}
|
|
168
|
+
return v
|
|
169
|
+
})
|
|
166
170
|
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
each(lowdb.data[key], (v, k) => {
|
|
170
|
-
kp[v.id] = { k, v }
|
|
171
|
-
})
|
|
171
|
+
//read
|
|
172
|
+
await lowdb.read()
|
|
172
173
|
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
each(data, (v) => {
|
|
174
|
+
//default, 使用lowdb.read()初始化後須馬上檢測, 若無key則須先創建空陣列
|
|
175
|
+
if (!haskey(lowdb.data, key)) {
|
|
176
|
+
lowdb.data[key] = []
|
|
177
|
+
}
|
|
178
178
|
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
179
|
+
//kp
|
|
180
|
+
let kp = {}
|
|
181
|
+
each(lowdb.data[key], (v, k) => {
|
|
182
|
+
kp[v.id] = { k, v }
|
|
183
|
+
})
|
|
182
184
|
|
|
183
|
-
|
|
184
|
-
|
|
185
|
+
//each
|
|
186
|
+
let nAll = size(data)
|
|
187
|
+
let nPush = 0
|
|
188
|
+
let b = false
|
|
189
|
+
each(data, (v) => {
|
|
185
190
|
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
else {
|
|
190
|
-
//已存在v.id則不push
|
|
191
|
-
}
|
|
191
|
+
//check
|
|
192
|
+
if (!haskey(kp, v.id)) {
|
|
193
|
+
//未存在v.id
|
|
192
194
|
|
|
193
|
-
|
|
195
|
+
//push
|
|
196
|
+
lowdb.data[key].push(v)
|
|
194
197
|
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
await lowdb.write()
|
|
198
|
+
nPush++
|
|
199
|
+
b = true
|
|
198
200
|
}
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
res = {
|
|
202
|
-
n: nAll,
|
|
203
|
-
nInserted: nPush,
|
|
204
|
-
ok: 1,
|
|
201
|
+
else {
|
|
202
|
+
//已存在v.id則不push
|
|
205
203
|
}
|
|
206
204
|
|
|
207
|
-
|
|
208
|
-
ee.emit('change', 'insert', data, res)
|
|
205
|
+
})
|
|
209
206
|
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
res = err
|
|
207
|
+
//write
|
|
208
|
+
if (b) {
|
|
209
|
+
await lowdb.write()
|
|
214
210
|
}
|
|
215
211
|
|
|
216
|
-
|
|
217
|
-
|
|
212
|
+
//res
|
|
213
|
+
res = {
|
|
214
|
+
n: nAll,
|
|
215
|
+
nInserted: nPush,
|
|
216
|
+
ok: 1,
|
|
218
217
|
}
|
|
219
|
-
|
|
220
|
-
|
|
218
|
+
|
|
219
|
+
//emit
|
|
220
|
+
ee.emit('change', 'insert', data, res)
|
|
221
|
+
|
|
222
|
+
}
|
|
223
|
+
catch (err) {
|
|
224
|
+
isErr = true
|
|
225
|
+
res = err
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
if (isErr) {
|
|
229
|
+
return Promise.reject(res)
|
|
230
|
+
}
|
|
231
|
+
return res
|
|
232
|
+
}
|
|
233
|
+
async function insert(data) {
|
|
234
|
+
if (glock) {
|
|
235
|
+
await waitFun(() => {
|
|
236
|
+
return !glock
|
|
237
|
+
})
|
|
238
|
+
}
|
|
239
|
+
glock = true
|
|
240
|
+
return await insertCore(data)
|
|
241
|
+
.finally(() => {
|
|
242
|
+
glock = false
|
|
243
|
+
})
|
|
221
244
|
}
|
|
222
245
|
|
|
223
246
|
/**
|
|
@@ -229,122 +252,132 @@ function WOrmLowdb(opt = {}) {
|
|
|
229
252
|
* @param {boolean} [option.autoInsert=true] 輸入是否於儲存時發現原本無數據,則自動改以插入處理,預設為true
|
|
230
253
|
* @returns {Promise} 回傳Promise,resolve回傳儲存結果,reject回傳錯誤訊息
|
|
231
254
|
*/
|
|
232
|
-
async function
|
|
233
|
-
|
|
234
|
-
let isErr = false
|
|
235
|
-
|
|
236
|
-
//check
|
|
237
|
-
if (!iseobj(data) && !isearr(data)) {
|
|
238
|
-
return Promise.reject(`data is not an effective object or array`)
|
|
239
|
-
}
|
|
240
|
-
|
|
241
|
-
//cloneDeep, 與外部數據脫勾
|
|
242
|
-
data = cloneDeep(data)
|
|
255
|
+
async function saveCore(data, option = {}) {
|
|
256
|
+
let isErr = false
|
|
243
257
|
|
|
244
|
-
|
|
245
|
-
|
|
258
|
+
//check
|
|
259
|
+
if (!iseobj(data) && !isearr(data)) {
|
|
260
|
+
return Promise.reject(`data is not an effective object or array`)
|
|
261
|
+
}
|
|
246
262
|
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
try {
|
|
263
|
+
//cloneDeep, 與外部數據脫勾
|
|
264
|
+
data = cloneDeep(data)
|
|
250
265
|
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
data = [data]
|
|
254
|
-
}
|
|
266
|
+
//autoInsert
|
|
267
|
+
let autoInsert = get(option, 'autoInsert', true)
|
|
255
268
|
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
v.id = genID()
|
|
260
|
-
}
|
|
261
|
-
return v
|
|
262
|
-
})
|
|
269
|
+
//res
|
|
270
|
+
let res = null
|
|
271
|
+
try {
|
|
263
272
|
|
|
264
|
-
|
|
265
|
-
|
|
273
|
+
//check
|
|
274
|
+
if (!isarr(data)) {
|
|
275
|
+
data = [data]
|
|
276
|
+
}
|
|
266
277
|
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
278
|
+
//check id
|
|
279
|
+
data = map(data, function(v) {
|
|
280
|
+
if (!isestr(v.id)) {
|
|
281
|
+
v.id = genID()
|
|
270
282
|
}
|
|
283
|
+
return v
|
|
284
|
+
})
|
|
271
285
|
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
each(lowdb.data[key], (v, k) => {
|
|
275
|
-
kp[v.id] = { k, v }
|
|
276
|
-
})
|
|
277
|
-
|
|
278
|
-
//pmSeries
|
|
279
|
-
let b = false
|
|
280
|
-
res = await pmSeries(data, async(v) => {
|
|
286
|
+
//read
|
|
287
|
+
await lowdb.read()
|
|
281
288
|
|
|
282
|
-
|
|
283
|
-
|
|
289
|
+
//default, 使用lowdb.read()初始化後須馬上檢測, 若無key則須先創建空陣列
|
|
290
|
+
if (!haskey(lowdb.data, key)) {
|
|
291
|
+
lowdb.data[key] = []
|
|
292
|
+
}
|
|
284
293
|
|
|
285
|
-
|
|
286
|
-
|
|
294
|
+
//kp
|
|
295
|
+
let kp = {}
|
|
296
|
+
each(lowdb.data[key], (v, k) => {
|
|
297
|
+
kp[v.id] = { k, v }
|
|
298
|
+
})
|
|
287
299
|
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
if (isEqual(v, r.v)) {
|
|
292
|
-
//內容相同不更新
|
|
293
|
-
}
|
|
294
|
-
else {
|
|
295
|
-
//內容不同須更新
|
|
300
|
+
//pmSeries
|
|
301
|
+
let b = false
|
|
302
|
+
res = await pmSeries(data, async(v) => {
|
|
296
303
|
|
|
297
|
-
|
|
298
|
-
|
|
304
|
+
//rest
|
|
305
|
+
let rest = null
|
|
299
306
|
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
}
|
|
303
|
-
}
|
|
307
|
+
//查找資料表內v.id
|
|
308
|
+
let r = get(kp, v.id, null)
|
|
304
309
|
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
ok: 1,
|
|
311
|
-
}
|
|
310
|
+
//check
|
|
311
|
+
if (iseobj(r)) {
|
|
312
|
+
//已存在v.id
|
|
313
|
+
if (isEqual(v, r.v)) {
|
|
314
|
+
//內容相同不更新
|
|
312
315
|
}
|
|
313
316
|
else {
|
|
314
|
-
|
|
315
|
-
n: 0,
|
|
316
|
-
nModified: 0,
|
|
317
|
-
ok: 1,
|
|
318
|
-
}
|
|
319
|
-
}
|
|
317
|
+
//內容不同須更新
|
|
320
318
|
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
319
|
+
//merge
|
|
320
|
+
lowdb.data[key][r.k] = merge(lowdb.data[key][r.k], v)
|
|
321
|
+
|
|
322
|
+
rest = { update: true }
|
|
323
|
+
b = true
|
|
324
324
|
}
|
|
325
|
+
}
|
|
325
326
|
|
|
326
|
-
|
|
327
|
-
|
|
327
|
+
//rest
|
|
328
|
+
if (iseobj(rest)) {
|
|
329
|
+
rest = {
|
|
330
|
+
n: 1,
|
|
331
|
+
nModified: 1,
|
|
332
|
+
ok: 1,
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
else {
|
|
336
|
+
rest = {
|
|
337
|
+
n: 0,
|
|
338
|
+
nModified: 0,
|
|
339
|
+
ok: 1,
|
|
340
|
+
}
|
|
341
|
+
}
|
|
328
342
|
|
|
329
|
-
//
|
|
330
|
-
if (
|
|
331
|
-
await
|
|
343
|
+
//autoInsert
|
|
344
|
+
if (autoInsert && rest.n === 0) {
|
|
345
|
+
rest = await insertCore(v)
|
|
332
346
|
}
|
|
333
347
|
|
|
334
|
-
|
|
335
|
-
|
|
348
|
+
return rest
|
|
349
|
+
})
|
|
336
350
|
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
res = err
|
|
351
|
+
//write
|
|
352
|
+
if (b) {
|
|
353
|
+
await lowdb.write()
|
|
341
354
|
}
|
|
342
355
|
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
356
|
+
//emit
|
|
357
|
+
ee.emit('change', 'save', data, res)
|
|
358
|
+
|
|
359
|
+
}
|
|
360
|
+
catch (err) {
|
|
361
|
+
isErr = true
|
|
362
|
+
res = err
|
|
363
|
+
}
|
|
364
|
+
|
|
365
|
+
if (isErr) {
|
|
366
|
+
return Promise.reject(res)
|
|
367
|
+
}
|
|
368
|
+
return res
|
|
369
|
+
}
|
|
370
|
+
async function save(data, option = {}) {
|
|
371
|
+
if (glock) {
|
|
372
|
+
await waitFun(() => {
|
|
373
|
+
return !glock
|
|
374
|
+
})
|
|
375
|
+
}
|
|
376
|
+
glock = true
|
|
377
|
+
return await saveCore(data, option)
|
|
378
|
+
.finally(() => {
|
|
379
|
+
glock = false
|
|
380
|
+
})
|
|
348
381
|
}
|
|
349
382
|
|
|
350
383
|
/**
|
|
@@ -354,127 +387,137 @@ function WOrmLowdb(opt = {}) {
|
|
|
354
387
|
* @param {Object|Array} data 輸入數據物件或陣列
|
|
355
388
|
* @returns {Promise} 回傳Promise,resolve回傳刪除結果,reject回傳錯誤訊息
|
|
356
389
|
*/
|
|
357
|
-
async function
|
|
358
|
-
|
|
359
|
-
let isErr = false
|
|
360
|
-
|
|
361
|
-
//check
|
|
362
|
-
if (!iseobj(data) && !isearr(data)) {
|
|
363
|
-
return Promise.reject(`data is not an effective object or array`)
|
|
364
|
-
}
|
|
365
|
-
|
|
366
|
-
//cloneDeep, 與外部數據脫勾
|
|
367
|
-
data = cloneDeep(data)
|
|
368
|
-
|
|
369
|
-
//res
|
|
370
|
-
let res = null
|
|
371
|
-
try {
|
|
390
|
+
async function delCore(data) {
|
|
391
|
+
let isErr = false
|
|
372
392
|
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
393
|
+
//check
|
|
394
|
+
if (!iseobj(data) && !isearr(data)) {
|
|
395
|
+
return Promise.reject(`data is not an effective object or array`)
|
|
396
|
+
}
|
|
377
397
|
|
|
378
|
-
|
|
379
|
-
|
|
398
|
+
//cloneDeep, 與外部數據脫勾
|
|
399
|
+
data = cloneDeep(data)
|
|
380
400
|
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
}
|
|
401
|
+
//res
|
|
402
|
+
let res = null
|
|
403
|
+
try {
|
|
385
404
|
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
})
|
|
405
|
+
//check
|
|
406
|
+
if (!isarr(data)) {
|
|
407
|
+
data = [data]
|
|
408
|
+
}
|
|
391
409
|
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
let b = false
|
|
395
|
-
res = await pmSeries(data, async(v) => {
|
|
410
|
+
//read
|
|
411
|
+
await lowdb.read()
|
|
396
412
|
|
|
397
|
-
|
|
398
|
-
|
|
413
|
+
//default, 使用lowdb.read()初始化後須馬上檢測, 若無key則須先創建空陣列
|
|
414
|
+
if (!haskey(lowdb.data, key)) {
|
|
415
|
+
lowdb.data[key] = []
|
|
416
|
+
}
|
|
399
417
|
|
|
400
|
-
|
|
401
|
-
|
|
418
|
+
//kp
|
|
419
|
+
let kp = {}
|
|
420
|
+
each(lowdb.data[key], (v, k) => {
|
|
421
|
+
kp[v.id] = { k, v }
|
|
422
|
+
})
|
|
402
423
|
|
|
403
|
-
|
|
404
|
-
|
|
424
|
+
//pmSeries
|
|
425
|
+
let ks = []
|
|
426
|
+
let b = false
|
|
427
|
+
res = await pmSeries(data, async(v) => {
|
|
405
428
|
|
|
406
|
-
|
|
407
|
-
|
|
429
|
+
//rest
|
|
430
|
+
let rest = null
|
|
408
431
|
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
//已存在v.id則須刪除
|
|
432
|
+
//id
|
|
433
|
+
let id = get(v, 'id', '')
|
|
412
434
|
|
|
413
|
-
|
|
414
|
-
|
|
435
|
+
//check
|
|
436
|
+
if (isestr(id)) {
|
|
415
437
|
|
|
416
|
-
|
|
438
|
+
//查找資料表內v.id為_v
|
|
439
|
+
let r = get(kp, id, null)
|
|
417
440
|
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
nDeleted: 1,
|
|
422
|
-
ok: 1,
|
|
423
|
-
}
|
|
441
|
+
//check
|
|
442
|
+
if (iseobj(r)) {
|
|
443
|
+
//已存在v.id則須刪除
|
|
424
444
|
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
//不存在v.id則不刪除
|
|
445
|
+
//push
|
|
446
|
+
ks.push(r.k)
|
|
428
447
|
|
|
429
|
-
|
|
430
|
-
rest = {
|
|
431
|
-
n: 1,
|
|
432
|
-
nDeleted: 0,
|
|
433
|
-
ok: 1,
|
|
434
|
-
}
|
|
448
|
+
b = true
|
|
435
449
|
|
|
450
|
+
//rest
|
|
451
|
+
rest = {
|
|
452
|
+
n: 1,
|
|
453
|
+
nDeleted: 1,
|
|
454
|
+
ok: 1,
|
|
436
455
|
}
|
|
437
456
|
|
|
438
457
|
}
|
|
439
458
|
else {
|
|
440
|
-
|
|
459
|
+
//不存在v.id則不刪除
|
|
441
460
|
|
|
442
461
|
//rest
|
|
443
462
|
rest = {
|
|
444
463
|
n: 1,
|
|
445
464
|
nDeleted: 0,
|
|
446
|
-
ok:
|
|
465
|
+
ok: 1,
|
|
447
466
|
}
|
|
448
467
|
|
|
449
468
|
}
|
|
450
469
|
|
|
451
|
-
return rest
|
|
452
|
-
})
|
|
453
|
-
|
|
454
|
-
//update
|
|
455
|
-
if (b) {
|
|
456
|
-
lowdb.data[key] = arrPullAt(lowdb.data[key], ks)
|
|
457
470
|
}
|
|
471
|
+
else {
|
|
472
|
+
//未給v.id則不刪除
|
|
473
|
+
|
|
474
|
+
//rest
|
|
475
|
+
rest = {
|
|
476
|
+
n: 1,
|
|
477
|
+
nDeleted: 0,
|
|
478
|
+
ok: 0, //未給v.id視為有問題數據, 故ok給0
|
|
479
|
+
}
|
|
458
480
|
|
|
459
|
-
//write
|
|
460
|
-
if (b) {
|
|
461
|
-
await lowdb.write()
|
|
462
481
|
}
|
|
463
482
|
|
|
464
|
-
|
|
465
|
-
|
|
483
|
+
return rest
|
|
484
|
+
})
|
|
466
485
|
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
res = err
|
|
486
|
+
//update
|
|
487
|
+
if (b) {
|
|
488
|
+
lowdb.data[key] = arrPullAt(lowdb.data[key], ks)
|
|
471
489
|
}
|
|
472
490
|
|
|
473
|
-
|
|
474
|
-
|
|
491
|
+
//write
|
|
492
|
+
if (b) {
|
|
493
|
+
await lowdb.write()
|
|
475
494
|
}
|
|
476
|
-
|
|
477
|
-
|
|
495
|
+
|
|
496
|
+
//emit
|
|
497
|
+
ee.emit('change', 'del', data, res)
|
|
498
|
+
|
|
499
|
+
}
|
|
500
|
+
catch (err) {
|
|
501
|
+
isErr = true
|
|
502
|
+
res = err
|
|
503
|
+
}
|
|
504
|
+
|
|
505
|
+
if (isErr) {
|
|
506
|
+
return Promise.reject(res)
|
|
507
|
+
}
|
|
508
|
+
return res
|
|
509
|
+
}
|
|
510
|
+
async function del(data) {
|
|
511
|
+
if (glock) {
|
|
512
|
+
await waitFun(() => {
|
|
513
|
+
return !glock
|
|
514
|
+
})
|
|
515
|
+
}
|
|
516
|
+
glock = true
|
|
517
|
+
return await delCore(data)
|
|
518
|
+
.finally(() => {
|
|
519
|
+
glock = false
|
|
520
|
+
})
|
|
478
521
|
}
|
|
479
522
|
|
|
480
523
|
/**
|
|
@@ -484,112 +527,122 @@ function WOrmLowdb(opt = {}) {
|
|
|
484
527
|
* @param {Object} [find={}] 輸入刪除條件物件
|
|
485
528
|
* @returns {Promise} 回傳Promise,resolve回傳刪除結果,reject回傳錯誤訊息
|
|
486
529
|
*/
|
|
487
|
-
async function
|
|
488
|
-
|
|
489
|
-
let isErr = false
|
|
490
|
-
|
|
491
|
-
//res
|
|
492
|
-
let res = null
|
|
493
|
-
try {
|
|
494
|
-
|
|
495
|
-
//read
|
|
496
|
-
await lowdb.read()
|
|
497
|
-
|
|
498
|
-
//default, 使用lowdb.read()初始化後須馬上檢測, 若無key則須先創建空陣列
|
|
499
|
-
if (!haskey(lowdb.data, key)) {
|
|
500
|
-
lowdb.data[key] = []
|
|
501
|
-
}
|
|
530
|
+
async function delAllCore(find = {}) {
|
|
531
|
+
let isErr = false
|
|
502
532
|
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
let b = false
|
|
507
|
-
if (iseobj(find)) {
|
|
533
|
+
//res
|
|
534
|
+
let res = null
|
|
535
|
+
try {
|
|
508
536
|
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
// console.log('q', q)
|
|
537
|
+
//read
|
|
538
|
+
await lowdb.read()
|
|
512
539
|
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
540
|
+
//default, 使用lowdb.read()初始化後須馬上檢測, 若無key則須先創建空陣列
|
|
541
|
+
if (!haskey(lowdb.data, key)) {
|
|
542
|
+
lowdb.data[key] = []
|
|
543
|
+
}
|
|
516
544
|
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
545
|
+
//filter
|
|
546
|
+
let nAll = size(lowdb.data[key])
|
|
547
|
+
let nDel = 0
|
|
548
|
+
let b = false
|
|
549
|
+
if (iseobj(find)) {
|
|
520
550
|
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
else if (nAll === nDel) {
|
|
525
|
-
//全在find結果內等於全部刪除
|
|
551
|
+
//q
|
|
552
|
+
let q = new Query(find)
|
|
553
|
+
// console.log('q', q)
|
|
526
554
|
|
|
527
|
-
|
|
528
|
-
|
|
555
|
+
//find
|
|
556
|
+
let _res = q.find(lowdb.data[key]).all()
|
|
557
|
+
// console.log('_res', _res)
|
|
529
558
|
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
//部份在find結果內
|
|
534
|
-
|
|
535
|
-
//_kp
|
|
536
|
-
let _kp = {}
|
|
537
|
-
each(_res, (v, k) => {
|
|
538
|
-
_kp[v.id] = { k, v }
|
|
539
|
-
})
|
|
540
|
-
|
|
541
|
-
//arr
|
|
542
|
-
let arr = []
|
|
543
|
-
each(lowdb.data[key], (v, k) => {
|
|
544
|
-
if (!haskey(_kp, v.id)) {
|
|
545
|
-
//未在find結果內代表須保留
|
|
546
|
-
arr.push(v)
|
|
547
|
-
}
|
|
548
|
-
})
|
|
549
|
-
|
|
550
|
-
//update
|
|
551
|
-
lowdb.data[key] = arr
|
|
559
|
+
//nDel
|
|
560
|
+
nDel = size(_res)
|
|
561
|
+
// console.log('nDel', nDel)
|
|
552
562
|
|
|
553
|
-
|
|
554
|
-
|
|
563
|
+
if (nDel === 0) {
|
|
564
|
+
//未有find結果等於不刪除
|
|
555
565
|
}
|
|
556
|
-
else {
|
|
557
|
-
|
|
558
|
-
//nDel
|
|
559
|
-
nDel = nAll
|
|
566
|
+
else if (nAll === nDel) {
|
|
567
|
+
//全在find結果內等於全部刪除
|
|
560
568
|
|
|
561
569
|
//empty
|
|
562
570
|
lowdb.data[key] = []
|
|
563
571
|
|
|
564
572
|
b = true
|
|
565
573
|
}
|
|
574
|
+
else {
|
|
575
|
+
//部份在find結果內
|
|
576
|
+
|
|
577
|
+
//_kp
|
|
578
|
+
let _kp = {}
|
|
579
|
+
each(_res, (v, k) => {
|
|
580
|
+
_kp[v.id] = { k, v }
|
|
581
|
+
})
|
|
582
|
+
|
|
583
|
+
//arr
|
|
584
|
+
let arr = []
|
|
585
|
+
each(lowdb.data[key], (v, k) => {
|
|
586
|
+
if (!haskey(_kp, v.id)) {
|
|
587
|
+
//未在find結果內代表須保留
|
|
588
|
+
arr.push(v)
|
|
589
|
+
}
|
|
590
|
+
})
|
|
566
591
|
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
await lowdb.write()
|
|
570
|
-
}
|
|
592
|
+
//update
|
|
593
|
+
lowdb.data[key] = arr
|
|
571
594
|
|
|
572
|
-
|
|
573
|
-
res = {
|
|
574
|
-
n: nAll,
|
|
575
|
-
nDeleted: nDel,
|
|
576
|
-
ok: 1,
|
|
595
|
+
b = true
|
|
577
596
|
}
|
|
597
|
+
}
|
|
598
|
+
else {
|
|
578
599
|
|
|
579
|
-
//
|
|
580
|
-
|
|
600
|
+
//nDel
|
|
601
|
+
nDel = nAll
|
|
602
|
+
|
|
603
|
+
//empty
|
|
604
|
+
lowdb.data[key] = []
|
|
581
605
|
|
|
606
|
+
b = true
|
|
582
607
|
}
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
608
|
+
|
|
609
|
+
//write
|
|
610
|
+
if (b) {
|
|
611
|
+
await lowdb.write()
|
|
586
612
|
}
|
|
587
613
|
|
|
588
|
-
|
|
589
|
-
|
|
614
|
+
//res
|
|
615
|
+
res = {
|
|
616
|
+
n: nAll,
|
|
617
|
+
nDeleted: nDel,
|
|
618
|
+
ok: 1,
|
|
590
619
|
}
|
|
591
|
-
|
|
592
|
-
|
|
620
|
+
|
|
621
|
+
//emit
|
|
622
|
+
ee.emit('change', 'delAll', null, res)
|
|
623
|
+
|
|
624
|
+
}
|
|
625
|
+
catch (err) {
|
|
626
|
+
isErr = true
|
|
627
|
+
res = err
|
|
628
|
+
}
|
|
629
|
+
|
|
630
|
+
if (isErr) {
|
|
631
|
+
return Promise.reject(res)
|
|
632
|
+
}
|
|
633
|
+
return res
|
|
634
|
+
}
|
|
635
|
+
async function delAll(find = {}) {
|
|
636
|
+
if (glock) {
|
|
637
|
+
await waitFun(() => {
|
|
638
|
+
return !glock
|
|
639
|
+
})
|
|
640
|
+
}
|
|
641
|
+
glock = true
|
|
642
|
+
return await delAllCore(find)
|
|
643
|
+
.finally(() => {
|
|
644
|
+
glock = false
|
|
645
|
+
})
|
|
593
646
|
}
|
|
594
647
|
|
|
595
648
|
//bind
|