@platforma-open/milaboratories.mixcr-shm-trees.workflow 3.5.1 → 3.6.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.
- package/.turbo/turbo-build.log +5 -2
- package/CHANGELOG.md +7 -0
- package/dist/index.cjs +1 -0
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -0
- package/dist/tengo/tpl/main.plj.gz +0 -0
- package/dist/tengo/tpl/process.plj.gz +0 -0
- package/dist/tengo/tpl/reconstruct-shm-trees.plj.gz +0 -0
- package/dist/tengo/tpl/request-library.plj.gz +0 -0
- package/dist/tengo/tpl/soi.plj.gz +0 -0
- package/package.json +5 -7
- package/src/main.tpl.tengo +8 -4
- package/src/process.tpl.tengo +12 -2
- package/src/reconstruct-shm-trees.tpl.tengo +33 -7
- package/src/request-library.tpl.tengo +42 -0
package/.turbo/turbo-build.log
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
+
WARN Issue while reading "/home/runner/work/mixcr-shm-trees/mixcr-shm-trees/.npmrc". Failed to replace env in config: ${NPMJS_TOKEN}
|
|
1
2
|
|
|
2
|
-
> @platforma-open/milaboratories.mixcr-shm-trees.workflow@3.
|
|
3
|
+
> @platforma-open/milaboratories.mixcr-shm-trees.workflow@3.6.0 build /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow
|
|
3
4
|
> rm -rf dist && pl-tengo check && pl-tengo build
|
|
4
5
|
|
|
5
6
|
Processing "src/export-settings.lib.tengo"...
|
|
@@ -7,6 +8,7 @@ Processing "src/main.tpl.tengo"...
|
|
|
7
8
|
Processing "src/prepare-donor-column.lib.tengo"...
|
|
8
9
|
Processing "src/process.tpl.tengo"...
|
|
9
10
|
Processing "src/reconstruct-shm-trees.tpl.tengo"...
|
|
11
|
+
Processing "src/request-library.tpl.tengo"...
|
|
10
12
|
Processing "src/soi-export.lib.tengo"...
|
|
11
13
|
Processing "src/soi.tpl.tengo"...
|
|
12
14
|
Processing "src/tablesAggregation.lib.tengo"...
|
|
@@ -17,8 +19,9 @@ No syntax errors found.
|
|
|
17
19
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/lib/soi-export.lib.tengo
|
|
18
20
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/lib/tablesAggregation.lib.tengo
|
|
19
21
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/tpl/reconstruct-shm-trees.plj.gz
|
|
22
|
+
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/tpl/request-library.plj.gz
|
|
20
23
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/tpl/soi.plj.gz
|
|
21
24
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/tpl/process.plj.gz
|
|
22
25
|
info: - writing /home/runner/work/mixcr-shm-trees/mixcr-shm-trees/workflow/dist/tengo/tpl/main.plj.gz
|
|
23
|
-
info:
|
|
26
|
+
info: Template Pack build done.
|
|
24
27
|
info: Template Pack build done.
|
package/CHANGELOG.md
CHANGED
package/dist/index.cjs
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
module.exports = { Templates: {
|
|
2
2
|
'reconstruct-shm-trees': { type: 'from-file', path: require.resolve('./tengo/tpl/reconstruct-shm-trees.plj.gz') },
|
|
3
|
+
'request-library': { type: 'from-file', path: require.resolve('./tengo/tpl/request-library.plj.gz') },
|
|
3
4
|
'soi': { type: 'from-file', path: require.resolve('./tengo/tpl/soi.plj.gz') },
|
|
4
5
|
'process': { type: 'from-file', path: require.resolve('./tengo/tpl/process.plj.gz') },
|
|
5
6
|
'main': { type: 'from-file', path: require.resolve('./tengo/tpl/main.plj.gz') }
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
declare type TemplateFromFile = { readonly type: "from-file"; readonly path: string; };
|
|
2
|
-
declare type TplName = "reconstruct-shm-trees" | "soi" | "process" | "main";
|
|
2
|
+
declare type TplName = "reconstruct-shm-trees" | "request-library" | "soi" | "process" | "main";
|
|
3
3
|
declare const Templates: Record<TplName, TemplateFromFile>;
|
|
4
4
|
export { Templates };
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { resolve } from 'node:path';
|
|
2
2
|
export const Templates = {
|
|
3
3
|
'reconstruct-shm-trees': { type: 'from-file', path: resolve(import.meta.dirname, './tengo/tpl/reconstruct-shm-trees.plj.gz') },
|
|
4
|
+
'request-library': { type: 'from-file', path: resolve(import.meta.dirname, './tengo/tpl/request-library.plj.gz') },
|
|
4
5
|
'soi': { type: 'from-file', path: resolve(import.meta.dirname, './tengo/tpl/soi.plj.gz') },
|
|
5
6
|
'process': { type: 'from-file', path: resolve(import.meta.dirname, './tengo/tpl/process.plj.gz') },
|
|
6
7
|
'main': { type: 'from-file', path: resolve(import.meta.dirname, './tengo/tpl/main.plj.gz') }
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
package/package.json
CHANGED
|
@@ -1,23 +1,21 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@platforma-open/milaboratories.mixcr-shm-trees.workflow",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.6.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Tengo-based template",
|
|
6
6
|
"//": {
|
|
7
7
|
"build": "node ./scripts/build-static.mjs src/pfconv_params.json src/pfconv_params.lib.tengo && rm -rf dist && pl-tengo check && pl-tengo build && ./create_tags.sh"
|
|
8
8
|
},
|
|
9
9
|
"dependencies": {
|
|
10
|
-
"@platforma-sdk/workflow-tengo": "^
|
|
10
|
+
"@platforma-sdk/workflow-tengo": "^4.2.0"
|
|
11
11
|
},
|
|
12
12
|
"devDependencies": {
|
|
13
|
-
"@platforma-sdk/tengo-builder": "^2.
|
|
14
|
-
"@milaboratories/software-pframes-conv": "^2.1.20",
|
|
15
|
-
"@platforma-open/milaboratories.software-small-binaries": "^1.15.19",
|
|
13
|
+
"@platforma-sdk/tengo-builder": "^2.1.3",
|
|
16
14
|
"@platforma-open/milaboratories.software-mixcr": "4.7.0-139-develop",
|
|
17
15
|
"@platforma-open/milaboratories.software-mitool": "2.3.1-5-main",
|
|
18
16
|
"@platforma-open/milaboratories.software-ptransform": "^1.3.1",
|
|
19
|
-
"@platforma-sdk/test": "^1.
|
|
20
|
-
"vitest": "
|
|
17
|
+
"@platforma-sdk/test": "^1.30.4",
|
|
18
|
+
"vitest": "~2.1.8",
|
|
21
19
|
"typescript": "~5.6.3"
|
|
22
20
|
},
|
|
23
21
|
"scripts": {
|
package/src/main.tpl.tengo
CHANGED
|
@@ -6,6 +6,7 @@ ll := import("@platforma-sdk/workflow-tengo:ll")
|
|
|
6
6
|
pframes := import("@platforma-sdk/workflow-tengo:pframes")
|
|
7
7
|
|
|
8
8
|
processTpl := assets.importTemplate(":process")
|
|
9
|
+
requestLibraryTpl := assets.importTemplate(":request-library")
|
|
9
10
|
|
|
10
11
|
wf.body(func(args) {
|
|
11
12
|
if is_undefined(args.donorColumn) {
|
|
@@ -19,13 +20,15 @@ wf.body(func(args) {
|
|
|
19
20
|
// we could not use array as request for waiting (see below), so we store datasets in a dictionary
|
|
20
21
|
datasets := {}
|
|
21
22
|
for datasetRef in args.datasetColumns {
|
|
22
|
-
|
|
23
|
-
ll.panic("Dataset is undefined")
|
|
24
|
-
}
|
|
25
|
-
// it's blockId of MiXCR, we suppose that it procuce only one clns column
|
|
23
|
+
// we assume that mixcr block produces exactly one clns column
|
|
26
24
|
datasets[datasetRef.blockId] = wf.resolve(datasetRef)
|
|
27
25
|
}
|
|
28
26
|
|
|
27
|
+
library := render.createEphemeral(requestLibraryTpl, {
|
|
28
|
+
datasets: datasets,
|
|
29
|
+
ctx: wf.getParentBCtx()
|
|
30
|
+
}).output("library")
|
|
31
|
+
|
|
29
32
|
donorColumn := wf.resolve(args.donorColumn)
|
|
30
33
|
|
|
31
34
|
// The problem is that refs for data is not resolved.
|
|
@@ -34,6 +37,7 @@ wf.body(func(args) {
|
|
|
34
37
|
results := render.createEphemeral(processTpl, {
|
|
35
38
|
datasets: datasets,
|
|
36
39
|
donorColumn: donorColumn,
|
|
40
|
+
library: library,
|
|
37
41
|
params: {
|
|
38
42
|
downsampling: args.downsampling,
|
|
39
43
|
sequencesOfInterest: args.sequencesOfInterest
|
package/src/process.tpl.tengo
CHANGED
|
@@ -6,6 +6,7 @@ maps := import("@platforma-sdk/workflow-tengo:maps")
|
|
|
6
6
|
assets := import("@platforma-sdk/workflow-tengo:assets")
|
|
7
7
|
render := import("@platforma-sdk/workflow-tengo:render")
|
|
8
8
|
xsv := import("@platforma-sdk/workflow-tengo:pframes.xsv")
|
|
9
|
+
smart := import("@platforma-sdk/workflow-tengo:smart")
|
|
9
10
|
text := import("text")
|
|
10
11
|
json := import("json")
|
|
11
12
|
exportSettings := import(":export-settings")
|
|
@@ -20,6 +21,7 @@ self.awaitState("datasets", { wildcard: "*" }, "AllInputsSet")
|
|
|
20
21
|
self.awaitState("datasets", { wildcard: "*" }, "data", "InputsLocked")
|
|
21
22
|
// but we need spec already
|
|
22
23
|
self.awaitState("datasets", { wildcard: "*" }, "spec", "ResourceReady")
|
|
24
|
+
self.awaitState("library", "spec", "ResourceReady")
|
|
23
25
|
self.awaitState("donorColumn", "ResourceReady")
|
|
24
26
|
self.awaitState("params", "ResourceReady")
|
|
25
27
|
|
|
@@ -36,6 +38,8 @@ self.body(func(inputs) {
|
|
|
36
38
|
cellsAssembled: false
|
|
37
39
|
}
|
|
38
40
|
|
|
41
|
+
library := inputs.library
|
|
42
|
+
|
|
39
43
|
// clonotypingBlockId -> "bulk" | "sc"
|
|
40
44
|
datasetTypes := {}
|
|
41
45
|
|
|
@@ -78,6 +82,8 @@ self.body(func(inputs) {
|
|
|
78
82
|
shmTreeNodesWithClonesTableOptions := exportSettings.shmTreeNodesWithClonesTableOptions(dataDescription, inputs.donorColumn)
|
|
79
83
|
shmTreeNodesUniqueIsotypeTableOptions := exportSettings.shmTreeNodesUniqueIsotypeTableOptions(dataDescription)
|
|
80
84
|
|
|
85
|
+
libraryFormat := library.spec.annotations["pl7.app/vdj/libraryFormat"]
|
|
86
|
+
|
|
81
87
|
// TODO that call is too low level. Should be replaced with something that works with pColumns, not data only
|
|
82
88
|
mixcrResults := llPFrames.aggregate(
|
|
83
89
|
// files to iterate through
|
|
@@ -131,9 +137,13 @@ self.body(func(inputs) {
|
|
|
131
137
|
shmTreeNodesWithClonesTableOptions: shmTreeNodesWithClonesTableOptions,
|
|
132
138
|
shmTreeNodesWithClonesTableArgs: shmTreeNodesWithClonesTableOptions.cmdArgs,
|
|
133
139
|
shmTreeNodesUniqueIsotypeTableOptions: shmTreeNodesUniqueIsotypeTableOptions,
|
|
140
|
+
library: is_undefined(library) ? smart.createNullResource() : library.data,
|
|
134
141
|
globalParams: maps.merge(
|
|
135
142
|
inputs.params,
|
|
136
|
-
{
|
|
143
|
+
{
|
|
144
|
+
datasetTypes: datasetTypes,
|
|
145
|
+
libraryFormat: libraryFormat
|
|
146
|
+
}
|
|
137
147
|
)
|
|
138
148
|
}
|
|
139
149
|
)
|
|
@@ -143,7 +153,7 @@ self.body(func(inputs) {
|
|
|
143
153
|
additionalAxesSpec: dataGroupedByDonorId.spec["axesSpec"][:1]
|
|
144
154
|
}
|
|
145
155
|
|
|
146
|
-
ll.print("__THE_LOG__ " + string(json.encode(additionalArgsForImportTsv)))
|
|
156
|
+
// ll.print("__THE_LOG__ " + string(json.encode(additionalArgsForImportTsv)))
|
|
147
157
|
|
|
148
158
|
trees := xsv.importFileMap(
|
|
149
159
|
mixcrResults.output("trees"),
|
|
@@ -33,19 +33,32 @@ self.body(func(inputs) {
|
|
|
33
33
|
globalParams := inputs.globalParams
|
|
34
34
|
datasetTypes := globalParams.datasetTypes
|
|
35
35
|
downsampling := globalParams.downsampling
|
|
36
|
+
library := inputs.library
|
|
37
|
+
libraryFormat := globalParams.libraryFormat
|
|
36
38
|
|
|
37
39
|
// ll.print("__THE_LOG__ " + json.encode(datasetTypes))
|
|
38
40
|
// ll.print("__THE_LOG__ " + json.encode(downsampling))
|
|
41
|
+
// ll.print("__THE_LOG__ " + json.encode(libraryFormat))
|
|
39
42
|
|
|
40
43
|
ll.assert(!is_undefined(datasetTypes), "datasetTypes undefined")
|
|
41
44
|
|
|
42
|
-
|
|
45
|
+
addLibraryFile := func(cmdBuilder) {
|
|
46
|
+
if !is_undefined(library) {
|
|
47
|
+
if libraryFormat == "repseqio.json.gz" {
|
|
48
|
+
cmdBuilder.addFile("library.json.gz", library)
|
|
49
|
+
} else {
|
|
50
|
+
cmdBuilder.addFile("library.json", library)
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
// seed := times.time_string(times.now())
|
|
43
56
|
|
|
44
57
|
allelesCmdBuilder := exec.builder().
|
|
45
58
|
printErrStreamToStdout().
|
|
46
59
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
47
60
|
env("MI_PROGRESS_PREFIX", progressPrefix).
|
|
48
|
-
env("SEED", seed).
|
|
61
|
+
// env("SEED", seed).
|
|
49
62
|
software(mixcrSw).
|
|
50
63
|
arg("findAlleles").
|
|
51
64
|
arg("--report").arg("report.txt").
|
|
@@ -55,6 +68,8 @@ self.body(func(inputs) {
|
|
|
55
68
|
// template specifies where result files will be written
|
|
56
69
|
arg("--output-template").arg("alleles/{file_name}.clns")
|
|
57
70
|
|
|
71
|
+
addLibraryFile(allelesCmdBuilder)
|
|
72
|
+
|
|
58
73
|
if !is_undefined(globalParams.seed) {
|
|
59
74
|
allelesCmdBuilder.env("SEED", globalParams.seed)
|
|
60
75
|
}
|
|
@@ -108,7 +123,7 @@ self.body(func(inputs) {
|
|
|
108
123
|
|
|
109
124
|
for input in toProcess {
|
|
110
125
|
if datasetTypes[input.clonotypingBlockId] == "bulk" {
|
|
111
|
-
|
|
126
|
+
downsamplingCmdBuilder := exec.builder().
|
|
112
127
|
printErrStreamToStdout().
|
|
113
128
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
114
129
|
env("MI_PROGRESS_PREFIX", progressPrefix).
|
|
@@ -118,8 +133,9 @@ self.body(func(inputs) {
|
|
|
118
133
|
arg(downsamplingParam).
|
|
119
134
|
arg("clones.clns").
|
|
120
135
|
addFile("clones.clns", input.alleles).
|
|
121
|
-
saveFile("clones.downsampled.clns")
|
|
122
|
-
|
|
136
|
+
saveFile("clones.downsampled.clns")
|
|
137
|
+
addLibraryFile(downsamplingCmdBuilder)
|
|
138
|
+
downsamplingCmd := downsamplingCmdBuilder.run()
|
|
123
139
|
input.alleles = downsamplingCmd.getFile("clones.downsampled.clns")
|
|
124
140
|
}
|
|
125
141
|
}
|
|
@@ -129,7 +145,6 @@ self.body(func(inputs) {
|
|
|
129
145
|
printErrStreamToStdout().
|
|
130
146
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
131
147
|
env("MI_PROGRESS_PREFIX", progressPrefix).
|
|
132
|
-
env("SEED", seed).
|
|
133
148
|
software(mixcrSw).
|
|
134
149
|
arg("findShmTrees").
|
|
135
150
|
arg("--report").arg("report.txt").
|
|
@@ -141,6 +156,8 @@ self.body(func(inputs) {
|
|
|
141
156
|
shmTreesCmdBuilder.env("SEED", globalParams.seed)
|
|
142
157
|
}
|
|
143
158
|
|
|
159
|
+
addLibraryFile(shmTreesCmdBuilder)
|
|
160
|
+
|
|
144
161
|
for input in toProcess {
|
|
145
162
|
shmTreesCmdBuilder.
|
|
146
163
|
addFile(input.fileName, input.alleles).
|
|
@@ -151,15 +168,18 @@ self.body(func(inputs) {
|
|
|
151
168
|
|
|
152
169
|
shmTrees := shmTreesCmdBuilder.run()
|
|
153
170
|
outputShmt := shmTrees.getFile("output.shmt")
|
|
154
|
-
|
|
171
|
+
|
|
155
172
|
// export trees without nodes
|
|
156
173
|
shmTreeExportsCmdBuilder := exec.builder().
|
|
157
174
|
printErrStreamToStdout().
|
|
175
|
+
dontSaveStdoutOrStderr().
|
|
158
176
|
inLightQueue().
|
|
159
177
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
160
178
|
software(mixcrSw).
|
|
161
179
|
arg("exportShmTrees")
|
|
162
180
|
|
|
181
|
+
addLibraryFile(shmTreeExportsCmdBuilder)
|
|
182
|
+
|
|
163
183
|
for arg in inputs.shmTreeTableArgs {
|
|
164
184
|
shmTreeExportsCmdBuilder = shmTreeExportsCmdBuilder.arg(arg)
|
|
165
185
|
}
|
|
@@ -178,11 +198,14 @@ self.body(func(inputs) {
|
|
|
178
198
|
// export tree nodes with data uniq for the node
|
|
179
199
|
shmTreeNodesExportsCmdBuilder := exec.builder().
|
|
180
200
|
printErrStreamToStdout().
|
|
201
|
+
dontSaveStdoutOrStderr().
|
|
181
202
|
inLightQueue().
|
|
182
203
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
183
204
|
software(mixcrSw).
|
|
184
205
|
arg("exportShmTreesWithNodes")
|
|
185
206
|
|
|
207
|
+
addLibraryFile(shmTreeNodesExportsCmdBuilder)
|
|
208
|
+
|
|
186
209
|
for arg in inputs.shmTreeNodesTableOptions.cmdArgs {
|
|
187
210
|
shmTreeNodesExportsCmdBuilder = shmTreeNodesExportsCmdBuilder.arg(arg)
|
|
188
211
|
}
|
|
@@ -201,6 +224,7 @@ self.body(func(inputs) {
|
|
|
201
224
|
// export nodes with clones. For each node could be several clones
|
|
202
225
|
shmTreeNodesWithClonesExportsCmdBuilder := exec.builder().
|
|
203
226
|
printErrStreamToStdout().
|
|
227
|
+
dontSaveStdoutOrStderr().
|
|
204
228
|
inLightQueue().
|
|
205
229
|
secret("MI_LICENSE", "MI_LICENSE").
|
|
206
230
|
env("MI_PROGRESS_PREFIX", progressPrefix).
|
|
@@ -209,6 +233,8 @@ self.body(func(inputs) {
|
|
|
209
233
|
// don't export nodes that don't have clones
|
|
210
234
|
arg("--only-observed")
|
|
211
235
|
|
|
236
|
+
addLibraryFile(shmTreeNodesWithClonesExportsCmdBuilder)
|
|
237
|
+
|
|
212
238
|
for arg in inputs.shmTreeNodesWithClonesTableArgs {
|
|
213
239
|
shmTreeNodesWithClonesExportsCmdBuilder = shmTreeNodesWithClonesExportsCmdBuilder.arg(arg)
|
|
214
240
|
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
smart := import("@platforma-sdk/workflow-tengo:smart")
|
|
2
|
+
bquery := import("@platforma-sdk/workflow-tengo:workflow.bquery")
|
|
3
|
+
ll := import("@platforma-sdk/workflow-tengo:ll")
|
|
4
|
+
self := import("@platforma-sdk/workflow-tengo:tpl")
|
|
5
|
+
|
|
6
|
+
self.awaitState("datasets", { wildcard: "*" }, "spec", "ResourceReady")
|
|
7
|
+
self.awaitState("datasets", { wildcard: "*" }, "ref", "ResourceReady")
|
|
8
|
+
|
|
9
|
+
self.body(func(args) {
|
|
10
|
+
datasets := args.datasets
|
|
11
|
+
ctx := args.ctx
|
|
12
|
+
|
|
13
|
+
// undefined - not initialized
|
|
14
|
+
// "" - no custom library, built-in library will be used
|
|
15
|
+
// "...." - custom library id, to be requested from the context
|
|
16
|
+
libraryId := undefined
|
|
17
|
+
|
|
18
|
+
for _, dataset in datasets {
|
|
19
|
+
dsLibraryId := dataset.spec.annotations["pl7.app/vdj/libraryId"]
|
|
20
|
+
if is_undefined(libraryId) {
|
|
21
|
+
libraryId = !is_undefined(dsLibraryId) ? dsLibraryId : ""
|
|
22
|
+
} else {
|
|
23
|
+
if libraryId != dsLibraryId {
|
|
24
|
+
ll.panic("All datasets should have the same libraryId. Got " + libraryId + " and " + dsLibraryId)
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
if libraryId == "" || is_undefined(libraryId) {
|
|
30
|
+
return { library: smart.createNullResource() }
|
|
31
|
+
} else {
|
|
32
|
+
querySpec := {
|
|
33
|
+
type: "And",
|
|
34
|
+
operands: [
|
|
35
|
+
{ type: "Name", name: "pl7.app/vdj/library" },
|
|
36
|
+
{ type: "Domain", domain: { "pl7.app/vdj/libraryId": libraryId } }
|
|
37
|
+
]
|
|
38
|
+
}
|
|
39
|
+
return { library: bquery.create(querySpec, ctx, { single: true, errIfMissing: true }) }
|
|
40
|
+
}
|
|
41
|
+
})
|
|
42
|
+
|