nesoi 3.4.0 → 3.4.1
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/lib/compiler/elements/bucket.element.js +3 -3
- package/lib/elements/entities/bucket/adapters/memory.nql.js +12 -18
- package/lib/elements/entities/bucket/bucket.d.ts +6 -2
- package/lib/elements/entities/bucket/bucket.js +4 -4
- package/lib/elements/entities/bucket/graph/bucket_graph.js +13 -3
- package/lib/elements/entities/bucket/model/bucket_model.convert.js +9 -17
- package/lib/elements/entities/bucket/model/bucket_model.d.ts +6 -1
- package/lib/elements/entities/bucket/model/bucket_model.js +182 -33
- package/lib/elements/entities/bucket/model/bucket_model.schema.d.ts +1 -1
- package/lib/elements/entities/bucket/model/bucket_model.schema.js +2 -2
- package/lib/elements/entities/bucket/query/nql.schema.d.ts +1 -0
- package/lib/elements/entities/bucket/query/nql_compiler.js +5 -4
- package/lib/elements/entities/bucket/query/nql_engine.js +0 -2
- package/lib/elements/entities/bucket/view/bucket_view.d.ts +5 -4
- package/lib/elements/entities/bucket/view/bucket_view.js +300 -188
- package/lib/elements/entities/bucket/view/bucket_view.schema.d.ts +5 -3
- package/lib/elements/entities/bucket/view/bucket_view.schema.js +3 -1
- package/lib/elements/entities/bucket/view/bucket_view_field.builder.d.ts +15 -5
- package/lib/elements/entities/bucket/view/bucket_view_field.builder.js +82 -28
- package/lib/engine/data/error.d.ts +12 -0
- package/lib/engine/data/error.js +12 -0
- package/lib/engine/transaction/nodes/bucket.trx_node.d.ts +6 -2
- package/lib/engine/transaction/nodes/bucket.trx_node.js +4 -4
- package/lib/engine/transaction/nodes/external.trx_node.d.ts +4 -1
- package/lib/engine/transaction/nodes/external.trx_node.js +5 -2
- package/lib/engine/transaction/nodes/job.trx_node.js +0 -1
- package/lib/engine/transaction/trx_engine.js +8 -10
- package/package.json +1 -1
- package/tools/joaquin/bucket.d.ts +6 -2
- package/tools/joaquin/bucket.js +4 -4
- package/tsconfig.build.tsbuildinfo +1 -1
|
@@ -10,6 +10,7 @@ const error_1 = require("../../../../engine/data/error");
|
|
|
10
10
|
const tree_1 = require("../../../../engine/data/tree");
|
|
11
11
|
const daemon_1 = require("../../../../engine/daemon");
|
|
12
12
|
const dependency_1 = require("../../../../engine/dependency");
|
|
13
|
+
const bucket_model_1 = require("../model/bucket_model");
|
|
13
14
|
class ViewValue {
|
|
14
15
|
value = undefined;
|
|
15
16
|
constructor() { }
|
|
@@ -25,22 +26,24 @@ class BucketView {
|
|
|
25
26
|
this.bucket = bucket;
|
|
26
27
|
this.schema = schema;
|
|
27
28
|
}
|
|
28
|
-
async parse(trx,
|
|
29
|
+
async parse(trx, root, flags) {
|
|
29
30
|
const module = trx_node_1.TrxNode.getModule(trx);
|
|
30
31
|
const tag = new dependency_1.Tag(this.bucket.module.name, 'bucket', this.bucket.schema.name);
|
|
31
32
|
const meta = await daemon_1.Daemon.getBucketMetadata(module.daemon, tag);
|
|
32
33
|
const parsed = {};
|
|
33
|
-
if ('
|
|
34
|
-
Object.assign(parsed,
|
|
34
|
+
if ('__root' in this.schema.fields || '__parent' in this.schema.fields || '__value' in this.schema.fields) {
|
|
35
|
+
Object.assign(parsed, root);
|
|
35
36
|
}
|
|
36
37
|
let layer = Object.values(this.schema.fields).map(field => ({
|
|
37
38
|
bucket: meta,
|
|
38
39
|
field,
|
|
39
40
|
data: [{
|
|
40
|
-
|
|
41
|
-
|
|
41
|
+
root,
|
|
42
|
+
parent: root,
|
|
42
43
|
index: [],
|
|
43
|
-
|
|
44
|
+
value: root,
|
|
45
|
+
target: parsed,
|
|
46
|
+
key: field.name
|
|
44
47
|
}]
|
|
45
48
|
}));
|
|
46
49
|
while (layer.length) {
|
|
@@ -48,37 +51,39 @@ class BucketView {
|
|
|
48
51
|
}
|
|
49
52
|
parsed['$v'] = this.schema.name;
|
|
50
53
|
return {
|
|
51
|
-
id:
|
|
54
|
+
id: root.id,
|
|
52
55
|
...parsed
|
|
53
56
|
};
|
|
54
57
|
}
|
|
55
|
-
async parseMany(trx,
|
|
58
|
+
async parseMany(trx, roots, flags) {
|
|
56
59
|
const module = trx_node_1.TrxNode.getModule(trx);
|
|
57
60
|
const tag = new dependency_1.Tag(this.bucket.module.name, 'bucket', this.bucket.schema.name);
|
|
58
61
|
const meta = await daemon_1.Daemon.getBucketMetadata(module.daemon, tag);
|
|
59
62
|
const parseds = [];
|
|
60
|
-
for (const
|
|
63
|
+
for (const root of roots) {
|
|
61
64
|
const parsed = {};
|
|
62
|
-
if ('
|
|
63
|
-
Object.assign(parsed,
|
|
65
|
+
if ('__root' in this.schema.fields || '__parent' in this.schema.fields || '__value' in this.schema.fields) {
|
|
66
|
+
Object.assign(parsed, root);
|
|
64
67
|
}
|
|
65
68
|
parseds.push(parsed);
|
|
66
69
|
}
|
|
67
70
|
let layer = Object.values(this.schema.fields).map(field => ({
|
|
68
71
|
bucket: meta,
|
|
69
72
|
field,
|
|
70
|
-
data:
|
|
71
|
-
|
|
72
|
-
|
|
73
|
+
data: roots.map((root, i) => ({
|
|
74
|
+
root,
|
|
75
|
+
parent: root,
|
|
73
76
|
index: [],
|
|
74
|
-
|
|
77
|
+
value: root,
|
|
78
|
+
target: parseds[i],
|
|
79
|
+
key: field.name
|
|
75
80
|
}))
|
|
76
81
|
}));
|
|
77
82
|
while (layer.length) {
|
|
78
83
|
layer = await this.parseLayer(trx, layer, flags);
|
|
79
84
|
}
|
|
80
|
-
for (let i = 0; i <
|
|
81
|
-
parseds[i].id =
|
|
85
|
+
for (let i = 0; i < roots.length; i++) {
|
|
86
|
+
parseds[i].id = roots[i].id;
|
|
82
87
|
parseds[i]['$v'] = this.schema.name;
|
|
83
88
|
}
|
|
84
89
|
return parseds;
|
|
@@ -115,9 +120,9 @@ class BucketView {
|
|
|
115
120
|
continue;
|
|
116
121
|
if (!node.field.children)
|
|
117
122
|
continue;
|
|
118
|
-
if ('
|
|
123
|
+
if ('__root' in node.field.children || '__parent' in this.schema.fields || '__value' in node.field.children) {
|
|
119
124
|
for (const d of node.data) {
|
|
120
|
-
d.target[
|
|
125
|
+
d.target[d.key] = d.value;
|
|
121
126
|
}
|
|
122
127
|
}
|
|
123
128
|
next.push(...Object.values(node.field.children).map(field => ({
|
|
@@ -126,152 +131,230 @@ class BucketView {
|
|
|
126
131
|
data: node.data
|
|
127
132
|
})));
|
|
128
133
|
}
|
|
129
|
-
// Chains
|
|
130
|
-
for (const node of layer) {
|
|
131
|
-
if (!node.field.chain)
|
|
132
|
-
continue;
|
|
133
|
-
next.push({
|
|
134
|
-
bucket: node.bucket,
|
|
135
|
-
field: node.field.chain,
|
|
136
|
-
data: node.data.map(d => ({
|
|
137
|
-
index: d.index,
|
|
138
|
-
target: d.target,
|
|
139
|
-
raw: d.raw,
|
|
140
|
-
value: d.target[node.field.name]
|
|
141
|
-
}))
|
|
142
|
-
});
|
|
143
|
-
}
|
|
144
134
|
return next;
|
|
145
135
|
}
|
|
136
|
+
toDict(as_dict, data, final = false) {
|
|
137
|
+
const dict = {};
|
|
138
|
+
const next_data = [];
|
|
139
|
+
let poll = data.map(d => ({
|
|
140
|
+
i: 0,
|
|
141
|
+
index: d.index,
|
|
142
|
+
value: d.value,
|
|
143
|
+
target: dict
|
|
144
|
+
}));
|
|
145
|
+
while (poll.length) {
|
|
146
|
+
const next = [];
|
|
147
|
+
for (const entry of poll) {
|
|
148
|
+
const isLeaf = entry.i === as_dict.length - 1;
|
|
149
|
+
const key = entry.index.at(as_dict[entry.i]);
|
|
150
|
+
if (!key) {
|
|
151
|
+
throw new Error(`Invalid view dict argument ${as_dict}`); // TODO: NesoiError
|
|
152
|
+
}
|
|
153
|
+
if (isLeaf) {
|
|
154
|
+
if (final) {
|
|
155
|
+
entry.target[key] = entry.value;
|
|
156
|
+
}
|
|
157
|
+
else {
|
|
158
|
+
entry.target[key] = {};
|
|
159
|
+
next_data.push({
|
|
160
|
+
target: entry.target[key],
|
|
161
|
+
value: entry.value,
|
|
162
|
+
index: entry.index
|
|
163
|
+
});
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
else {
|
|
167
|
+
entry.target[key] = {};
|
|
168
|
+
next.push({
|
|
169
|
+
i: entry.i + 1,
|
|
170
|
+
index: entry.index,
|
|
171
|
+
value: entry.value,
|
|
172
|
+
target: entry.target[key]
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
poll = next;
|
|
177
|
+
}
|
|
178
|
+
return {
|
|
179
|
+
value: dict,
|
|
180
|
+
next: next_data
|
|
181
|
+
};
|
|
182
|
+
}
|
|
146
183
|
/**
|
|
147
184
|
* [model]
|
|
148
185
|
* Read one property from
|
|
149
186
|
*/
|
|
150
187
|
parseModelProp(node, flags) {
|
|
151
|
-
const
|
|
152
|
-
const rawChild = '__raw' in (node.field.children || {});
|
|
153
|
-
const nextData = this.doParseModelProp(node, initAs, rawChild, flags);
|
|
154
|
-
if (!node.field.children)
|
|
155
|
-
return [];
|
|
188
|
+
const nextData = this.doParseModelProp(node, flags);
|
|
156
189
|
const next = [];
|
|
157
|
-
// subview
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
190
|
+
// Add children (subview) to queue
|
|
191
|
+
if (node.field.children) {
|
|
192
|
+
for (const key in node.field.children) {
|
|
193
|
+
if (key === '__root')
|
|
194
|
+
continue;
|
|
195
|
+
if (key === '__parent')
|
|
196
|
+
continue;
|
|
197
|
+
if (key === '__value')
|
|
198
|
+
continue;
|
|
199
|
+
next.push({
|
|
200
|
+
bucket: node.bucket,
|
|
201
|
+
field: node.field.children[key],
|
|
202
|
+
data: nextData.map(d => ({
|
|
203
|
+
...d,
|
|
204
|
+
key: d.key ?? node.field.children[key].name
|
|
205
|
+
}))
|
|
206
|
+
});
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
// Chains
|
|
210
|
+
if (node.field.chain) {
|
|
161
211
|
next.push({
|
|
162
212
|
bucket: node.bucket,
|
|
163
|
-
field: node.field.
|
|
164
|
-
data: nextData
|
|
213
|
+
field: node.field.chain,
|
|
214
|
+
data: nextData.map(d => ({
|
|
215
|
+
root: d.root,
|
|
216
|
+
parent: d.parent,
|
|
217
|
+
index: d.index,
|
|
218
|
+
value: d.value,
|
|
219
|
+
target: d.target,
|
|
220
|
+
key: d.key
|
|
221
|
+
}))
|
|
165
222
|
});
|
|
166
223
|
}
|
|
167
224
|
return next;
|
|
168
225
|
}
|
|
169
|
-
doParseModelProp(node,
|
|
170
|
-
const
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
})
|
|
178
|
-
|
|
179
|
-
|
|
226
|
+
doParseModelProp(node, flags) {
|
|
227
|
+
const model = new bucket_model_1.BucketModel(node.bucket.schema);
|
|
228
|
+
let modelpath = node.field.meta.model.path;
|
|
229
|
+
if (node.field.prop)
|
|
230
|
+
modelpath += '.' + node.field.prop;
|
|
231
|
+
const hasSubview = node.field.children;
|
|
232
|
+
const hasChain = node.field.chain;
|
|
233
|
+
const hasRootSubviewField = '__root' in (node.field.children || {});
|
|
234
|
+
const hasParentSubviewField = '__parent' in (node.field.children || {});
|
|
235
|
+
const hasValueSubviewField = '__value' in (node.field.children || {});
|
|
236
|
+
const nextData = [];
|
|
237
|
+
for (const data of node.data) {
|
|
238
|
+
// Modelpath refers to the whole value
|
|
239
|
+
if (modelpath === '__root') {
|
|
240
|
+
data.target[data.key] = data.root;
|
|
241
|
+
continue;
|
|
242
|
+
}
|
|
243
|
+
if (modelpath === '__parent') {
|
|
244
|
+
data.target[data.key] = data.parent;
|
|
245
|
+
continue;
|
|
246
|
+
}
|
|
247
|
+
if (modelpath === '__value') {
|
|
180
248
|
data.target[data.key] = data.value;
|
|
249
|
+
continue;
|
|
181
250
|
}
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
value: v,
|
|
201
|
-
target: item.target[item.key],
|
|
202
|
-
key: i
|
|
203
|
-
}));
|
|
204
|
-
}
|
|
251
|
+
let node_modelpath = modelpath;
|
|
252
|
+
if (data.index.length) {
|
|
253
|
+
for (let i = 0; i < data.index.length; i++) {
|
|
254
|
+
node_modelpath = node_modelpath.replace(new RegExp('\\$' + i, 'g'), data.index[i].toString());
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
// Copy modelpath value from object
|
|
258
|
+
const value = model.copy(data.parent, 'save', () => !!flags?.serialize, node_modelpath);
|
|
259
|
+
const many = modelpath.split('.').includes('*');
|
|
260
|
+
// Modelpath contains '*', so it returns N results
|
|
261
|
+
if (many) {
|
|
262
|
+
const next = value.map(v => {
|
|
263
|
+
const index = [...data.index, ...v.index];
|
|
264
|
+
if (hasRootSubviewField || hasParentSubviewField || hasValueSubviewField) {
|
|
265
|
+
// Value is not an object, start subview as empty object
|
|
266
|
+
if (typeof v.value !== 'object' || Array.isArray(v.value))
|
|
267
|
+
return { value: v.value, target: {}, index: index };
|
|
268
|
+
// Value is an object, start subview with root/value
|
|
205
269
|
else {
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
: Object.fromEntries(Object.entries(item.value).map(([k]) => [k, {}]));
|
|
209
|
-
return Object.entries(item.value).map(([k, v]) => ({
|
|
210
|
-
index: [...item.index, k],
|
|
211
|
-
raw: item.raw,
|
|
212
|
-
value: v,
|
|
213
|
-
target: item.target[item.key],
|
|
214
|
-
key: k
|
|
215
|
-
}));
|
|
270
|
+
const val = Object.assign({}, hasRootSubviewField ? data.root : {}, hasParentSubviewField ? data.parent : {}, hasValueSubviewField ? v.value : {});
|
|
271
|
+
return { value: v.value, target: val, index: index };
|
|
216
272
|
}
|
|
217
|
-
}
|
|
218
|
-
|
|
273
|
+
}
|
|
274
|
+
else if (hasSubview)
|
|
275
|
+
return { value: v.value, target: {}, index: index };
|
|
276
|
+
else
|
|
277
|
+
return { value: v.value, target: v.value, index: index };
|
|
278
|
+
});
|
|
279
|
+
if (node.field.as_dict) {
|
|
280
|
+
const dict = this.toDict(node.field.as_dict, next, !node.field.children);
|
|
281
|
+
data.target[data.key] = dict.value;
|
|
282
|
+
// Add to be processed by subview
|
|
283
|
+
nextData.push(...dict.next.map((v, i) => ({
|
|
284
|
+
root: data.root,
|
|
285
|
+
parent: data.parent,
|
|
286
|
+
index: v.index,
|
|
287
|
+
value: v.value,
|
|
288
|
+
target: v.target
|
|
289
|
+
})));
|
|
219
290
|
}
|
|
220
|
-
// $1, $2.. or string|number
|
|
221
291
|
else {
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
}
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
:
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
target: item.target,
|
|
244
|
-
key: item.key
|
|
245
|
-
});
|
|
246
|
-
}
|
|
292
|
+
if (hasChain) {
|
|
293
|
+
data.target[data.key] = [];
|
|
294
|
+
nextData.push(...next.map((v, i) => ({
|
|
295
|
+
root: data.root,
|
|
296
|
+
parent: data.parent,
|
|
297
|
+
index: v.index,
|
|
298
|
+
value: v.value,
|
|
299
|
+
target: data.target[data.key],
|
|
300
|
+
key: i.toString()
|
|
301
|
+
})));
|
|
302
|
+
}
|
|
303
|
+
else {
|
|
304
|
+
data.target[data.key] = next.map(v => v.target);
|
|
305
|
+
// Add to be processed by subview
|
|
306
|
+
nextData.push(...next.map((v, i) => ({
|
|
307
|
+
root: data.root,
|
|
308
|
+
parent: data.parent,
|
|
309
|
+
index: v.index,
|
|
310
|
+
value: v.value,
|
|
311
|
+
target: v.target
|
|
312
|
+
})));
|
|
247
313
|
}
|
|
248
|
-
poll = next;
|
|
249
314
|
}
|
|
250
315
|
}
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
316
|
+
// Modelpath does not contain '*', so it returns 1 result
|
|
317
|
+
else {
|
|
318
|
+
const v = value[0];
|
|
319
|
+
const index = [...data.index, ...(v?.index ?? [])];
|
|
320
|
+
let target = v?.value;
|
|
321
|
+
if (hasRootSubviewField || hasParentSubviewField || hasValueSubviewField) {
|
|
322
|
+
// Value is not an object, start subview as empty object
|
|
323
|
+
if (typeof v.value !== 'object' || Array.isArray(v.value))
|
|
324
|
+
target = {};
|
|
325
|
+
// Value is an object, start subview with root/value
|
|
326
|
+
else {
|
|
327
|
+
target = Object.assign({}, hasRootSubviewField ? data.root : {}, hasParentSubviewField ? data.parent : {}, hasValueSubviewField ? v.value : {});
|
|
328
|
+
}
|
|
329
|
+
}
|
|
330
|
+
else if (hasSubview)
|
|
331
|
+
target = {};
|
|
332
|
+
if (target) {
|
|
333
|
+
if (hasChain) {
|
|
334
|
+
nextData.push({
|
|
335
|
+
root: data.root,
|
|
336
|
+
parent: data.parent,
|
|
337
|
+
index: index,
|
|
338
|
+
value: v.value,
|
|
339
|
+
target: data.target,
|
|
340
|
+
key: data.key
|
|
341
|
+
});
|
|
342
|
+
}
|
|
343
|
+
else {
|
|
344
|
+
data.target[data.key] = target;
|
|
345
|
+
// Add to be processed by subview
|
|
346
|
+
nextData.push({
|
|
347
|
+
root: data.root,
|
|
348
|
+
parent: target,
|
|
349
|
+
index: index,
|
|
350
|
+
value: v.value,
|
|
351
|
+
target
|
|
352
|
+
});
|
|
353
|
+
}
|
|
260
354
|
}
|
|
261
355
|
}
|
|
262
356
|
}
|
|
263
|
-
|
|
264
|
-
for (const data of poll) {
|
|
265
|
-
if (node.field.prop) {
|
|
266
|
-
data.target[data.key] = data.target[data.key][node.field.prop];
|
|
267
|
-
}
|
|
268
|
-
}
|
|
269
|
-
return poll.map(p => ({
|
|
270
|
-
index: p.index,
|
|
271
|
-
raw: p.raw,
|
|
272
|
-
value: p.value,
|
|
273
|
-
target: p.target[p.key]
|
|
274
|
-
}));
|
|
357
|
+
return nextData;
|
|
275
358
|
}
|
|
276
359
|
/**
|
|
277
360
|
* [computed]
|
|
@@ -279,7 +362,7 @@ class BucketView {
|
|
|
279
362
|
async parseComputedProp(trx, node) {
|
|
280
363
|
const meta = node.field.meta.computed;
|
|
281
364
|
for (const entry of node.data) {
|
|
282
|
-
entry.target[
|
|
365
|
+
entry.target[entry.key] = await promise_1.default.solve(meta.fn({ trx, root: entry.root, parent: entry.parent, value: entry.value, bucket: node.bucket.schema }));
|
|
283
366
|
}
|
|
284
367
|
}
|
|
285
368
|
/**
|
|
@@ -292,69 +375,77 @@ class BucketView {
|
|
|
292
375
|
// Step 1: Read many links from bucket
|
|
293
376
|
// External
|
|
294
377
|
if (node.bucket.tag.module !== module.name) {
|
|
295
|
-
linksObjs = await trx.bucket(node.bucket.tag.short).readManyLinks(node.data.map(entry => entry.
|
|
296
|
-
meta.path,
|
|
297
|
-
);
|
|
378
|
+
linksObjs = await trx.bucket(node.bucket.tag.short).readManyLinks(node.data.map(entry => entry.parent.id), //ids -> objs -> params
|
|
379
|
+
meta.path, node.data.map(entry => entry.index));
|
|
298
380
|
}
|
|
299
381
|
// Internal
|
|
300
382
|
else {
|
|
301
383
|
const bucket = module.buckets[node.bucket.tag.name];
|
|
302
|
-
linksObjs = await bucket.graph.readManyLinks(trx, node.data.map(entry => entry.
|
|
384
|
+
linksObjs = await bucket.graph.readManyLinks(trx, node.data.map(entry => entry.parent), {
|
|
303
385
|
name: meta.link,
|
|
304
|
-
indexes:
|
|
386
|
+
indexes: node.data.map(entry => entry.index)
|
|
305
387
|
}, { silent: true });
|
|
306
388
|
}
|
|
307
389
|
// Step 2: Initialize target values
|
|
308
390
|
const link = node.bucket.schema.graph.links[meta.link];
|
|
309
391
|
for (let i = 0; i < linksObjs.length; i++) {
|
|
392
|
+
const target = node.data[i].target;
|
|
393
|
+
const key = node.data[i].key;
|
|
310
394
|
if (meta.view) {
|
|
311
395
|
if (link.many) {
|
|
312
|
-
|
|
396
|
+
target[key] = [];
|
|
313
397
|
}
|
|
314
398
|
else {
|
|
315
|
-
|
|
399
|
+
target[key] = linksObjs[i] ? {} : undefined;
|
|
316
400
|
}
|
|
317
401
|
}
|
|
318
402
|
else if (node.field.prop) {
|
|
319
403
|
if (link.many) {
|
|
320
|
-
|
|
404
|
+
target[key] = linksObjs[i].map((link) => link[node.field.prop]);
|
|
321
405
|
}
|
|
322
406
|
else {
|
|
323
|
-
|
|
407
|
+
target[key] = linksObjs[i]?.[node.field.prop];
|
|
324
408
|
}
|
|
325
409
|
}
|
|
326
410
|
else {
|
|
327
|
-
|
|
411
|
+
target[key] = linksObjs[i];
|
|
328
412
|
}
|
|
329
413
|
}
|
|
414
|
+
const schema = node.bucket.schema;
|
|
415
|
+
const otherBucketDep = schema.graph.links[meta.link].bucket;
|
|
416
|
+
const daemon = module.daemon;
|
|
417
|
+
const otherBucket = await daemon_1.Daemon.getBucketMetadata(daemon, otherBucketDep);
|
|
330
418
|
// Step 3: Build view
|
|
331
419
|
let next = [];
|
|
332
420
|
let nextData = linksObjs;
|
|
333
421
|
if (meta.view) {
|
|
334
|
-
const schema = node.bucket.schema;
|
|
335
|
-
const otherBucketDep = schema.graph.links[meta.link].bucket;
|
|
336
|
-
const module = trx_node_1.TrxNode.getModule(trx);
|
|
337
|
-
const daemon = module.daemon;
|
|
338
|
-
const otherBucket = await daemon_1.Daemon.getBucketMetadata(daemon, otherBucketDep);
|
|
339
422
|
const view = otherBucket.schema.views[meta.view];
|
|
340
|
-
const
|
|
423
|
+
const includeRoot = '__root' in view.fields;
|
|
424
|
+
const includeParent = '__parent' in view.fields;
|
|
425
|
+
const includeValue = '__value' in view.fields;
|
|
426
|
+
const v = { ...view.fields };
|
|
427
|
+
delete v['__root'];
|
|
428
|
+
delete v['__parent'];
|
|
429
|
+
delete v['__value'];
|
|
341
430
|
const link = node.bucket.schema.graph.links[meta.link];
|
|
342
431
|
if (link.many) {
|
|
343
432
|
const _links = linksObjs;
|
|
344
433
|
for (let i = 0; i < _links.length; i++) {
|
|
345
|
-
const
|
|
434
|
+
const key = node.data[i].key;
|
|
435
|
+
const target = node.data[i].target[key];
|
|
346
436
|
for (let j = 0; j < _links[i].length; j++) {
|
|
347
437
|
if (node.field.prop) {
|
|
348
438
|
target.push(_links[i][j][node.field.prop]);
|
|
349
439
|
}
|
|
350
440
|
else {
|
|
351
|
-
|
|
441
|
+
const init = Object.assign({ $v: meta.view }, (includeRoot || includeParent || includeValue) ? _links[i][j] : {});
|
|
442
|
+
target.push(init);
|
|
352
443
|
target[j].$v = meta.view;
|
|
353
444
|
}
|
|
354
445
|
}
|
|
355
446
|
}
|
|
356
447
|
if (!node.field.prop) {
|
|
357
|
-
nextData = _links.map((ll, i) => ll.map((l, j) => ({ value: l, target: node.data[i].target[node.
|
|
448
|
+
nextData = _links.map((ll, i) => ll.map((l, j) => ({ value: l, target: node.data[i].target[node.data[i].key][j] }))).flat(1);
|
|
358
449
|
}
|
|
359
450
|
else {
|
|
360
451
|
nextData = [];
|
|
@@ -366,35 +457,38 @@ class BucketView {
|
|
|
366
457
|
for (let i = 0; i < _links.length; i++) {
|
|
367
458
|
if (!_links[i])
|
|
368
459
|
continue;
|
|
460
|
+
const key = node.data[i].key;
|
|
369
461
|
if (node.field.prop) {
|
|
370
|
-
node.data[i].target[
|
|
462
|
+
node.data[i].target[key] = _links[i][node.field.prop];
|
|
371
463
|
}
|
|
372
464
|
else {
|
|
373
|
-
const target = node.data[i].target[
|
|
374
|
-
if (
|
|
465
|
+
const target = node.data[i].target[key];
|
|
466
|
+
if (includeRoot || includeParent || includeValue) {
|
|
375
467
|
Object.assign(target, _links[i]);
|
|
376
468
|
}
|
|
377
469
|
target.$v = meta.view;
|
|
378
470
|
nextData.push({
|
|
379
|
-
value: _links[i], target: node.data[i].target[
|
|
471
|
+
value: _links[i], target: node.data[i].target[key]
|
|
380
472
|
});
|
|
381
473
|
}
|
|
382
474
|
}
|
|
383
475
|
}
|
|
384
476
|
// (still step 3) Add link bucket view fields to queue
|
|
385
477
|
next = [];
|
|
386
|
-
const bucket = await
|
|
478
|
+
// const bucket = await Daemon.getBucketMetadata(module.daemon!, otherBucketDep);
|
|
387
479
|
// Next data is empty if meta.prop is defined, since there's no need to go deeper
|
|
388
480
|
if (nextData.length) {
|
|
389
481
|
for (const field of Object.values(v)) {
|
|
390
482
|
next.push({
|
|
391
|
-
bucket,
|
|
483
|
+
bucket: otherBucket,
|
|
392
484
|
field,
|
|
393
485
|
data: nextData.map($ => ({
|
|
394
|
-
|
|
486
|
+
root: $.value,
|
|
487
|
+
parent: $.value,
|
|
395
488
|
value: $.value,
|
|
396
489
|
index: [],
|
|
397
|
-
target: $.target
|
|
490
|
+
target: $.target,
|
|
491
|
+
key: field.name
|
|
398
492
|
}))
|
|
399
493
|
});
|
|
400
494
|
}
|
|
@@ -406,45 +500,63 @@ class BucketView {
|
|
|
406
500
|
const subview_data = [];
|
|
407
501
|
for (let i = 0; i < linksObjs.length; i++) {
|
|
408
502
|
const objs = linksObjs[i];
|
|
503
|
+
if (!objs)
|
|
504
|
+
continue;
|
|
505
|
+
const key = node.data[i].key;
|
|
409
506
|
let target;
|
|
410
507
|
if (link.many) {
|
|
411
508
|
target = [];
|
|
412
|
-
for (const tobj of node.data[i].target[
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
}
|
|
416
|
-
else {
|
|
417
|
-
target.push({ id: tobj.id });
|
|
418
|
-
}
|
|
509
|
+
for (const tobj of node.data[i].target[key]) {
|
|
510
|
+
const init = Object.assign({ id: tobj.id }, '__root' in node.field.children ? node.data[i].root : {}, '__parent' in node.field.children ? node.data[i].root : {}, '__value' in node.field.children ? tobj : {});
|
|
511
|
+
target.push(init);
|
|
419
512
|
}
|
|
420
|
-
subview_data.push(...objs.map((obj,
|
|
421
|
-
|
|
422
|
-
|
|
513
|
+
subview_data.push(...objs.map((obj, j) => ({
|
|
514
|
+
root: node.data[i].root,
|
|
515
|
+
parent: node.data[i].parent,
|
|
516
|
+
value: { ...obj },
|
|
517
|
+
target: target[j]
|
|
423
518
|
})));
|
|
424
519
|
}
|
|
425
520
|
else {
|
|
426
521
|
target = { id: objs.id };
|
|
427
|
-
if ('
|
|
428
|
-
Object.assign(target, node.data[i].
|
|
522
|
+
if ('__root' in node.field.children) {
|
|
523
|
+
Object.assign(target, node.data[i].root);
|
|
429
524
|
}
|
|
430
|
-
|
|
525
|
+
if ('__parent' in node.field.children) {
|
|
526
|
+
Object.assign(target, node.data[i].parent);
|
|
527
|
+
}
|
|
528
|
+
if ('__value' in node.field.children) {
|
|
529
|
+
Object.assign(target, node.data[i].target[key]);
|
|
530
|
+
}
|
|
531
|
+
subview_data.push({
|
|
532
|
+
root: node.data[i].root,
|
|
533
|
+
parent: node.data[i].parent,
|
|
534
|
+
value: { ...objs },
|
|
535
|
+
target
|
|
536
|
+
});
|
|
431
537
|
}
|
|
432
|
-
node.data[i].target[
|
|
538
|
+
node.data[i].target[key] = target;
|
|
433
539
|
}
|
|
434
540
|
const module = trx_node_1.TrxNode.getModule(trx);
|
|
435
541
|
const subview_bucket = daemon_1.Daemon.getBucketMetadata(module.daemon, link.bucket);
|
|
436
542
|
// Add subview data to queue
|
|
437
543
|
for (const key in node.field.children) {
|
|
438
|
-
if (key === '
|
|
544
|
+
if (key === '__root')
|
|
545
|
+
continue;
|
|
546
|
+
if (key === '__parent')
|
|
547
|
+
continue;
|
|
548
|
+
if (key === '__value')
|
|
439
549
|
continue;
|
|
440
550
|
next.push({
|
|
441
551
|
bucket: subview_bucket,
|
|
442
552
|
field: node.field.children[key],
|
|
443
553
|
data: subview_data.map(data => ({
|
|
444
|
-
|
|
445
|
-
|
|
554
|
+
root: data.root,
|
|
555
|
+
parent: data.value,
|
|
446
556
|
index: [],
|
|
447
|
-
|
|
557
|
+
value: data.value,
|
|
558
|
+
target: data.target,
|
|
559
|
+
key: node.field.children[key].name
|
|
448
560
|
}))
|
|
449
561
|
});
|
|
450
562
|
}
|
|
@@ -462,16 +574,16 @@ class BucketView {
|
|
|
462
574
|
}
|
|
463
575
|
const meta = node.field.meta.drive;
|
|
464
576
|
for (const entry of node.data) {
|
|
465
|
-
const value = tree_1.Tree.get(entry.
|
|
577
|
+
const value = tree_1.Tree.get(entry.root, meta.path);
|
|
466
578
|
if (Array.isArray(value)) {
|
|
467
579
|
const public_urls = [];
|
|
468
580
|
for (const obj of value) {
|
|
469
581
|
public_urls.push(await drive.public(obj));
|
|
470
582
|
}
|
|
471
|
-
entry.target[
|
|
583
|
+
entry.target[entry.key] = public_urls;
|
|
472
584
|
}
|
|
473
585
|
else {
|
|
474
|
-
entry.target[
|
|
586
|
+
entry.target[entry.key] = await drive.public(value);
|
|
475
587
|
}
|
|
476
588
|
}
|
|
477
589
|
}
|