@botpress/zai 1.1.0 → 1.2.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/README.md +1 -1
- package/build.ts +9 -0
- package/dist/adapters/botpress-table.js +21 -21
- package/dist/index.d.ts +22 -521
- package/dist/operations/check.js +15 -3
- package/dist/operations/extract.js +28 -8
- package/dist/operations/filter.js +15 -3
- package/dist/operations/label.js +15 -3
- package/dist/operations/rewrite.js +18 -6
- package/dist/operations/summarize.js +6 -5
- package/dist/operations/text.js +4 -3
- package/dist/utils.js +0 -6
- package/dist/zai.js +28 -68
- package/e2e/data/cache.jsonl +107 -0
- package/{src/operations/__tests/index.ts → e2e/utils.ts} +18 -16
- package/package.json +23 -21
- package/src/adapters/adapter.ts +2 -2
- package/src/adapters/botpress-table.ts +36 -36
- package/src/adapters/memory.ts +3 -3
- package/src/operations/check.ts +31 -17
- package/src/operations/errors.ts +1 -1
- package/src/operations/extract.ts +49 -31
- package/src/operations/filter.ts +36 -23
- package/src/operations/label.ts +32 -19
- package/src/operations/rewrite.ts +28 -15
- package/src/operations/summarize.ts +11 -9
- package/src/operations/text.ts +7 -5
- package/src/utils.ts +5 -14
- package/src/zai.ts +45 -91
- package/tsconfig.json +2 -22
- package/dist/models.js +0 -387
- package/src/models.ts +0 -394
- package/src/operations/__tests/cache.jsonl +0 -101
- package/src/sdk-interfaces/llm/generateContent.ts +0 -127
- package/src/sdk-interfaces/llm/listLanguageModels.ts +0 -19
- /package/{src/operations/__tests → e2e/data}/botpress_docs.txt +0 -0
|
@@ -1,19 +1,20 @@
|
|
|
1
1
|
import { Client } from '@botpress/client'
|
|
2
|
-
import { type TextTokenizer, getWasmTokenizer } from '@
|
|
3
|
-
|
|
2
|
+
import { type TextTokenizer, getWasmTokenizer } from '@bpinternal/thicktoken'
|
|
4
3
|
import fs from 'node:fs'
|
|
5
4
|
import path from 'node:path'
|
|
6
5
|
import { beforeAll } from 'vitest'
|
|
6
|
+
import { Zai } from '../src'
|
|
7
|
+
import { fastHash } from '../src/utils'
|
|
7
8
|
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
9
|
+
const DATA_PATH = path.join(__dirname, 'data')
|
|
10
|
+
const CACHE_PATH = path.join(DATA_PATH, 'cache.jsonl')
|
|
11
|
+
const DOC_PATH = path.join(DATA_PATH, 'botpress_docs.txt')
|
|
11
12
|
|
|
12
13
|
export const getClient = () => {
|
|
13
14
|
return new Client({
|
|
14
15
|
apiUrl: process.env.CLOUD_API_ENDPOINT ?? 'https://api.botpress.dev',
|
|
15
16
|
botId: process.env.CLOUD_BOT_ID,
|
|
16
|
-
token: process.env.CLOUD_PAT
|
|
17
|
+
token: process.env.CLOUD_PAT,
|
|
17
18
|
})
|
|
18
19
|
}
|
|
19
20
|
|
|
@@ -31,10 +32,7 @@ function readJSONL<T>(filePath: string, keyProperty: keyof T): Map<string, T> {
|
|
|
31
32
|
return map
|
|
32
33
|
}
|
|
33
34
|
|
|
34
|
-
const cache: Map<string, { key: string; value: any }> = readJSONL(
|
|
35
|
-
path.resolve(import.meta.dirname, './cache.jsonl'),
|
|
36
|
-
'key'
|
|
37
|
-
)
|
|
35
|
+
const cache: Map<string, { key: string; value: any }> = readJSONL(CACHE_PATH, 'key')
|
|
38
36
|
|
|
39
37
|
export const getCachedClient = () => {
|
|
40
38
|
const client = getClient()
|
|
@@ -54,10 +52,10 @@ export const getCachedClient = () => {
|
|
|
54
52
|
cache.set(key, { key, value: response })
|
|
55
53
|
|
|
56
54
|
fs.appendFileSync(
|
|
57
|
-
|
|
55
|
+
CACHE_PATH,
|
|
58
56
|
JSON.stringify({
|
|
59
57
|
key,
|
|
60
|
-
value: response
|
|
58
|
+
value: response,
|
|
61
59
|
}) + '\n'
|
|
62
60
|
)
|
|
63
61
|
|
|
@@ -65,23 +63,27 @@ export const getCachedClient = () => {
|
|
|
65
63
|
}
|
|
66
64
|
}
|
|
67
65
|
return Reflect.get(target, prop)
|
|
68
|
-
}
|
|
66
|
+
},
|
|
69
67
|
})
|
|
70
68
|
|
|
69
|
+
;(proxy as any).clone = () => {
|
|
70
|
+
return getCachedClient()
|
|
71
|
+
}
|
|
72
|
+
|
|
71
73
|
return proxy
|
|
72
74
|
}
|
|
73
75
|
|
|
74
76
|
export const getZai = () => {
|
|
75
77
|
const client = getCachedClient()
|
|
76
|
-
return new Zai({ client
|
|
78
|
+
return new Zai({ client })
|
|
77
79
|
}
|
|
78
80
|
|
|
79
81
|
export let tokenizer: TextTokenizer = null!
|
|
80
82
|
|
|
81
83
|
beforeAll(async () => {
|
|
82
|
-
tokenizer = await getWasmTokenizer()
|
|
84
|
+
tokenizer = (await getWasmTokenizer()) as TextTokenizer
|
|
83
85
|
})
|
|
84
86
|
|
|
85
|
-
export const BotpressDocumentation = fs.readFileSync(
|
|
87
|
+
export const BotpressDocumentation = fs.readFileSync(DOC_PATH, 'utf-8').trim()
|
|
86
88
|
|
|
87
89
|
export const metadata = { cost: { input: 1, output: 1 }, latency: 0, model: '', tokens: { input: 1, output: 1 } }
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@botpress/zai",
|
|
3
3
|
"description": "Zui AI (zai) – An LLM utility library written on top of Zui and the Botpress API",
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.2.0",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"types": "./dist/index.d.ts",
|
|
7
7
|
"exports": {
|
|
@@ -10,39 +10,41 @@
|
|
|
10
10
|
"import": "./dist/index.js"
|
|
11
11
|
},
|
|
12
12
|
"scripts": {
|
|
13
|
-
"
|
|
14
|
-
"build
|
|
13
|
+
"check:type": "tsc --noEmit",
|
|
14
|
+
"build": "bp add -y && pnpm run build:types && pnpm run build:neutral",
|
|
15
|
+
"build:neutral": "ts-node -T ./build.ts",
|
|
15
16
|
"build:types": "tsup",
|
|
16
17
|
"watch": "tsup --watch",
|
|
17
|
-
"test": "vitest run --config vitest.config.ts",
|
|
18
|
-
"test:update": "vitest -u run --config vitest.config.ts",
|
|
19
|
-
"test:watch": "vitest --config vitest.config.ts"
|
|
20
|
-
"build-with-latest-models": "pnpm run update-types && pnpm run update-models && pnpm run build",
|
|
21
|
-
"update-models": "ts-node ./scripts/update-models.mts",
|
|
22
|
-
"update-types": "ts-node ./scripts/update-types.mts"
|
|
18
|
+
"test:e2e": "vitest run --config vitest.config.ts",
|
|
19
|
+
"test:e2e:update": "vitest -u run --config vitest.config.ts",
|
|
20
|
+
"test:e2e:watch": "vitest --config vitest.config.ts"
|
|
23
21
|
},
|
|
24
22
|
"keywords": [],
|
|
25
23
|
"author": "",
|
|
26
24
|
"license": "ISC",
|
|
27
25
|
"dependencies": {
|
|
26
|
+
"@botpress/cognitive": "^0.1.6",
|
|
28
27
|
"json5": "^2.2.3",
|
|
29
|
-
"jsonrepair": "^3.
|
|
28
|
+
"jsonrepair": "^3.10.0",
|
|
30
29
|
"lodash-es": "^4.17.21"
|
|
31
30
|
},
|
|
32
31
|
"devDependencies": {
|
|
33
|
-
"@botpress/
|
|
32
|
+
"@botpress/client": "workspace:^",
|
|
33
|
+
"@botpress/common": "workspace:*",
|
|
34
|
+
"@botpress/vai": "workspace:*",
|
|
34
35
|
"@types/lodash-es": "^4.17.12",
|
|
35
|
-
"dotenv": "^16.4.
|
|
36
|
-
"esbuild": "^0.
|
|
36
|
+
"dotenv": "^16.4.4",
|
|
37
|
+
"esbuild": "^0.16.12",
|
|
38
|
+
"glob": "^9.3.4",
|
|
37
39
|
"lodash": "^4.17.21",
|
|
38
|
-
"
|
|
39
|
-
"tsup": "^8.3.5",
|
|
40
|
-
"typescript": "^5.7.2",
|
|
41
|
-
"vitest": "^2.1.8"
|
|
40
|
+
"tsup": "^8.0.2"
|
|
42
41
|
},
|
|
43
42
|
"peerDependencies": {
|
|
44
|
-
"@
|
|
45
|
-
"@
|
|
46
|
-
|
|
47
|
-
|
|
43
|
+
"@bpinternal/thicktoken": "^1.0.0",
|
|
44
|
+
"@bpinternal/zui": "^0.17.1"
|
|
45
|
+
},
|
|
46
|
+
"engines": {
|
|
47
|
+
"node": ">=18.0.0"
|
|
48
|
+
},
|
|
49
|
+
"packageManager": "pnpm@8.6.2"
|
|
48
50
|
}
|
package/src/adapters/adapter.ts
CHANGED
|
@@ -19,7 +19,7 @@ export type GetExamplesProps<TInput> = {
|
|
|
19
19
|
}
|
|
20
20
|
|
|
21
21
|
export abstract class Adapter {
|
|
22
|
-
abstract getExamples<TInput, TOutput>(
|
|
22
|
+
public abstract getExamples<TInput, TOutput>(
|
|
23
23
|
props: GetExamplesProps<TInput>
|
|
24
24
|
): Promise<
|
|
25
25
|
Array<{
|
|
@@ -31,5 +31,5 @@ export abstract class Adapter {
|
|
|
31
31
|
}>
|
|
32
32
|
>
|
|
33
33
|
|
|
34
|
-
abstract saveExample<TInput, TOutput>(props: SaveExampleProps<TInput, TOutput>): Promise<void>
|
|
34
|
+
public abstract saveExample<TInput, TOutput>(props: SaveExampleProps<TInput, TOutput>): Promise<void>
|
|
35
35
|
}
|
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import { type Client } from '@botpress/client'
|
|
2
2
|
import { z } from '@bpinternal/zui'
|
|
3
3
|
|
|
4
|
-
import {
|
|
4
|
+
import { GenerationMetadata } from '../utils'
|
|
5
5
|
import { Adapter, GetExamplesProps, SaveExampleProps } from './adapter'
|
|
6
6
|
|
|
7
7
|
const CRITICAL_TAGS = {
|
|
8
8
|
system: 'true',
|
|
9
9
|
'schema-purpose': 'active-learning',
|
|
10
|
-
'schema-version': 'Oct-2024'
|
|
10
|
+
'schema-version': 'Oct-2024',
|
|
11
11
|
} as const
|
|
12
12
|
|
|
13
13
|
const OPTIONAL_TAGS = {
|
|
@@ -15,19 +15,19 @@ const OPTIONAL_TAGS = {
|
|
|
15
15
|
'x-studio-description': 'Table for storing active learning tasks and examples',
|
|
16
16
|
'x-studio-readonly': 'true',
|
|
17
17
|
'x-studio-icon': 'lucide://atom',
|
|
18
|
-
'x-studio-color': 'green'
|
|
18
|
+
'x-studio-color': 'green',
|
|
19
19
|
} as const
|
|
20
20
|
|
|
21
21
|
const FACTOR = 30
|
|
22
22
|
|
|
23
23
|
const Props = z.object({
|
|
24
|
-
client:
|
|
24
|
+
client: z.custom(() => true),
|
|
25
25
|
tableName: z
|
|
26
26
|
.string()
|
|
27
27
|
.regex(
|
|
28
28
|
/^[a-zA-Z0-9_]{1,45}Table$/,
|
|
29
29
|
'Table name must be lowercase and contain only letters, numbers and underscores'
|
|
30
|
-
)
|
|
30
|
+
),
|
|
31
31
|
})
|
|
32
32
|
|
|
33
33
|
export type TableSchema = z.input<typeof TableSchema>
|
|
@@ -44,10 +44,10 @@ const TableSchema = z.object({
|
|
|
44
44
|
feedback: z
|
|
45
45
|
.object({
|
|
46
46
|
rating: z.enum(['very-bad', 'bad', 'good', 'very-good']),
|
|
47
|
-
comment: z.string().nullable()
|
|
47
|
+
comment: z.string().nullable(),
|
|
48
48
|
})
|
|
49
49
|
.nullable()
|
|
50
|
-
.default(null)
|
|
50
|
+
.default(null),
|
|
51
51
|
})
|
|
52
52
|
|
|
53
53
|
const searchableColumns = ['input'] as const satisfies Array<keyof typeof TableSchema.shape> as string[]
|
|
@@ -60,33 +60,33 @@ const TableJsonSchema = Object.entries(TableSchema.shape).reduce((acc, [key, val
|
|
|
60
60
|
}, {})
|
|
61
61
|
|
|
62
62
|
export class TableAdapter extends Adapter {
|
|
63
|
-
private
|
|
64
|
-
private
|
|
63
|
+
private _client: Client
|
|
64
|
+
private _tableName: string
|
|
65
65
|
|
|
66
|
-
private
|
|
66
|
+
private _status: 'initialized' | 'ready' | 'error'
|
|
67
67
|
|
|
68
|
-
constructor(props: z.input<typeof Props>) {
|
|
68
|
+
public constructor(props: z.input<typeof Props>) {
|
|
69
69
|
super()
|
|
70
70
|
props = Props.parse(props)
|
|
71
|
-
this.
|
|
72
|
-
this.
|
|
73
|
-
this.
|
|
71
|
+
this._client = props.client
|
|
72
|
+
this._tableName = props.tableName
|
|
73
|
+
this._status = 'ready'
|
|
74
74
|
}
|
|
75
75
|
|
|
76
76
|
public async getExamples<TInput, TOutput>({ taskType, taskId, input }: GetExamplesProps<TInput>) {
|
|
77
|
-
await this.
|
|
77
|
+
await this._assertTableExists()
|
|
78
78
|
|
|
79
|
-
const { rows } = await this.
|
|
79
|
+
const { rows } = await this._client
|
|
80
80
|
.findTableRows({
|
|
81
|
-
table: this.
|
|
81
|
+
table: this._tableName,
|
|
82
82
|
search: JSON.stringify({ value: input }).substring(0, 1023), // Search is limited to 1024 characters
|
|
83
83
|
limit: 10, // TODO
|
|
84
84
|
filter: {
|
|
85
85
|
// Proximity match of approved examples
|
|
86
86
|
taskType,
|
|
87
87
|
taskId,
|
|
88
|
-
status: 'approved'
|
|
89
|
-
} satisfies Partial<TableSchema
|
|
88
|
+
status: 'approved',
|
|
89
|
+
} satisfies Partial<TableSchema>,
|
|
90
90
|
})
|
|
91
91
|
.catch((err) => {
|
|
92
92
|
// TODO: handle error
|
|
@@ -99,7 +99,7 @@ export class TableAdapter extends Adapter {
|
|
|
99
99
|
input: row.input.value as TInput,
|
|
100
100
|
output: row.output.value as TOutput,
|
|
101
101
|
explanation: row.explanation,
|
|
102
|
-
similarity: row.similarity ?? 0
|
|
102
|
+
similarity: row.similarity ?? 0,
|
|
103
103
|
}))
|
|
104
104
|
}
|
|
105
105
|
|
|
@@ -112,13 +112,13 @@ export class TableAdapter extends Adapter {
|
|
|
112
112
|
output,
|
|
113
113
|
explanation,
|
|
114
114
|
metadata,
|
|
115
|
-
status = 'pending'
|
|
115
|
+
status = 'pending',
|
|
116
116
|
}: SaveExampleProps<TInput, TOutput>) {
|
|
117
|
-
await this.
|
|
117
|
+
await this._assertTableExists()
|
|
118
118
|
|
|
119
|
-
await this.
|
|
119
|
+
await this._client
|
|
120
120
|
.upsertTableRows({
|
|
121
|
-
table: this.
|
|
121
|
+
table: this._tableName,
|
|
122
122
|
keyColumn: 'key',
|
|
123
123
|
rows: [
|
|
124
124
|
{
|
|
@@ -130,34 +130,34 @@ export class TableAdapter extends Adapter {
|
|
|
130
130
|
output: { value: output },
|
|
131
131
|
explanation: explanation ?? null,
|
|
132
132
|
status,
|
|
133
|
-
metadata
|
|
134
|
-
} satisfies TableSchema
|
|
135
|
-
]
|
|
133
|
+
metadata,
|
|
134
|
+
} satisfies TableSchema,
|
|
135
|
+
],
|
|
136
136
|
})
|
|
137
137
|
.catch(() => {
|
|
138
138
|
// TODO: handle error
|
|
139
139
|
})
|
|
140
140
|
}
|
|
141
141
|
|
|
142
|
-
private async
|
|
143
|
-
if (this.
|
|
142
|
+
private async _assertTableExists() {
|
|
143
|
+
if (this._status !== 'ready') {
|
|
144
144
|
return
|
|
145
145
|
}
|
|
146
146
|
|
|
147
|
-
const { table, created } = await this.
|
|
147
|
+
const { table, created } = await this._client
|
|
148
148
|
.getOrCreateTable({
|
|
149
|
-
table: this.
|
|
149
|
+
table: this._tableName,
|
|
150
150
|
factor: FACTOR,
|
|
151
151
|
frozen: true,
|
|
152
152
|
isComputeEnabled: false,
|
|
153
153
|
tags: {
|
|
154
154
|
...CRITICAL_TAGS,
|
|
155
|
-
...OPTIONAL_TAGS
|
|
155
|
+
...OPTIONAL_TAGS,
|
|
156
156
|
},
|
|
157
|
-
schema: TableJsonSchema
|
|
157
|
+
schema: TableJsonSchema,
|
|
158
158
|
})
|
|
159
159
|
.catch(() => {
|
|
160
|
-
this.
|
|
160
|
+
this._status = 'error'
|
|
161
161
|
return { table: null, created: false }
|
|
162
162
|
})
|
|
163
163
|
|
|
@@ -201,10 +201,10 @@ export class TableAdapter extends Adapter {
|
|
|
201
201
|
}
|
|
202
202
|
|
|
203
203
|
if (issues.length) {
|
|
204
|
-
this.
|
|
204
|
+
this._status = 'error'
|
|
205
205
|
}
|
|
206
206
|
}
|
|
207
207
|
|
|
208
|
-
this.
|
|
208
|
+
this._status = 'initialized'
|
|
209
209
|
}
|
|
210
210
|
}
|
package/src/adapters/memory.ts
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import { Adapter } from './adapter'
|
|
2
2
|
|
|
3
3
|
export class MemoryAdapter extends Adapter {
|
|
4
|
-
constructor(public examples: any[]) {
|
|
4
|
+
public constructor(public examples: any[]) {
|
|
5
5
|
super()
|
|
6
6
|
}
|
|
7
7
|
|
|
8
|
-
async getExamples() {
|
|
8
|
+
public async getExamples() {
|
|
9
9
|
return this.examples
|
|
10
10
|
}
|
|
11
11
|
|
|
12
|
-
async saveExample() {}
|
|
12
|
+
public async saveExample() {}
|
|
13
13
|
}
|
package/src/operations/check.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
// eslint-disable consistent-type-definitions
|
|
1
2
|
import { z } from '@bpinternal/zui'
|
|
2
3
|
|
|
3
4
|
import { fastHash, stringify, takeUntilTokens } from '../utils'
|
|
@@ -7,12 +8,12 @@ import { PROMPT_INPUT_BUFFER } from './constants'
|
|
|
7
8
|
const Example = z.object({
|
|
8
9
|
input: z.any(),
|
|
9
10
|
check: z.boolean(),
|
|
10
|
-
reason: z.string().optional()
|
|
11
|
+
reason: z.string().optional(),
|
|
11
12
|
})
|
|
12
13
|
|
|
13
14
|
export type Options = z.input<typeof Options>
|
|
14
15
|
const Options = z.object({
|
|
15
|
-
examples: z.array(Example).describe('Examples to check the condition against').default([])
|
|
16
|
+
examples: z.array(Example).describe('Examples to check the condition against').default([]),
|
|
16
17
|
})
|
|
17
18
|
|
|
18
19
|
declare module '@botpress/zai' {
|
|
@@ -29,14 +30,15 @@ const END = '■END■'
|
|
|
29
30
|
Zai.prototype.check = async function (this: Zai, input, condition, _options) {
|
|
30
31
|
const options = Options.parse(_options ?? {})
|
|
31
32
|
const tokenizer = await this.getTokenizer()
|
|
32
|
-
|
|
33
|
+
await this.fetchModelDetails()
|
|
34
|
+
const PROMPT_COMPONENT = Math.max(this.ModelDetails.input.maxTokens - PROMPT_INPUT_BUFFER, 100)
|
|
33
35
|
|
|
34
36
|
const taskId = this.taskId
|
|
35
37
|
const taskType = 'zai.check'
|
|
36
38
|
|
|
37
39
|
const PROMPT_TOKENS = {
|
|
38
40
|
INPUT: Math.floor(0.5 * PROMPT_COMPONENT),
|
|
39
|
-
CONDITION: Math.floor(0.2 * PROMPT_COMPONENT)
|
|
41
|
+
CONDITION: Math.floor(0.2 * PROMPT_COMPONENT),
|
|
40
42
|
}
|
|
41
43
|
|
|
42
44
|
// Truncate the input to fit the model's input size
|
|
@@ -51,7 +53,7 @@ Zai.prototype.check = async function (this: Zai, input, condition, _options) {
|
|
|
51
53
|
taskType,
|
|
52
54
|
taskId,
|
|
53
55
|
input: inputAsString,
|
|
54
|
-
condition
|
|
56
|
+
condition,
|
|
55
57
|
})
|
|
56
58
|
)
|
|
57
59
|
|
|
@@ -59,7 +61,7 @@ Zai.prototype.check = async function (this: Zai, input, condition, _options) {
|
|
|
59
61
|
? await this.adapter.getExamples<string, boolean>({
|
|
60
62
|
input: inputAsString,
|
|
61
63
|
taskType,
|
|
62
|
-
taskId
|
|
64
|
+
taskId,
|
|
63
65
|
})
|
|
64
66
|
: []
|
|
65
67
|
|
|
@@ -73,13 +75,14 @@ Zai.prototype.check = async function (this: Zai, input, condition, _options) {
|
|
|
73
75
|
{
|
|
74
76
|
input: ['apple', 'banana', 'carrot', 'house'],
|
|
75
77
|
check: false,
|
|
76
|
-
reason:
|
|
77
|
-
|
|
78
|
+
reason:
|
|
79
|
+
'The list contains a house, which is not a fruit. Also, the list contains a carrot, which is a vegetable.',
|
|
80
|
+
},
|
|
78
81
|
]
|
|
79
82
|
|
|
80
83
|
const userExamples = [
|
|
81
84
|
...examples.map((e) => ({ input: e.input, check: e.output, reason: e.explanation })),
|
|
82
|
-
...options.examples
|
|
85
|
+
...options.examples,
|
|
83
86
|
]
|
|
84
87
|
|
|
85
88
|
let exampleId = 1
|
|
@@ -108,8 +111,8 @@ ${END}
|
|
|
108
111
|
{
|
|
109
112
|
type: 'text' as const,
|
|
110
113
|
content: formatOutput(example.check, example.reason ?? ''),
|
|
111
|
-
role: 'assistant' as const
|
|
112
|
-
}
|
|
114
|
+
role: 'assistant' as const,
|
|
115
|
+
},
|
|
113
116
|
]
|
|
114
117
|
|
|
115
118
|
const allExamples = takeUntilTokens(
|
|
@@ -129,7 +132,7 @@ ${END}
|
|
|
129
132
|
`.trim()
|
|
130
133
|
: ''
|
|
131
134
|
|
|
132
|
-
const output = await this.callModel({
|
|
135
|
+
const { output, meta } = await this.callModel({
|
|
133
136
|
systemPrompt: `
|
|
134
137
|
Check if the following condition is true or false for the given input. Before answering, make sure to read the input and the condition carefully.
|
|
135
138
|
Justify your answer, then answer with either ${TRUE} or ${FALSE} at the very end, then add ${END} to finish the response.
|
|
@@ -147,9 +150,9 @@ ${specialInstructions}
|
|
|
147
150
|
Considering the below input and above examples, is the following condition true or false?
|
|
148
151
|
${formatInput(inputAsString, condition)}
|
|
149
152
|
In your "Analysis", please refer to the Expert Examples # to justify your decision.`.trim(),
|
|
150
|
-
role: 'user'
|
|
151
|
-
}
|
|
152
|
-
]
|
|
153
|
+
role: 'user',
|
|
154
|
+
},
|
|
155
|
+
],
|
|
153
156
|
})
|
|
154
157
|
|
|
155
158
|
const answer = output.choices[0]?.content as string
|
|
@@ -177,9 +180,20 @@ In your "Analysis", please refer to the Expert Examples # to justify your decisi
|
|
|
177
180
|
taskId,
|
|
178
181
|
input: inputAsString,
|
|
179
182
|
instructions: condition,
|
|
180
|
-
metadata:
|
|
183
|
+
metadata: {
|
|
184
|
+
cost: {
|
|
185
|
+
input: meta.cost.input,
|
|
186
|
+
output: meta.cost.output,
|
|
187
|
+
},
|
|
188
|
+
latency: meta.latency,
|
|
189
|
+
model: this.Model,
|
|
190
|
+
tokens: {
|
|
191
|
+
input: meta.tokens.input,
|
|
192
|
+
output: meta.tokens.output,
|
|
193
|
+
},
|
|
194
|
+
},
|
|
181
195
|
output: finalAnswer,
|
|
182
|
-
explanation: answer.replace(TRUE, '').replace(FALSE, '').replace(END, '').replace('Final Answer:', '').trim()
|
|
196
|
+
explanation: answer.replace(TRUE, '').replace(FALSE, '').replace(END, '').replace('Final Answer:', '').trim(),
|
|
183
197
|
})
|
|
184
198
|
}
|
|
185
199
|
|
package/src/operations/errors.ts
CHANGED