digital-tasks 2.0.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/.turbo/turbo-build.log +5 -0
- package/CHANGELOG.md +10 -0
- package/dist/function-task.d.ts +319 -0
- package/dist/function-task.d.ts.map +1 -0
- package/dist/function-task.js +286 -0
- package/dist/function-task.js.map +1 -0
- package/dist/index.d.ts +72 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +74 -0
- package/dist/index.js.map +1 -0
- package/dist/markdown.d.ts +112 -0
- package/dist/markdown.d.ts.map +1 -0
- package/dist/markdown.js +510 -0
- package/dist/markdown.js.map +1 -0
- package/dist/project.d.ts +259 -0
- package/dist/project.d.ts.map +1 -0
- package/dist/project.js +397 -0
- package/dist/project.js.map +1 -0
- package/dist/queue.d.ts +17 -0
- package/dist/queue.d.ts.map +1 -0
- package/dist/queue.js +347 -0
- package/dist/queue.js.map +1 -0
- package/dist/task.d.ts +69 -0
- package/dist/task.d.ts.map +1 -0
- package/dist/task.js +321 -0
- package/dist/task.js.map +1 -0
- package/dist/types.d.ts +292 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +15 -0
- package/dist/types.js.map +1 -0
- package/package.json +41 -0
- package/src/index.ts +161 -0
- package/src/markdown.ts +622 -0
- package/src/project.ts +571 -0
- package/src/queue.ts +424 -0
- package/src/task.ts +389 -0
- package/src/types.ts +403 -0
- package/test/markdown.test.ts +550 -0
- package/test/project.test.ts +562 -0
- package/test/queue.test.ts +482 -0
- package/test/task.test.ts +464 -0
- package/tsconfig.json +20 -0
|
@@ -0,0 +1,464 @@
|
|
|
1
|
+
import { describe, it, expect, beforeEach } from 'vitest'
|
|
2
|
+
import {
|
|
3
|
+
createTask,
|
|
4
|
+
getTask,
|
|
5
|
+
startTask,
|
|
6
|
+
updateProgress,
|
|
7
|
+
completeTask,
|
|
8
|
+
failTask,
|
|
9
|
+
cancelTask,
|
|
10
|
+
addComment,
|
|
11
|
+
createSubtask,
|
|
12
|
+
getSubtasks,
|
|
13
|
+
waitForTask,
|
|
14
|
+
taskQueue,
|
|
15
|
+
createTaskQueue,
|
|
16
|
+
} from '../src/index.js'
|
|
17
|
+
import type { FunctionDefinition, WorkerRef } from '../src/index.js'
|
|
18
|
+
|
|
19
|
+
describe('Task Management', () => {
|
|
20
|
+
let queue: ReturnType<typeof createTaskQueue>
|
|
21
|
+
|
|
22
|
+
beforeEach(() => {
|
|
23
|
+
// Create a fresh queue for each test
|
|
24
|
+
queue = createTaskQueue({ name: 'test' })
|
|
25
|
+
})
|
|
26
|
+
|
|
27
|
+
describe('createTask()', () => {
|
|
28
|
+
it('should create a task with a generative function', async () => {
|
|
29
|
+
const func: FunctionDefinition = {
|
|
30
|
+
type: 'generative',
|
|
31
|
+
name: 'summarize',
|
|
32
|
+
description: 'Summarize text',
|
|
33
|
+
args: { text: 'The text to summarize' },
|
|
34
|
+
output: 'string',
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const task = await createTask({
|
|
38
|
+
function: func,
|
|
39
|
+
input: { text: 'Long article content...' },
|
|
40
|
+
priority: 'high',
|
|
41
|
+
})
|
|
42
|
+
|
|
43
|
+
expect(task).toBeDefined()
|
|
44
|
+
expect(task.id).toMatch(/^task_/)
|
|
45
|
+
expect(task.function).toEqual(func)
|
|
46
|
+
expect(task.priority).toBe('high')
|
|
47
|
+
expect(task.status).toBe('queued')
|
|
48
|
+
expect(task.input).toEqual({ text: 'Long article content...' })
|
|
49
|
+
expect(task.createdAt).toBeInstanceOf(Date)
|
|
50
|
+
})
|
|
51
|
+
|
|
52
|
+
it('should create a task with a code function', async () => {
|
|
53
|
+
const func: FunctionDefinition = {
|
|
54
|
+
type: 'code',
|
|
55
|
+
name: 'processData',
|
|
56
|
+
args: { data: 'Input data' },
|
|
57
|
+
output: 'object',
|
|
58
|
+
code: 'return data',
|
|
59
|
+
language: 'typescript',
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
const task = await createTask({
|
|
63
|
+
function: func,
|
|
64
|
+
priority: 'normal',
|
|
65
|
+
})
|
|
66
|
+
|
|
67
|
+
expect(task.function.type).toBe('code')
|
|
68
|
+
expect(task.allowedWorkers).toEqual(['any'])
|
|
69
|
+
})
|
|
70
|
+
|
|
71
|
+
it('should set allowedWorkers to human for human functions', async () => {
|
|
72
|
+
const func: FunctionDefinition = {
|
|
73
|
+
type: 'human',
|
|
74
|
+
name: 'review',
|
|
75
|
+
description: 'Review document',
|
|
76
|
+
args: { document: 'Document to review' },
|
|
77
|
+
output: 'object',
|
|
78
|
+
instructions: 'Please review this document',
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
const task = await createTask({
|
|
82
|
+
function: func,
|
|
83
|
+
})
|
|
84
|
+
|
|
85
|
+
expect(task.allowedWorkers).toEqual(['human'])
|
|
86
|
+
})
|
|
87
|
+
|
|
88
|
+
it('should set allowedWorkers to agent for agentic functions', async () => {
|
|
89
|
+
const func: FunctionDefinition = {
|
|
90
|
+
type: 'agentic',
|
|
91
|
+
name: 'research',
|
|
92
|
+
args: { topic: 'Topic to research' },
|
|
93
|
+
output: 'string',
|
|
94
|
+
tools: [],
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
const task = await createTask({
|
|
98
|
+
function: func,
|
|
99
|
+
})
|
|
100
|
+
|
|
101
|
+
expect(task.allowedWorkers).toEqual(['agent'])
|
|
102
|
+
})
|
|
103
|
+
|
|
104
|
+
it('should create a task with dependencies', async () => {
|
|
105
|
+
const func: FunctionDefinition = {
|
|
106
|
+
type: 'generative',
|
|
107
|
+
name: 'task1',
|
|
108
|
+
args: {},
|
|
109
|
+
output: 'string',
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
const task1 = await createTask({ function: func })
|
|
113
|
+
const task2 = await createTask({
|
|
114
|
+
function: { ...func, name: 'task2' },
|
|
115
|
+
dependencies: [task1.id],
|
|
116
|
+
})
|
|
117
|
+
|
|
118
|
+
expect(task2.status).toBe('blocked')
|
|
119
|
+
expect(task2.dependencies).toHaveLength(1)
|
|
120
|
+
expect(task2.dependencies![0].taskId).toBe(task1.id)
|
|
121
|
+
expect(task2.dependencies![0].type).toBe('blocked_by')
|
|
122
|
+
expect(task2.dependencies![0].satisfied).toBe(false)
|
|
123
|
+
})
|
|
124
|
+
|
|
125
|
+
it('should create a task with assignment', async () => {
|
|
126
|
+
const func: FunctionDefinition = {
|
|
127
|
+
type: 'generative',
|
|
128
|
+
name: 'assigned-task',
|
|
129
|
+
args: {},
|
|
130
|
+
output: 'string',
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
const worker: WorkerRef = {
|
|
134
|
+
type: 'agent',
|
|
135
|
+
id: 'agent_123',
|
|
136
|
+
name: 'Test Agent',
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
const task = await createTask({
|
|
140
|
+
function: func,
|
|
141
|
+
assignTo: worker,
|
|
142
|
+
})
|
|
143
|
+
|
|
144
|
+
expect(task.status).toBe('assigned')
|
|
145
|
+
expect(task.assignment).toBeDefined()
|
|
146
|
+
expect(task.assignment!.worker).toEqual(worker)
|
|
147
|
+
})
|
|
148
|
+
|
|
149
|
+
it('should create a task with scheduled start time', async () => {
|
|
150
|
+
const func: FunctionDefinition = {
|
|
151
|
+
type: 'generative',
|
|
152
|
+
name: 'scheduled-task',
|
|
153
|
+
args: {},
|
|
154
|
+
output: 'string',
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const scheduledFor = new Date(Date.now() + 60000)
|
|
158
|
+
|
|
159
|
+
const task = await createTask({
|
|
160
|
+
function: func,
|
|
161
|
+
scheduledFor,
|
|
162
|
+
})
|
|
163
|
+
|
|
164
|
+
expect(task.status).toBe('pending')
|
|
165
|
+
expect(task.scheduledFor).toEqual(scheduledFor)
|
|
166
|
+
})
|
|
167
|
+
|
|
168
|
+
it('should create a task with metadata and tags', async () => {
|
|
169
|
+
const func: FunctionDefinition = {
|
|
170
|
+
type: 'generative',
|
|
171
|
+
name: 'tagged-task',
|
|
172
|
+
args: {},
|
|
173
|
+
output: 'string',
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
const task = await createTask({
|
|
177
|
+
function: func,
|
|
178
|
+
tags: ['urgent', 'frontend'],
|
|
179
|
+
metadata: { source: 'api', version: '1.0' },
|
|
180
|
+
})
|
|
181
|
+
|
|
182
|
+
expect(task.tags).toEqual(['urgent', 'frontend'])
|
|
183
|
+
expect(task.metadata).toEqual({ source: 'api', version: '1.0' })
|
|
184
|
+
})
|
|
185
|
+
})
|
|
186
|
+
|
|
187
|
+
describe('getTask()', () => {
|
|
188
|
+
it('should retrieve an existing task', async () => {
|
|
189
|
+
const func: FunctionDefinition = {
|
|
190
|
+
type: 'generative',
|
|
191
|
+
name: 'test-task',
|
|
192
|
+
args: {},
|
|
193
|
+
output: 'string',
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
const created = await createTask({ function: func })
|
|
197
|
+
const retrieved = await getTask(created.id)
|
|
198
|
+
|
|
199
|
+
expect(retrieved).toBeDefined()
|
|
200
|
+
expect(retrieved!.id).toBe(created.id)
|
|
201
|
+
})
|
|
202
|
+
|
|
203
|
+
it('should return undefined for non-existent task', async () => {
|
|
204
|
+
const result = await getTask('non_existent_id')
|
|
205
|
+
expect(result).toBeUndefined()
|
|
206
|
+
})
|
|
207
|
+
})
|
|
208
|
+
|
|
209
|
+
describe('startTask()', () => {
|
|
210
|
+
it('should start a task and update status', async () => {
|
|
211
|
+
const func: FunctionDefinition = {
|
|
212
|
+
type: 'generative',
|
|
213
|
+
name: 'start-test',
|
|
214
|
+
args: {},
|
|
215
|
+
output: 'string',
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
const task = await createTask({ function: func })
|
|
219
|
+
const worker: WorkerRef = { type: 'agent', id: 'agent_1', name: 'Worker' }
|
|
220
|
+
|
|
221
|
+
const started = await startTask(task.id, worker)
|
|
222
|
+
|
|
223
|
+
expect(started).toBeDefined()
|
|
224
|
+
expect(started!.status).toBe('in_progress')
|
|
225
|
+
expect(started!.assignment?.worker).toEqual(worker)
|
|
226
|
+
})
|
|
227
|
+
|
|
228
|
+
it('should return undefined for non-existent task', async () => {
|
|
229
|
+
const worker: WorkerRef = { type: 'agent', id: 'agent_1' }
|
|
230
|
+
const result = await startTask('non_existent', worker)
|
|
231
|
+
expect(result).toBeUndefined()
|
|
232
|
+
})
|
|
233
|
+
})
|
|
234
|
+
|
|
235
|
+
describe('updateProgress()', () => {
|
|
236
|
+
it('should update task progress', async () => {
|
|
237
|
+
const func: FunctionDefinition = {
|
|
238
|
+
type: 'generative',
|
|
239
|
+
name: 'progress-test',
|
|
240
|
+
args: {},
|
|
241
|
+
output: 'string',
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
const task = await createTask({ function: func })
|
|
245
|
+
const updated = await updateProgress(task.id, 50, 'Processing data')
|
|
246
|
+
|
|
247
|
+
expect(updated).toBeDefined()
|
|
248
|
+
expect(updated!.progress?.percent).toBe(50)
|
|
249
|
+
expect(updated!.progress?.step).toBe('Processing data')
|
|
250
|
+
})
|
|
251
|
+
})
|
|
252
|
+
|
|
253
|
+
describe('completeTask()', () => {
|
|
254
|
+
it('should complete a task with output', async () => {
|
|
255
|
+
const func: FunctionDefinition = {
|
|
256
|
+
type: 'generative',
|
|
257
|
+
name: 'complete-test',
|
|
258
|
+
args: {},
|
|
259
|
+
output: 'string',
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
const task = await createTask({ function: func })
|
|
263
|
+
const worker: WorkerRef = { type: 'agent', id: 'agent_1' }
|
|
264
|
+
await startTask(task.id, worker)
|
|
265
|
+
|
|
266
|
+
const result = await completeTask(task.id, 'Task completed successfully')
|
|
267
|
+
|
|
268
|
+
expect(result.success).toBe(true)
|
|
269
|
+
expect(result.output).toBe('Task completed successfully')
|
|
270
|
+
expect(result.taskId).toBe(task.id)
|
|
271
|
+
})
|
|
272
|
+
|
|
273
|
+
it('should return error for non-existent task', async () => {
|
|
274
|
+
const result = await completeTask('non_existent', 'output')
|
|
275
|
+
|
|
276
|
+
expect(result.success).toBe(false)
|
|
277
|
+
expect(result.error?.code).toBe('TASK_NOT_FOUND')
|
|
278
|
+
})
|
|
279
|
+
})
|
|
280
|
+
|
|
281
|
+
describe('failTask()', () => {
|
|
282
|
+
it('should fail a task with error message', async () => {
|
|
283
|
+
const func: FunctionDefinition = {
|
|
284
|
+
type: 'generative',
|
|
285
|
+
name: 'fail-test',
|
|
286
|
+
args: {},
|
|
287
|
+
output: 'string',
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
const task = await createTask({ function: func })
|
|
291
|
+
const result = await failTask(task.id, 'Something went wrong')
|
|
292
|
+
|
|
293
|
+
expect(result.success).toBe(false)
|
|
294
|
+
expect(result.error?.code).toBe('TASK_FAILED')
|
|
295
|
+
expect(result.error?.message).toBe('Something went wrong')
|
|
296
|
+
})
|
|
297
|
+
|
|
298
|
+
it('should fail a task with Error object', async () => {
|
|
299
|
+
const func: FunctionDefinition = {
|
|
300
|
+
type: 'generative',
|
|
301
|
+
name: 'fail-error-test',
|
|
302
|
+
args: {},
|
|
303
|
+
output: 'string',
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
const task = await createTask({ function: func })
|
|
307
|
+
const error = new Error('Error object message')
|
|
308
|
+
const result = await failTask(task.id, error)
|
|
309
|
+
|
|
310
|
+
expect(result.success).toBe(false)
|
|
311
|
+
expect(result.error?.message).toBe('Error object message')
|
|
312
|
+
})
|
|
313
|
+
})
|
|
314
|
+
|
|
315
|
+
describe('cancelTask()', () => {
|
|
316
|
+
it('should cancel a task', async () => {
|
|
317
|
+
const func: FunctionDefinition = {
|
|
318
|
+
type: 'generative',
|
|
319
|
+
name: 'cancel-test',
|
|
320
|
+
args: {},
|
|
321
|
+
output: 'string',
|
|
322
|
+
}
|
|
323
|
+
|
|
324
|
+
const task = await createTask({ function: func })
|
|
325
|
+
const cancelled = await cancelTask(task.id, 'No longer needed')
|
|
326
|
+
|
|
327
|
+
expect(cancelled).toBe(true)
|
|
328
|
+
|
|
329
|
+
const updated = await getTask(task.id)
|
|
330
|
+
expect(updated?.status).toBe('cancelled')
|
|
331
|
+
})
|
|
332
|
+
|
|
333
|
+
it('should return false for non-existent task', async () => {
|
|
334
|
+
const result = await cancelTask('non_existent')
|
|
335
|
+
expect(result).toBe(false)
|
|
336
|
+
})
|
|
337
|
+
})
|
|
338
|
+
|
|
339
|
+
describe('addComment()', () => {
|
|
340
|
+
it('should add a comment to a task', async () => {
|
|
341
|
+
const func: FunctionDefinition = {
|
|
342
|
+
type: 'generative',
|
|
343
|
+
name: 'comment-test',
|
|
344
|
+
args: {},
|
|
345
|
+
output: 'string',
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
const task = await createTask({ function: func })
|
|
349
|
+
const author: WorkerRef = { type: 'human', id: 'user_1', name: 'John' }
|
|
350
|
+
|
|
351
|
+
const updated = await addComment(task.id, 'This is a comment', author)
|
|
352
|
+
|
|
353
|
+
expect(updated).toBeDefined()
|
|
354
|
+
const commentEvent = updated!.events?.find(e => e.type === 'comment')
|
|
355
|
+
expect(commentEvent).toBeDefined()
|
|
356
|
+
expect(commentEvent!.message).toBe('This is a comment')
|
|
357
|
+
expect(commentEvent!.actor).toEqual(author)
|
|
358
|
+
})
|
|
359
|
+
})
|
|
360
|
+
|
|
361
|
+
describe('createSubtask()', () => {
|
|
362
|
+
it('should create a subtask with parent reference', async () => {
|
|
363
|
+
const func: FunctionDefinition = {
|
|
364
|
+
type: 'generative',
|
|
365
|
+
name: 'parent-task',
|
|
366
|
+
args: {},
|
|
367
|
+
output: 'string',
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
const parent = await createTask({ function: func })
|
|
371
|
+
|
|
372
|
+
const subtask = await createSubtask(parent.id, {
|
|
373
|
+
function: {
|
|
374
|
+
type: 'generative',
|
|
375
|
+
name: 'subtask',
|
|
376
|
+
args: {},
|
|
377
|
+
output: 'string',
|
|
378
|
+
},
|
|
379
|
+
})
|
|
380
|
+
|
|
381
|
+
expect(subtask.parentId).toBe(parent.id)
|
|
382
|
+
})
|
|
383
|
+
})
|
|
384
|
+
|
|
385
|
+
describe('getSubtasks()', () => {
|
|
386
|
+
it('should retrieve all subtasks of a parent', async () => {
|
|
387
|
+
const func: FunctionDefinition = {
|
|
388
|
+
type: 'generative',
|
|
389
|
+
name: 'parent',
|
|
390
|
+
args: {},
|
|
391
|
+
output: 'string',
|
|
392
|
+
}
|
|
393
|
+
|
|
394
|
+
const parent = await createTask({ function: func })
|
|
395
|
+
|
|
396
|
+
await createSubtask(parent.id, {
|
|
397
|
+
function: { type: 'generative', name: 'sub1', args: {}, output: 'string' },
|
|
398
|
+
})
|
|
399
|
+
await createSubtask(parent.id, {
|
|
400
|
+
function: { type: 'generative', name: 'sub2', args: {}, output: 'string' },
|
|
401
|
+
})
|
|
402
|
+
|
|
403
|
+
const subtasks = await getSubtasks(parent.id)
|
|
404
|
+
expect(subtasks).toHaveLength(2)
|
|
405
|
+
})
|
|
406
|
+
})
|
|
407
|
+
|
|
408
|
+
describe('waitForTask()', () => {
|
|
409
|
+
it('should return immediately for completed task', async () => {
|
|
410
|
+
const func: FunctionDefinition = {
|
|
411
|
+
type: 'generative',
|
|
412
|
+
name: 'wait-test',
|
|
413
|
+
args: {},
|
|
414
|
+
output: 'string',
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
const task = await createTask({ function: func })
|
|
418
|
+
await completeTask(task.id, 'done')
|
|
419
|
+
|
|
420
|
+
const result = await waitForTask(task.id, { timeout: 1000 })
|
|
421
|
+
expect(result.success).toBe(true)
|
|
422
|
+
// Output is wrapped in { value, producedAt } by queue.complete()
|
|
423
|
+
expect(result.output).toEqual({ value: 'done', producedAt: expect.any(Date) })
|
|
424
|
+
})
|
|
425
|
+
|
|
426
|
+
it('should return error for failed task', async () => {
|
|
427
|
+
const func: FunctionDefinition = {
|
|
428
|
+
type: 'generative',
|
|
429
|
+
name: 'wait-fail-test',
|
|
430
|
+
args: {},
|
|
431
|
+
output: 'string',
|
|
432
|
+
}
|
|
433
|
+
|
|
434
|
+
const task = await createTask({ function: func })
|
|
435
|
+
await failTask(task.id, 'task failed')
|
|
436
|
+
|
|
437
|
+
const result = await waitForTask(task.id, { timeout: 1000 })
|
|
438
|
+
expect(result.success).toBe(false)
|
|
439
|
+
expect(result.error?.code).toBe('TASK_FAILED')
|
|
440
|
+
})
|
|
441
|
+
|
|
442
|
+
it('should return error for cancelled task', async () => {
|
|
443
|
+
const func: FunctionDefinition = {
|
|
444
|
+
type: 'generative',
|
|
445
|
+
name: 'wait-cancel-test',
|
|
446
|
+
args: {},
|
|
447
|
+
output: 'string',
|
|
448
|
+
}
|
|
449
|
+
|
|
450
|
+
const task = await createTask({ function: func })
|
|
451
|
+
await cancelTask(task.id)
|
|
452
|
+
|
|
453
|
+
const result = await waitForTask(task.id, { timeout: 1000 })
|
|
454
|
+
expect(result.success).toBe(false)
|
|
455
|
+
expect(result.error?.code).toBe('TASK_CANCELLED')
|
|
456
|
+
})
|
|
457
|
+
|
|
458
|
+
it('should return error for non-existent task', async () => {
|
|
459
|
+
const result = await waitForTask('non_existent', { timeout: 100 })
|
|
460
|
+
expect(result.success).toBe(false)
|
|
461
|
+
expect(result.error?.code).toBe('TASK_NOT_FOUND')
|
|
462
|
+
})
|
|
463
|
+
})
|
|
464
|
+
})
|
package/tsconfig.json
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
{
|
|
2
|
+
"compilerOptions": {
|
|
3
|
+
"target": "ES2022",
|
|
4
|
+
"module": "NodeNext",
|
|
5
|
+
"moduleResolution": "NodeNext",
|
|
6
|
+
"lib": ["ES2022"],
|
|
7
|
+
"outDir": "dist",
|
|
8
|
+
"rootDir": "src",
|
|
9
|
+
"strict": true,
|
|
10
|
+
"esModuleInterop": true,
|
|
11
|
+
"skipLibCheck": true,
|
|
12
|
+
"forceConsistentCasingInFileNames": true,
|
|
13
|
+
"declaration": true,
|
|
14
|
+
"declarationMap": true,
|
|
15
|
+
"sourceMap": true,
|
|
16
|
+
"resolveJsonModule": true
|
|
17
|
+
},
|
|
18
|
+
"include": ["src/**/*"],
|
|
19
|
+
"exclude": ["node_modules", "dist", "test"]
|
|
20
|
+
}
|