@firebase/ai 1.4.0 → 1.4.1-canary.25b60fdaa
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/ai-public.d.ts +462 -213
- package/dist/ai.d.ts +465 -213
- package/dist/esm/{index.esm2017.js → index.esm.js} +349 -276
- package/dist/esm/index.esm.js.map +1 -0
- package/dist/esm/src/api.d.ts +2 -38
- package/dist/esm/src/errors.d.ts +1 -1
- package/dist/esm/src/public-types.d.ts +0 -18
- package/dist/esm/src/requests/schema-builder.d.ts +25 -6
- package/dist/esm/src/types/enums.d.ts +102 -60
- package/dist/esm/src/types/error.d.ts +21 -15
- package/dist/esm/src/types/imagen/requests.d.ts +53 -19
- package/dist/esm/src/types/imagen/responses.d.ts +2 -2
- package/dist/esm/src/types/requests.d.ts +69 -7
- package/dist/esm/src/types/responses.d.ts +135 -12
- package/dist/esm/src/types/schema.d.ts +41 -20
- package/dist/index.cjs.js +364 -279
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.node.cjs.js +364 -279
- package/dist/index.node.cjs.js.map +1 -1
- package/dist/index.node.mjs +348 -275
- package/dist/index.node.mjs.map +1 -1
- package/dist/src/api.d.ts +2 -38
- package/dist/src/errors.d.ts +1 -1
- package/dist/src/public-types.d.ts +0 -18
- package/dist/src/requests/schema-builder.d.ts +25 -6
- package/dist/src/types/enums.d.ts +102 -60
- package/dist/src/types/error.d.ts +21 -15
- package/dist/src/types/imagen/requests.d.ts +53 -19
- package/dist/src/types/imagen/responses.d.ts +2 -2
- package/dist/src/types/requests.d.ts +69 -7
- package/dist/src/types/responses.d.ts +135 -12
- package/dist/src/types/schema.d.ts +41 -20
- package/package.json +14 -13
- package/dist/esm/index.esm2017.js.map +0 -1
package/dist/index.cjs.js
CHANGED
|
@@ -6,10 +6,9 @@ var app = require('@firebase/app');
|
|
|
6
6
|
var component = require('@firebase/component');
|
|
7
7
|
var util = require('@firebase/util');
|
|
8
8
|
var logger$1 = require('@firebase/logger');
|
|
9
|
-
var tslib = require('tslib');
|
|
10
9
|
|
|
11
10
|
var name = "@firebase/ai";
|
|
12
|
-
var version = "1.4.
|
|
11
|
+
var version = "1.4.1-canary.25b60fdaa";
|
|
13
12
|
|
|
14
13
|
/**
|
|
15
14
|
* @license
|
|
@@ -60,230 +59,221 @@ const POSSIBLE_ROLES = ['user', 'model', 'function', 'system'];
|
|
|
60
59
|
* Harm categories that would cause prompts or candidates to be blocked.
|
|
61
60
|
* @public
|
|
62
61
|
*/
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
})(exports.HarmCategory || (exports.HarmCategory = {}));
|
|
62
|
+
const HarmCategory = {
|
|
63
|
+
HARM_CATEGORY_HATE_SPEECH: 'HARM_CATEGORY_HATE_SPEECH',
|
|
64
|
+
HARM_CATEGORY_SEXUALLY_EXPLICIT: 'HARM_CATEGORY_SEXUALLY_EXPLICIT',
|
|
65
|
+
HARM_CATEGORY_HARASSMENT: 'HARM_CATEGORY_HARASSMENT',
|
|
66
|
+
HARM_CATEGORY_DANGEROUS_CONTENT: 'HARM_CATEGORY_DANGEROUS_CONTENT'
|
|
67
|
+
};
|
|
70
68
|
/**
|
|
71
69
|
* Threshold above which a prompt or candidate will be blocked.
|
|
72
70
|
* @public
|
|
73
71
|
*/
|
|
74
|
-
|
|
75
|
-
(function (HarmBlockThreshold) {
|
|
72
|
+
const HarmBlockThreshold = {
|
|
76
73
|
/**
|
|
77
74
|
* Content with `NEGLIGIBLE` will be allowed.
|
|
78
75
|
*/
|
|
79
|
-
|
|
76
|
+
BLOCK_LOW_AND_ABOVE: 'BLOCK_LOW_AND_ABOVE',
|
|
80
77
|
/**
|
|
81
78
|
* Content with `NEGLIGIBLE` and `LOW` will be allowed.
|
|
82
79
|
*/
|
|
83
|
-
|
|
80
|
+
BLOCK_MEDIUM_AND_ABOVE: 'BLOCK_MEDIUM_AND_ABOVE',
|
|
84
81
|
/**
|
|
85
82
|
* Content with `NEGLIGIBLE`, `LOW`, and `MEDIUM` will be allowed.
|
|
86
83
|
*/
|
|
87
|
-
|
|
84
|
+
BLOCK_ONLY_HIGH: 'BLOCK_ONLY_HIGH',
|
|
88
85
|
/**
|
|
89
86
|
* All content will be allowed.
|
|
90
87
|
*/
|
|
91
|
-
|
|
88
|
+
BLOCK_NONE: 'BLOCK_NONE',
|
|
92
89
|
/**
|
|
93
90
|
* All content will be allowed. This is the same as `BLOCK_NONE`, but the metadata corresponding
|
|
94
91
|
* to the {@link HarmCategory} will not be present in the response.
|
|
95
92
|
*/
|
|
96
|
-
|
|
97
|
-
}
|
|
93
|
+
OFF: 'OFF'
|
|
94
|
+
};
|
|
98
95
|
/**
|
|
99
96
|
* This property is not supported in the Gemini Developer API ({@link GoogleAIBackend}).
|
|
100
97
|
*
|
|
101
98
|
* @public
|
|
102
99
|
*/
|
|
103
|
-
|
|
104
|
-
(function (HarmBlockMethod) {
|
|
100
|
+
const HarmBlockMethod = {
|
|
105
101
|
/**
|
|
106
102
|
* The harm block method uses both probability and severity scores.
|
|
107
103
|
*/
|
|
108
|
-
|
|
104
|
+
SEVERITY: 'SEVERITY',
|
|
109
105
|
/**
|
|
110
106
|
* The harm block method uses the probability score.
|
|
111
107
|
*/
|
|
112
|
-
|
|
113
|
-
}
|
|
108
|
+
PROBABILITY: 'PROBABILITY'
|
|
109
|
+
};
|
|
114
110
|
/**
|
|
115
111
|
* Probability that a prompt or candidate matches a harm category.
|
|
116
112
|
* @public
|
|
117
113
|
*/
|
|
118
|
-
|
|
119
|
-
(function (HarmProbability) {
|
|
114
|
+
const HarmProbability = {
|
|
120
115
|
/**
|
|
121
116
|
* Content has a negligible chance of being unsafe.
|
|
122
117
|
*/
|
|
123
|
-
|
|
118
|
+
NEGLIGIBLE: 'NEGLIGIBLE',
|
|
124
119
|
/**
|
|
125
120
|
* Content has a low chance of being unsafe.
|
|
126
121
|
*/
|
|
127
|
-
|
|
122
|
+
LOW: 'LOW',
|
|
128
123
|
/**
|
|
129
124
|
* Content has a medium chance of being unsafe.
|
|
130
125
|
*/
|
|
131
|
-
|
|
126
|
+
MEDIUM: 'MEDIUM',
|
|
132
127
|
/**
|
|
133
128
|
* Content has a high chance of being unsafe.
|
|
134
129
|
*/
|
|
135
|
-
|
|
136
|
-
}
|
|
130
|
+
HIGH: 'HIGH'
|
|
131
|
+
};
|
|
137
132
|
/**
|
|
138
133
|
* Harm severity levels.
|
|
139
134
|
* @public
|
|
140
135
|
*/
|
|
141
|
-
|
|
142
|
-
(function (HarmSeverity) {
|
|
136
|
+
const HarmSeverity = {
|
|
143
137
|
/**
|
|
144
138
|
* Negligible level of harm severity.
|
|
145
139
|
*/
|
|
146
|
-
|
|
140
|
+
HARM_SEVERITY_NEGLIGIBLE: 'HARM_SEVERITY_NEGLIGIBLE',
|
|
147
141
|
/**
|
|
148
142
|
* Low level of harm severity.
|
|
149
143
|
*/
|
|
150
|
-
|
|
144
|
+
HARM_SEVERITY_LOW: 'HARM_SEVERITY_LOW',
|
|
151
145
|
/**
|
|
152
146
|
* Medium level of harm severity.
|
|
153
147
|
*/
|
|
154
|
-
|
|
148
|
+
HARM_SEVERITY_MEDIUM: 'HARM_SEVERITY_MEDIUM',
|
|
155
149
|
/**
|
|
156
150
|
* High level of harm severity.
|
|
157
151
|
*/
|
|
158
|
-
|
|
152
|
+
HARM_SEVERITY_HIGH: 'HARM_SEVERITY_HIGH',
|
|
159
153
|
/**
|
|
160
154
|
* Harm severity is not supported.
|
|
161
155
|
*
|
|
162
156
|
* @remarks
|
|
163
157
|
* The GoogleAI backend does not support `HarmSeverity`, so this value is used as a fallback.
|
|
164
158
|
*/
|
|
165
|
-
|
|
166
|
-
}
|
|
159
|
+
HARM_SEVERITY_UNSUPPORTED: 'HARM_SEVERITY_UNSUPPORTED'
|
|
160
|
+
};
|
|
167
161
|
/**
|
|
168
162
|
* Reason that a prompt was blocked.
|
|
169
163
|
* @public
|
|
170
164
|
*/
|
|
171
|
-
|
|
172
|
-
(function (BlockReason) {
|
|
165
|
+
const BlockReason = {
|
|
173
166
|
/**
|
|
174
167
|
* Content was blocked by safety settings.
|
|
175
168
|
*/
|
|
176
|
-
|
|
169
|
+
SAFETY: 'SAFETY',
|
|
177
170
|
/**
|
|
178
171
|
* Content was blocked, but the reason is uncategorized.
|
|
179
172
|
*/
|
|
180
|
-
|
|
173
|
+
OTHER: 'OTHER',
|
|
181
174
|
/**
|
|
182
175
|
* Content was blocked because it contained terms from the terminology blocklist.
|
|
183
176
|
*/
|
|
184
|
-
|
|
177
|
+
BLOCKLIST: 'BLOCKLIST',
|
|
185
178
|
/**
|
|
186
179
|
* Content was blocked due to prohibited content.
|
|
187
180
|
*/
|
|
188
|
-
|
|
189
|
-
}
|
|
181
|
+
PROHIBITED_CONTENT: 'PROHIBITED_CONTENT'
|
|
182
|
+
};
|
|
190
183
|
/**
|
|
191
184
|
* Reason that a candidate finished.
|
|
192
185
|
* @public
|
|
193
186
|
*/
|
|
194
|
-
|
|
195
|
-
(function (FinishReason) {
|
|
187
|
+
const FinishReason = {
|
|
196
188
|
/**
|
|
197
189
|
* Natural stop point of the model or provided stop sequence.
|
|
198
190
|
*/
|
|
199
|
-
|
|
191
|
+
STOP: 'STOP',
|
|
200
192
|
/**
|
|
201
193
|
* The maximum number of tokens as specified in the request was reached.
|
|
202
194
|
*/
|
|
203
|
-
|
|
195
|
+
MAX_TOKENS: 'MAX_TOKENS',
|
|
204
196
|
/**
|
|
205
197
|
* The candidate content was flagged for safety reasons.
|
|
206
198
|
*/
|
|
207
|
-
|
|
199
|
+
SAFETY: 'SAFETY',
|
|
208
200
|
/**
|
|
209
201
|
* The candidate content was flagged for recitation reasons.
|
|
210
202
|
*/
|
|
211
|
-
|
|
203
|
+
RECITATION: 'RECITATION',
|
|
212
204
|
/**
|
|
213
205
|
* Unknown reason.
|
|
214
206
|
*/
|
|
215
|
-
|
|
207
|
+
OTHER: 'OTHER',
|
|
216
208
|
/**
|
|
217
209
|
* The candidate content contained forbidden terms.
|
|
218
210
|
*/
|
|
219
|
-
|
|
211
|
+
BLOCKLIST: 'BLOCKLIST',
|
|
220
212
|
/**
|
|
221
213
|
* The candidate content potentially contained prohibited content.
|
|
222
214
|
*/
|
|
223
|
-
|
|
215
|
+
PROHIBITED_CONTENT: 'PROHIBITED_CONTENT',
|
|
224
216
|
/**
|
|
225
217
|
* The candidate content potentially contained Sensitive Personally Identifiable Information (SPII).
|
|
226
218
|
*/
|
|
227
|
-
|
|
219
|
+
SPII: 'SPII',
|
|
228
220
|
/**
|
|
229
221
|
* The function call generated by the model was invalid.
|
|
230
222
|
*/
|
|
231
|
-
|
|
232
|
-
}
|
|
223
|
+
MALFORMED_FUNCTION_CALL: 'MALFORMED_FUNCTION_CALL'
|
|
224
|
+
};
|
|
233
225
|
/**
|
|
234
226
|
* @public
|
|
235
227
|
*/
|
|
236
|
-
|
|
237
|
-
(function (FunctionCallingMode) {
|
|
228
|
+
const FunctionCallingMode = {
|
|
238
229
|
/**
|
|
239
230
|
* Default model behavior; model decides to predict either a function call
|
|
240
231
|
* or a natural language response.
|
|
241
232
|
*/
|
|
242
|
-
|
|
233
|
+
AUTO: 'AUTO',
|
|
243
234
|
/**
|
|
244
235
|
* Model is constrained to always predicting a function call only.
|
|
245
236
|
* If `allowed_function_names` is set, the predicted function call will be
|
|
246
237
|
* limited to any one of `allowed_function_names`, else the predicted
|
|
247
238
|
* function call will be any one of the provided `function_declarations`.
|
|
248
239
|
*/
|
|
249
|
-
|
|
240
|
+
ANY: 'ANY',
|
|
250
241
|
/**
|
|
251
242
|
* Model will not predict any function call. Model behavior is same as when
|
|
252
243
|
* not passing any function declarations.
|
|
253
244
|
*/
|
|
254
|
-
|
|
255
|
-
}
|
|
245
|
+
NONE: 'NONE'
|
|
246
|
+
};
|
|
256
247
|
/**
|
|
257
248
|
* Content part modality.
|
|
258
249
|
* @public
|
|
259
250
|
*/
|
|
260
|
-
|
|
261
|
-
(function (Modality) {
|
|
251
|
+
const Modality = {
|
|
262
252
|
/**
|
|
263
253
|
* Unspecified modality.
|
|
264
254
|
*/
|
|
265
|
-
|
|
255
|
+
MODALITY_UNSPECIFIED: 'MODALITY_UNSPECIFIED',
|
|
266
256
|
/**
|
|
267
257
|
* Plain text.
|
|
268
258
|
*/
|
|
269
|
-
|
|
259
|
+
TEXT: 'TEXT',
|
|
270
260
|
/**
|
|
271
261
|
* Image.
|
|
272
262
|
*/
|
|
273
|
-
|
|
263
|
+
IMAGE: 'IMAGE',
|
|
274
264
|
/**
|
|
275
265
|
* Video.
|
|
276
266
|
*/
|
|
277
|
-
|
|
267
|
+
VIDEO: 'VIDEO',
|
|
278
268
|
/**
|
|
279
269
|
* Audio.
|
|
280
270
|
*/
|
|
281
|
-
|
|
271
|
+
AUDIO: 'AUDIO',
|
|
282
272
|
/**
|
|
283
273
|
* Document (for example, PDF).
|
|
284
274
|
*/
|
|
285
|
-
|
|
286
|
-
}
|
|
275
|
+
DOCUMENT: 'DOCUMENT'
|
|
276
|
+
};
|
|
287
277
|
/**
|
|
288
278
|
* Generation modalities to be returned in generation responses.
|
|
289
279
|
*
|
|
@@ -302,6 +292,56 @@ const ResponseModality = {
|
|
|
302
292
|
IMAGE: 'IMAGE'
|
|
303
293
|
};
|
|
304
294
|
|
|
295
|
+
/**
|
|
296
|
+
* @license
|
|
297
|
+
* Copyright 2024 Google LLC
|
|
298
|
+
*
|
|
299
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
300
|
+
* you may not use this file except in compliance with the License.
|
|
301
|
+
* You may obtain a copy of the License at
|
|
302
|
+
*
|
|
303
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
304
|
+
*
|
|
305
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
306
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
307
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
308
|
+
* See the License for the specific language governing permissions and
|
|
309
|
+
* limitations under the License.
|
|
310
|
+
*/
|
|
311
|
+
/**
|
|
312
|
+
* Standardized error codes that {@link AIError} can have.
|
|
313
|
+
*
|
|
314
|
+
* @public
|
|
315
|
+
*/
|
|
316
|
+
const AIErrorCode = {
|
|
317
|
+
/** A generic error occurred. */
|
|
318
|
+
ERROR: 'error',
|
|
319
|
+
/** An error occurred in a request. */
|
|
320
|
+
REQUEST_ERROR: 'request-error',
|
|
321
|
+
/** An error occurred in a response. */
|
|
322
|
+
RESPONSE_ERROR: 'response-error',
|
|
323
|
+
/** An error occurred while performing a fetch. */
|
|
324
|
+
FETCH_ERROR: 'fetch-error',
|
|
325
|
+
/** An error associated with a Content object. */
|
|
326
|
+
INVALID_CONTENT: 'invalid-content',
|
|
327
|
+
/** An error due to the Firebase API not being enabled in the Console. */
|
|
328
|
+
API_NOT_ENABLED: 'api-not-enabled',
|
|
329
|
+
/** An error due to invalid Schema input. */
|
|
330
|
+
INVALID_SCHEMA: 'invalid-schema',
|
|
331
|
+
/** An error occurred due to a missing Firebase API key. */
|
|
332
|
+
NO_API_KEY: 'no-api-key',
|
|
333
|
+
/** An error occurred due to a missing Firebase app ID. */
|
|
334
|
+
NO_APP_ID: 'no-app-id',
|
|
335
|
+
/** An error occurred due to a model name not being specified during initialization. */
|
|
336
|
+
NO_MODEL: 'no-model',
|
|
337
|
+
/** An error occurred due to a missing project ID. */
|
|
338
|
+
NO_PROJECT_ID: 'no-project-id',
|
|
339
|
+
/** An error occurred while parsing. */
|
|
340
|
+
PARSE_FAILED: 'parse-failed',
|
|
341
|
+
/** An error occurred due an attempt to use an unsupported feature. */
|
|
342
|
+
UNSUPPORTED: 'unsupported'
|
|
343
|
+
};
|
|
344
|
+
|
|
305
345
|
/**
|
|
306
346
|
* @license
|
|
307
347
|
* Copyright 2024 Google LLC
|
|
@@ -324,21 +364,20 @@ const ResponseModality = {
|
|
|
324
364
|
* {@link https://swagger.io/docs/specification/data-models/data-types/ | OpenAPI specification}
|
|
325
365
|
* @public
|
|
326
366
|
*/
|
|
327
|
-
|
|
328
|
-
(function (SchemaType) {
|
|
367
|
+
const SchemaType = {
|
|
329
368
|
/** String type. */
|
|
330
|
-
|
|
369
|
+
STRING: 'string',
|
|
331
370
|
/** Number type. */
|
|
332
|
-
|
|
371
|
+
NUMBER: 'number',
|
|
333
372
|
/** Integer type. */
|
|
334
|
-
|
|
373
|
+
INTEGER: 'integer',
|
|
335
374
|
/** Boolean type. */
|
|
336
|
-
|
|
375
|
+
BOOLEAN: 'boolean',
|
|
337
376
|
/** Array type. */
|
|
338
|
-
|
|
377
|
+
ARRAY: 'array',
|
|
339
378
|
/** Object type. */
|
|
340
|
-
|
|
341
|
-
}
|
|
379
|
+
OBJECT: 'object'
|
|
380
|
+
};
|
|
342
381
|
|
|
343
382
|
/**
|
|
344
383
|
* @license
|
|
@@ -368,28 +407,27 @@ exports.SchemaType = void 0;
|
|
|
368
407
|
*
|
|
369
408
|
* @beta
|
|
370
409
|
*/
|
|
371
|
-
|
|
372
|
-
(function (ImagenSafetyFilterLevel) {
|
|
410
|
+
const ImagenSafetyFilterLevel = {
|
|
373
411
|
/**
|
|
374
412
|
* The most aggressive filtering level; most strict blocking.
|
|
375
413
|
*/
|
|
376
|
-
|
|
414
|
+
BLOCK_LOW_AND_ABOVE: 'block_low_and_above',
|
|
377
415
|
/**
|
|
378
416
|
* Blocks some sensitive prompts and responses.
|
|
379
417
|
*/
|
|
380
|
-
|
|
418
|
+
BLOCK_MEDIUM_AND_ABOVE: 'block_medium_and_above',
|
|
381
419
|
/**
|
|
382
420
|
* Blocks few sensitive prompts and responses.
|
|
383
421
|
*/
|
|
384
|
-
|
|
422
|
+
BLOCK_ONLY_HIGH: 'block_only_high',
|
|
385
423
|
/**
|
|
386
424
|
* The least aggressive filtering level; blocks very few sensitive prompts and responses.
|
|
387
425
|
*
|
|
388
426
|
* Access to this feature is restricted and may require your case to be reviewed and approved by
|
|
389
427
|
* Cloud support.
|
|
390
428
|
*/
|
|
391
|
-
|
|
392
|
-
}
|
|
429
|
+
BLOCK_NONE: 'block_none'
|
|
430
|
+
};
|
|
393
431
|
/**
|
|
394
432
|
* A filter level controlling whether generation of images containing people or faces is allowed.
|
|
395
433
|
*
|
|
@@ -398,12 +436,11 @@ exports.ImagenSafetyFilterLevel = void 0;
|
|
|
398
436
|
*
|
|
399
437
|
* @beta
|
|
400
438
|
*/
|
|
401
|
-
|
|
402
|
-
(function (ImagenPersonFilterLevel) {
|
|
439
|
+
const ImagenPersonFilterLevel = {
|
|
403
440
|
/**
|
|
404
441
|
* Disallow generation of images containing people or faces; images of people are filtered out.
|
|
405
442
|
*/
|
|
406
|
-
|
|
443
|
+
BLOCK_ALL: 'dont_allow',
|
|
407
444
|
/**
|
|
408
445
|
* Allow generation of images containing adults only; images of children are filtered out.
|
|
409
446
|
*
|
|
@@ -411,7 +448,7 @@ exports.ImagenPersonFilterLevel = void 0;
|
|
|
411
448
|
* reviewed and approved by Cloud support; see the {@link https://cloud.google.com/vertex-ai/generative-ai/docs/image/responsible-ai-imagen#person-face-gen | Responsible AI and usage guidelines}
|
|
412
449
|
* for more details.
|
|
413
450
|
*/
|
|
414
|
-
|
|
451
|
+
ALLOW_ADULT: 'allow_adult',
|
|
415
452
|
/**
|
|
416
453
|
* Allow generation of images containing adults only; images of children are filtered out.
|
|
417
454
|
*
|
|
@@ -419,8 +456,8 @@ exports.ImagenPersonFilterLevel = void 0;
|
|
|
419
456
|
* reviewed and approved by Cloud support; see the {@link https://cloud.google.com/vertex-ai/generative-ai/docs/image/responsible-ai-imagen#person-face-gen | Responsible AI and usage guidelines}
|
|
420
457
|
* for more details.
|
|
421
458
|
*/
|
|
422
|
-
|
|
423
|
-
}
|
|
459
|
+
ALLOW_ALL: 'allow_all'
|
|
460
|
+
};
|
|
424
461
|
/**
|
|
425
462
|
* Aspect ratios for Imagen images.
|
|
426
463
|
*
|
|
@@ -432,29 +469,28 @@ exports.ImagenPersonFilterLevel = void 0;
|
|
|
432
469
|
*
|
|
433
470
|
* @beta
|
|
434
471
|
*/
|
|
435
|
-
|
|
436
|
-
(function (ImagenAspectRatio) {
|
|
472
|
+
const ImagenAspectRatio = {
|
|
437
473
|
/**
|
|
438
474
|
* Square (1:1) aspect ratio.
|
|
439
475
|
*/
|
|
440
|
-
|
|
476
|
+
'SQUARE': '1:1',
|
|
441
477
|
/**
|
|
442
478
|
* Landscape (3:4) aspect ratio.
|
|
443
479
|
*/
|
|
444
|
-
|
|
480
|
+
'LANDSCAPE_3x4': '3:4',
|
|
445
481
|
/**
|
|
446
482
|
* Portrait (4:3) aspect ratio.
|
|
447
483
|
*/
|
|
448
|
-
|
|
484
|
+
'PORTRAIT_4x3': '4:3',
|
|
449
485
|
/**
|
|
450
486
|
* Landscape (16:9) aspect ratio.
|
|
451
487
|
*/
|
|
452
|
-
|
|
488
|
+
'LANDSCAPE_16x9': '16:9',
|
|
453
489
|
/**
|
|
454
490
|
* Portrait (9:16) aspect ratio.
|
|
455
491
|
*/
|
|
456
|
-
|
|
457
|
-
}
|
|
492
|
+
'PORTRAIT_9x16': '9:16'
|
|
493
|
+
};
|
|
458
494
|
|
|
459
495
|
/**
|
|
460
496
|
* @license
|
|
@@ -593,8 +629,8 @@ class AIService {
|
|
|
593
629
|
constructor(app, backend, authProvider, appCheckProvider) {
|
|
594
630
|
this.app = app;
|
|
595
631
|
this.backend = backend;
|
|
596
|
-
const appCheck = appCheckProvider
|
|
597
|
-
const auth = authProvider
|
|
632
|
+
const appCheck = appCheckProvider?.getImmediate({ optional: true });
|
|
633
|
+
const auth = authProvider?.getImmediate({ optional: true });
|
|
598
634
|
this.auth = auth || null;
|
|
599
635
|
this.appCheck = appCheck || null;
|
|
600
636
|
if (backend instanceof VertexAIBackend) {
|
|
@@ -634,7 +670,7 @@ class AIError extends util.FirebaseError {
|
|
|
634
670
|
/**
|
|
635
671
|
* Constructs a new instance of the `AIError` class.
|
|
636
672
|
*
|
|
637
|
-
* @param code - The error code from {@link AIErrorCode}.
|
|
673
|
+
* @param code - The error code from {@link (AIErrorCode:type)}.
|
|
638
674
|
* @param message - A human-readable message describing the error.
|
|
639
675
|
* @param customErrorData - Optional error data.
|
|
640
676
|
*/
|
|
@@ -695,7 +731,7 @@ function encodeInstanceIdentifier(backend) {
|
|
|
695
731
|
return `${AI_TYPE}/vertexai/${backend.location}`;
|
|
696
732
|
}
|
|
697
733
|
else {
|
|
698
|
-
throw new AIError(
|
|
734
|
+
throw new AIError(AIErrorCode.ERROR, `Invalid backend: ${JSON.stringify(backend.backendType)}`);
|
|
699
735
|
}
|
|
700
736
|
}
|
|
701
737
|
/**
|
|
@@ -706,20 +742,20 @@ function encodeInstanceIdentifier(backend) {
|
|
|
706
742
|
function decodeInstanceIdentifier(instanceIdentifier) {
|
|
707
743
|
const identifierParts = instanceIdentifier.split('/');
|
|
708
744
|
if (identifierParts[0] !== AI_TYPE) {
|
|
709
|
-
throw new AIError(
|
|
745
|
+
throw new AIError(AIErrorCode.ERROR, `Invalid instance identifier, unknown prefix '${identifierParts[0]}'`);
|
|
710
746
|
}
|
|
711
747
|
const backendType = identifierParts[1];
|
|
712
748
|
switch (backendType) {
|
|
713
749
|
case 'vertexai':
|
|
714
750
|
const location = identifierParts[2];
|
|
715
751
|
if (!location) {
|
|
716
|
-
throw new AIError(
|
|
752
|
+
throw new AIError(AIErrorCode.ERROR, `Invalid instance identifier, unknown location '${instanceIdentifier}'`);
|
|
717
753
|
}
|
|
718
754
|
return new VertexAIBackend(location);
|
|
719
755
|
case 'googleai':
|
|
720
756
|
return new GoogleAIBackend();
|
|
721
757
|
default:
|
|
722
|
-
throw new AIError(
|
|
758
|
+
throw new AIError(AIErrorCode.ERROR, `Invalid instance identifier string: '${instanceIdentifier}'`);
|
|
723
759
|
}
|
|
724
760
|
}
|
|
725
761
|
|
|
@@ -766,15 +802,14 @@ class AIModel {
|
|
|
766
802
|
* @internal
|
|
767
803
|
*/
|
|
768
804
|
constructor(ai, modelName) {
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
throw new AIError("no-api-key" /* AIErrorCode.NO_API_KEY */, `The "apiKey" field is empty in the local Firebase config. Firebase AI requires this field to contain a valid API key.`);
|
|
805
|
+
if (!ai.app?.options?.apiKey) {
|
|
806
|
+
throw new AIError(AIErrorCode.NO_API_KEY, `The "apiKey" field is empty in the local Firebase config. Firebase AI requires this field to contain a valid API key.`);
|
|
772
807
|
}
|
|
773
|
-
else if (!
|
|
774
|
-
throw new AIError(
|
|
808
|
+
else if (!ai.app?.options?.projectId) {
|
|
809
|
+
throw new AIError(AIErrorCode.NO_PROJECT_ID, `The "projectId" field is empty in the local Firebase config. Firebase AI requires this field to contain a valid project ID.`);
|
|
775
810
|
}
|
|
776
|
-
else if (!
|
|
777
|
-
throw new AIError(
|
|
811
|
+
else if (!ai.app?.options?.appId) {
|
|
812
|
+
throw new AIError(AIErrorCode.NO_APP_ID, `The "appId" field is empty in the local Firebase config. Firebase AI requires this field to contain a valid app ID.`);
|
|
778
813
|
}
|
|
779
814
|
else {
|
|
780
815
|
this._apiSettings = {
|
|
@@ -901,8 +936,7 @@ class RequestUrl {
|
|
|
901
936
|
return url.toString();
|
|
902
937
|
}
|
|
903
938
|
get baseUrl() {
|
|
904
|
-
|
|
905
|
-
return ((_a = this.requestOptions) === null || _a === void 0 ? void 0 : _a.baseUrl) || DEFAULT_BASE_URL;
|
|
939
|
+
return this.requestOptions?.baseUrl || DEFAULT_BASE_URL;
|
|
906
940
|
}
|
|
907
941
|
get apiVersion() {
|
|
908
942
|
return DEFAULT_API_VERSION; // TODO: allow user-set options if that feature becomes available
|
|
@@ -915,7 +949,7 @@ class RequestUrl {
|
|
|
915
949
|
return `projects/${this.apiSettings.project}/locations/${this.apiSettings.backend.location}/${this.model}`;
|
|
916
950
|
}
|
|
917
951
|
else {
|
|
918
|
-
throw new AIError(
|
|
952
|
+
throw new AIError(AIErrorCode.ERROR, `Invalid backend: ${JSON.stringify(this.apiSettings.backend)}`);
|
|
919
953
|
}
|
|
920
954
|
}
|
|
921
955
|
get queryParams() {
|
|
@@ -978,7 +1012,7 @@ async function makeRequest(model, task, apiSettings, stream, body, requestOption
|
|
|
978
1012
|
try {
|
|
979
1013
|
const request = await constructRequest(model, task, apiSettings, stream, body, requestOptions);
|
|
980
1014
|
// Timeout is 180s by default
|
|
981
|
-
const timeoutMillis =
|
|
1015
|
+
const timeoutMillis = requestOptions?.timeout != null && requestOptions.timeout >= 0
|
|
982
1016
|
? requestOptions.timeout
|
|
983
1017
|
: DEFAULT_FETCH_TIMEOUT_MS;
|
|
984
1018
|
const abortController = new AbortController();
|
|
@@ -1000,12 +1034,10 @@ async function makeRequest(model, task, apiSettings, stream, body, requestOption
|
|
|
1000
1034
|
// ignored
|
|
1001
1035
|
}
|
|
1002
1036
|
if (response.status === 403 &&
|
|
1037
|
+
errorDetails &&
|
|
1003
1038
|
errorDetails.some((detail) => detail.reason === 'SERVICE_DISABLED') &&
|
|
1004
|
-
errorDetails.some((detail) => {
|
|
1005
|
-
|
|
1006
|
-
return (_b = (_a = detail.links) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.description.includes('Google developers console API activation');
|
|
1007
|
-
})) {
|
|
1008
|
-
throw new AIError("api-not-enabled" /* AIErrorCode.API_NOT_ENABLED */, `The Firebase AI SDK requires the Firebase AI ` +
|
|
1039
|
+
errorDetails.some((detail) => detail.links?.[0]?.description.includes('Google developers console API activation'))) {
|
|
1040
|
+
throw new AIError(AIErrorCode.API_NOT_ENABLED, `The Firebase AI SDK requires the Firebase AI ` +
|
|
1009
1041
|
`API ('firebasevertexai.googleapis.com') to be enabled in your ` +
|
|
1010
1042
|
`Firebase project. Enable this API by visiting the Firebase Console ` +
|
|
1011
1043
|
`at https://console.firebase.google.com/project/${url.apiSettings.project}/genai/ ` +
|
|
@@ -1017,7 +1049,7 @@ async function makeRequest(model, task, apiSettings, stream, body, requestOption
|
|
|
1017
1049
|
errorDetails
|
|
1018
1050
|
});
|
|
1019
1051
|
}
|
|
1020
|
-
throw new AIError(
|
|
1052
|
+
throw new AIError(AIErrorCode.FETCH_ERROR, `Error fetching from ${url}: [${response.status} ${response.statusText}] ${message}`, {
|
|
1021
1053
|
status: response.status,
|
|
1022
1054
|
statusText: response.statusText,
|
|
1023
1055
|
errorDetails
|
|
@@ -1026,10 +1058,10 @@ async function makeRequest(model, task, apiSettings, stream, body, requestOption
|
|
|
1026
1058
|
}
|
|
1027
1059
|
catch (e) {
|
|
1028
1060
|
let err = e;
|
|
1029
|
-
if (e.code !==
|
|
1030
|
-
e.code !==
|
|
1061
|
+
if (e.code !== AIErrorCode.FETCH_ERROR &&
|
|
1062
|
+
e.code !== AIErrorCode.API_NOT_ENABLED &&
|
|
1031
1063
|
e instanceof Error) {
|
|
1032
|
-
err = new AIError(
|
|
1064
|
+
err = new AIError(AIErrorCode.ERROR, `Error fetching from ${url.toString()}: ${e.message}`);
|
|
1033
1065
|
err.stack = e.stack;
|
|
1034
1066
|
}
|
|
1035
1067
|
throw err;
|
|
@@ -1088,14 +1120,14 @@ function addHelpers(response) {
|
|
|
1088
1120
|
`Access response.candidates directly to use the other candidates.`);
|
|
1089
1121
|
}
|
|
1090
1122
|
if (hadBadFinishReason(response.candidates[0])) {
|
|
1091
|
-
throw new AIError(
|
|
1123
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Response error: ${formatBlockErrorMessage(response)}. Response body stored in error.response`, {
|
|
1092
1124
|
response
|
|
1093
1125
|
});
|
|
1094
1126
|
}
|
|
1095
1127
|
return getText(response);
|
|
1096
1128
|
}
|
|
1097
1129
|
else if (response.promptFeedback) {
|
|
1098
|
-
throw new AIError(
|
|
1130
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Text not available. ${formatBlockErrorMessage(response)}`, {
|
|
1099
1131
|
response
|
|
1100
1132
|
});
|
|
1101
1133
|
}
|
|
@@ -1109,14 +1141,14 @@ function addHelpers(response) {
|
|
|
1109
1141
|
`Access response.candidates directly to use the other candidates.`);
|
|
1110
1142
|
}
|
|
1111
1143
|
if (hadBadFinishReason(response.candidates[0])) {
|
|
1112
|
-
throw new AIError(
|
|
1144
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Response error: ${formatBlockErrorMessage(response)}. Response body stored in error.response`, {
|
|
1113
1145
|
response
|
|
1114
1146
|
});
|
|
1115
1147
|
}
|
|
1116
1148
|
return getInlineDataParts(response);
|
|
1117
1149
|
}
|
|
1118
1150
|
else if (response.promptFeedback) {
|
|
1119
|
-
throw new AIError(
|
|
1151
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Data not available. ${formatBlockErrorMessage(response)}`, {
|
|
1120
1152
|
response
|
|
1121
1153
|
});
|
|
1122
1154
|
}
|
|
@@ -1130,14 +1162,14 @@ function addHelpers(response) {
|
|
|
1130
1162
|
`Access response.candidates directly to use the other candidates.`);
|
|
1131
1163
|
}
|
|
1132
1164
|
if (hadBadFinishReason(response.candidates[0])) {
|
|
1133
|
-
throw new AIError(
|
|
1165
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Response error: ${formatBlockErrorMessage(response)}. Response body stored in error.response`, {
|
|
1134
1166
|
response
|
|
1135
1167
|
});
|
|
1136
1168
|
}
|
|
1137
1169
|
return getFunctionCalls(response);
|
|
1138
1170
|
}
|
|
1139
1171
|
else if (response.promptFeedback) {
|
|
1140
|
-
throw new AIError(
|
|
1172
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Function call not available. ${formatBlockErrorMessage(response)}`, {
|
|
1141
1173
|
response
|
|
1142
1174
|
});
|
|
1143
1175
|
}
|
|
@@ -1149,10 +1181,9 @@ function addHelpers(response) {
|
|
|
1149
1181
|
* Returns all text found in all parts of first candidate.
|
|
1150
1182
|
*/
|
|
1151
1183
|
function getText(response) {
|
|
1152
|
-
var _a, _b, _c, _d;
|
|
1153
1184
|
const textStrings = [];
|
|
1154
|
-
if (
|
|
1155
|
-
for (const part of
|
|
1185
|
+
if (response.candidates?.[0].content?.parts) {
|
|
1186
|
+
for (const part of response.candidates?.[0].content?.parts) {
|
|
1156
1187
|
if (part.text) {
|
|
1157
1188
|
textStrings.push(part.text);
|
|
1158
1189
|
}
|
|
@@ -1169,10 +1200,9 @@ function getText(response) {
|
|
|
1169
1200
|
* Returns {@link FunctionCall}s associated with first candidate.
|
|
1170
1201
|
*/
|
|
1171
1202
|
function getFunctionCalls(response) {
|
|
1172
|
-
var _a, _b, _c, _d;
|
|
1173
1203
|
const functionCalls = [];
|
|
1174
|
-
if (
|
|
1175
|
-
for (const part of
|
|
1204
|
+
if (response.candidates?.[0].content?.parts) {
|
|
1205
|
+
for (const part of response.candidates?.[0].content?.parts) {
|
|
1176
1206
|
if (part.functionCall) {
|
|
1177
1207
|
functionCalls.push(part.functionCall);
|
|
1178
1208
|
}
|
|
@@ -1191,10 +1221,9 @@ function getFunctionCalls(response) {
|
|
|
1191
1221
|
* @internal
|
|
1192
1222
|
*/
|
|
1193
1223
|
function getInlineDataParts(response) {
|
|
1194
|
-
var _a, _b, _c, _d;
|
|
1195
1224
|
const data = [];
|
|
1196
|
-
if (
|
|
1197
|
-
for (const part of
|
|
1225
|
+
if (response.candidates?.[0].content?.parts) {
|
|
1226
|
+
for (const part of response.candidates?.[0].content?.parts) {
|
|
1198
1227
|
if (part.inlineData) {
|
|
1199
1228
|
data.push(part);
|
|
1200
1229
|
}
|
|
@@ -1207,25 +1236,24 @@ function getInlineDataParts(response) {
|
|
|
1207
1236
|
return undefined;
|
|
1208
1237
|
}
|
|
1209
1238
|
}
|
|
1210
|
-
const badFinishReasons = [
|
|
1239
|
+
const badFinishReasons = [FinishReason.RECITATION, FinishReason.SAFETY];
|
|
1211
1240
|
function hadBadFinishReason(candidate) {
|
|
1212
1241
|
return (!!candidate.finishReason &&
|
|
1213
|
-
badFinishReasons.
|
|
1242
|
+
badFinishReasons.some(reason => reason === candidate.finishReason));
|
|
1214
1243
|
}
|
|
1215
1244
|
function formatBlockErrorMessage(response) {
|
|
1216
|
-
var _a, _b, _c;
|
|
1217
1245
|
let message = '';
|
|
1218
1246
|
if ((!response.candidates || response.candidates.length === 0) &&
|
|
1219
1247
|
response.promptFeedback) {
|
|
1220
1248
|
message += 'Response was blocked';
|
|
1221
|
-
if (
|
|
1249
|
+
if (response.promptFeedback?.blockReason) {
|
|
1222
1250
|
message += ` due to ${response.promptFeedback.blockReason}`;
|
|
1223
1251
|
}
|
|
1224
|
-
if (
|
|
1252
|
+
if (response.promptFeedback?.blockReasonMessage) {
|
|
1225
1253
|
message += `: ${response.promptFeedback.blockReasonMessage}`;
|
|
1226
1254
|
}
|
|
1227
1255
|
}
|
|
1228
|
-
else if (
|
|
1256
|
+
else if (response.candidates?.[0]) {
|
|
1229
1257
|
const firstCandidate = response.candidates[0];
|
|
1230
1258
|
if (hadBadFinishReason(firstCandidate)) {
|
|
1231
1259
|
message += `Candidate was blocked due to ${firstCandidate.finishReason}`;
|
|
@@ -1244,13 +1272,12 @@ function formatBlockErrorMessage(response) {
|
|
|
1244
1272
|
* @internal
|
|
1245
1273
|
*/
|
|
1246
1274
|
async function handlePredictResponse(response) {
|
|
1247
|
-
var _a;
|
|
1248
1275
|
const responseJson = await response.json();
|
|
1249
1276
|
const images = [];
|
|
1250
1277
|
let filteredReason = undefined;
|
|
1251
1278
|
// The backend should always send a non-empty array of predictions if the response was successful.
|
|
1252
|
-
if (!responseJson.predictions ||
|
|
1253
|
-
throw new AIError(
|
|
1279
|
+
if (!responseJson.predictions || responseJson.predictions?.length === 0) {
|
|
1280
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, 'No predictions or filtered reason received from Vertex AI. Please report this issue with the full error details at https://github.com/firebase/firebase-js-sdk/issues.');
|
|
1254
1281
|
}
|
|
1255
1282
|
for (const prediction of responseJson.predictions) {
|
|
1256
1283
|
if (prediction.raiFilteredReason) {
|
|
@@ -1269,7 +1296,7 @@ async function handlePredictResponse(response) {
|
|
|
1269
1296
|
});
|
|
1270
1297
|
}
|
|
1271
1298
|
else {
|
|
1272
|
-
throw new AIError(
|
|
1299
|
+
throw new AIError(AIErrorCode.RESPONSE_ERROR, `Predictions array in response has missing properties. Response: ${JSON.stringify(responseJson)}`);
|
|
1273
1300
|
}
|
|
1274
1301
|
}
|
|
1275
1302
|
return { images, filteredReason };
|
|
@@ -1313,13 +1340,12 @@ async function handlePredictResponse(response) {
|
|
|
1313
1340
|
* @internal
|
|
1314
1341
|
*/
|
|
1315
1342
|
function mapGenerateContentRequest(generateContentRequest) {
|
|
1316
|
-
|
|
1317
|
-
(_a = generateContentRequest.safetySettings) === null || _a === void 0 ? void 0 : _a.forEach(safetySetting => {
|
|
1343
|
+
generateContentRequest.safetySettings?.forEach(safetySetting => {
|
|
1318
1344
|
if (safetySetting.method) {
|
|
1319
|
-
throw new AIError(
|
|
1345
|
+
throw new AIError(AIErrorCode.UNSUPPORTED, 'SafetySetting.method is not supported in the the Gemini Developer API. Please remove this property.');
|
|
1320
1346
|
}
|
|
1321
1347
|
});
|
|
1322
|
-
if (
|
|
1348
|
+
if (generateContentRequest.generationConfig?.topK) {
|
|
1323
1349
|
const roundedTopK = Math.round(generateContentRequest.generationConfig.topK);
|
|
1324
1350
|
if (roundedTopK !== generateContentRequest.generationConfig.topK) {
|
|
1325
1351
|
logger.warn('topK in GenerationConfig has been rounded to the nearest integer to match the format for requests to the Gemini Developer API.');
|
|
@@ -1360,7 +1386,10 @@ function mapGenerateContentResponse(googleAIResponse) {
|
|
|
1360
1386
|
*/
|
|
1361
1387
|
function mapCountTokensRequest(countTokensRequest, model) {
|
|
1362
1388
|
const mappedCountTokensRequest = {
|
|
1363
|
-
generateContentRequest:
|
|
1389
|
+
generateContentRequest: {
|
|
1390
|
+
model,
|
|
1391
|
+
...countTokensRequest
|
|
1392
|
+
}
|
|
1364
1393
|
};
|
|
1365
1394
|
return mappedCountTokensRequest;
|
|
1366
1395
|
}
|
|
@@ -1380,7 +1409,6 @@ function mapGenerateContentCandidates(candidates) {
|
|
|
1380
1409
|
let mappedSafetyRatings;
|
|
1381
1410
|
if (mappedCandidates) {
|
|
1382
1411
|
candidates.forEach(candidate => {
|
|
1383
|
-
var _a;
|
|
1384
1412
|
// Map citationSources to citations.
|
|
1385
1413
|
let citationMetadata;
|
|
1386
1414
|
if (candidate.citationMetadata) {
|
|
@@ -1391,15 +1419,19 @@ function mapGenerateContentCandidates(candidates) {
|
|
|
1391
1419
|
// Assign missing candidate SafetyRatings properties to their defaults if undefined.
|
|
1392
1420
|
if (candidate.safetyRatings) {
|
|
1393
1421
|
mappedSafetyRatings = candidate.safetyRatings.map(safetyRating => {
|
|
1394
|
-
|
|
1395
|
-
|
|
1422
|
+
return {
|
|
1423
|
+
...safetyRating,
|
|
1424
|
+
severity: safetyRating.severity ?? HarmSeverity.HARM_SEVERITY_UNSUPPORTED,
|
|
1425
|
+
probabilityScore: safetyRating.probabilityScore ?? 0,
|
|
1426
|
+
severityScore: safetyRating.severityScore ?? 0
|
|
1427
|
+
};
|
|
1396
1428
|
});
|
|
1397
1429
|
}
|
|
1398
1430
|
// videoMetadata is not supported.
|
|
1399
1431
|
// Throw early since developers may send a long video as input and only expect to pay
|
|
1400
1432
|
// for inference on a small portion of the video.
|
|
1401
|
-
if (
|
|
1402
|
-
throw new AIError(
|
|
1433
|
+
if (candidate.content?.parts.some(part => part?.videoMetadata)) {
|
|
1434
|
+
throw new AIError(AIErrorCode.UNSUPPORTED, 'Part.videoMetadata is not supported in the Gemini Developer API. Please remove this property.');
|
|
1403
1435
|
}
|
|
1404
1436
|
const mappedCandidate = {
|
|
1405
1437
|
index: candidate.index,
|
|
@@ -1419,13 +1451,12 @@ function mapPromptFeedback(promptFeedback) {
|
|
|
1419
1451
|
// Assign missing SafetyRating properties to their defaults if undefined.
|
|
1420
1452
|
const mappedSafetyRatings = [];
|
|
1421
1453
|
promptFeedback.safetyRatings.forEach(safetyRating => {
|
|
1422
|
-
var _a, _b, _c;
|
|
1423
1454
|
mappedSafetyRatings.push({
|
|
1424
1455
|
category: safetyRating.category,
|
|
1425
1456
|
probability: safetyRating.probability,
|
|
1426
|
-
severity:
|
|
1427
|
-
probabilityScore:
|
|
1428
|
-
severityScore:
|
|
1457
|
+
severity: safetyRating.severity ?? HarmSeverity.HARM_SEVERITY_UNSUPPORTED,
|
|
1458
|
+
probabilityScore: safetyRating.probabilityScore ?? 0,
|
|
1459
|
+
severityScore: safetyRating.severityScore ?? 0,
|
|
1429
1460
|
blocked: safetyRating.blocked
|
|
1430
1461
|
});
|
|
1431
1462
|
});
|
|
@@ -1486,24 +1517,22 @@ async function getResponsePromise(stream, apiSettings) {
|
|
|
1486
1517
|
allResponses.push(value);
|
|
1487
1518
|
}
|
|
1488
1519
|
}
|
|
1489
|
-
function generateResponseSequence(stream, apiSettings) {
|
|
1490
|
-
|
|
1491
|
-
|
|
1492
|
-
|
|
1493
|
-
|
|
1494
|
-
|
|
1495
|
-
break;
|
|
1496
|
-
}
|
|
1497
|
-
let enhancedResponse;
|
|
1498
|
-
if (apiSettings.backend.backendType === BackendType.GOOGLE_AI) {
|
|
1499
|
-
enhancedResponse = createEnhancedContentResponse(mapGenerateContentResponse(value));
|
|
1500
|
-
}
|
|
1501
|
-
else {
|
|
1502
|
-
enhancedResponse = createEnhancedContentResponse(value);
|
|
1503
|
-
}
|
|
1504
|
-
yield yield tslib.__await(enhancedResponse);
|
|
1520
|
+
async function* generateResponseSequence(stream, apiSettings) {
|
|
1521
|
+
const reader = stream.getReader();
|
|
1522
|
+
while (true) {
|
|
1523
|
+
const { value, done } = await reader.read();
|
|
1524
|
+
if (done) {
|
|
1525
|
+
break;
|
|
1505
1526
|
}
|
|
1506
|
-
|
|
1527
|
+
let enhancedResponse;
|
|
1528
|
+
if (apiSettings.backend.backendType === BackendType.GOOGLE_AI) {
|
|
1529
|
+
enhancedResponse = createEnhancedContentResponse(mapGenerateContentResponse(value));
|
|
1530
|
+
}
|
|
1531
|
+
else {
|
|
1532
|
+
enhancedResponse = createEnhancedContentResponse(value);
|
|
1533
|
+
}
|
|
1534
|
+
yield enhancedResponse;
|
|
1535
|
+
}
|
|
1507
1536
|
}
|
|
1508
1537
|
/**
|
|
1509
1538
|
* Reads a raw stream from the fetch response and join incomplete
|
|
@@ -1520,7 +1549,7 @@ function getResponseStream(inputStream) {
|
|
|
1520
1549
|
return reader.read().then(({ value, done }) => {
|
|
1521
1550
|
if (done) {
|
|
1522
1551
|
if (currentText.trim()) {
|
|
1523
|
-
controller.error(new AIError(
|
|
1552
|
+
controller.error(new AIError(AIErrorCode.PARSE_FAILED, 'Failed to parse stream'));
|
|
1524
1553
|
return;
|
|
1525
1554
|
}
|
|
1526
1555
|
controller.close();
|
|
@@ -1534,7 +1563,7 @@ function getResponseStream(inputStream) {
|
|
|
1534
1563
|
parsedResponse = JSON.parse(match[1]);
|
|
1535
1564
|
}
|
|
1536
1565
|
catch (e) {
|
|
1537
|
-
controller.error(new AIError(
|
|
1566
|
+
controller.error(new AIError(AIErrorCode.PARSE_FAILED, `Error parsing JSON response: "${match[1]}`));
|
|
1538
1567
|
return;
|
|
1539
1568
|
}
|
|
1540
1569
|
controller.enqueue(parsedResponse);
|
|
@@ -1555,7 +1584,7 @@ function getResponseStream(inputStream) {
|
|
|
1555
1584
|
function aggregateResponses(responses) {
|
|
1556
1585
|
const lastResponse = responses[responses.length - 1];
|
|
1557
1586
|
const aggregatedResponse = {
|
|
1558
|
-
promptFeedback: lastResponse
|
|
1587
|
+
promptFeedback: lastResponse?.promptFeedback
|
|
1559
1588
|
};
|
|
1560
1589
|
for (const response of responses) {
|
|
1561
1590
|
if (response.candidates) {
|
|
@@ -1579,6 +1608,8 @@ function aggregateResponses(responses) {
|
|
|
1579
1608
|
candidate.finishMessage;
|
|
1580
1609
|
aggregatedResponse.candidates[i].safetyRatings =
|
|
1581
1610
|
candidate.safetyRatings;
|
|
1611
|
+
aggregatedResponse.candidates[i].groundingMetadata =
|
|
1612
|
+
candidate.groundingMetadata;
|
|
1582
1613
|
/**
|
|
1583
1614
|
* Candidates should always have content and parts, but this handles
|
|
1584
1615
|
* possible malformed responses.
|
|
@@ -1605,7 +1636,7 @@ function aggregateResponses(responses) {
|
|
|
1605
1636
|
newPart.functionCall = part.functionCall;
|
|
1606
1637
|
}
|
|
1607
1638
|
if (Object.keys(newPart).length === 0) {
|
|
1608
|
-
throw new AIError(
|
|
1639
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, 'Part should have at least one property, but there are none. This is likely caused ' +
|
|
1609
1640
|
'by a malformed response from the backend.');
|
|
1610
1641
|
}
|
|
1611
1642
|
aggregatedResponse.candidates[i].content.parts.push(newPart);
|
|
@@ -1740,10 +1771,10 @@ function assignRoleToPartsAndValidateSendMessageRequest(parts) {
|
|
|
1740
1771
|
}
|
|
1741
1772
|
}
|
|
1742
1773
|
if (hasUserContent && hasFunctionContent) {
|
|
1743
|
-
throw new AIError(
|
|
1774
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, 'Within a single message, FunctionResponse cannot be mixed with other type of Part in the request for sending chat message.');
|
|
1744
1775
|
}
|
|
1745
1776
|
if (!hasUserContent && !hasFunctionContent) {
|
|
1746
|
-
throw new AIError(
|
|
1777
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, 'No Content is provided for sending chat message.');
|
|
1747
1778
|
}
|
|
1748
1779
|
if (hasUserContent) {
|
|
1749
1780
|
return userContent;
|
|
@@ -1836,16 +1867,16 @@ function validateChatHistory(history) {
|
|
|
1836
1867
|
for (const currContent of history) {
|
|
1837
1868
|
const { role, parts } = currContent;
|
|
1838
1869
|
if (!prevContent && role !== 'user') {
|
|
1839
|
-
throw new AIError(
|
|
1870
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `First Content should be with role 'user', got ${role}`);
|
|
1840
1871
|
}
|
|
1841
1872
|
if (!POSSIBLE_ROLES.includes(role)) {
|
|
1842
|
-
throw new AIError(
|
|
1873
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `Each item should include role field. Got ${role} but valid roles are: ${JSON.stringify(POSSIBLE_ROLES)}`);
|
|
1843
1874
|
}
|
|
1844
1875
|
if (!Array.isArray(parts)) {
|
|
1845
|
-
throw new AIError(
|
|
1876
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `Content should have 'parts' but property with an array of Parts`);
|
|
1846
1877
|
}
|
|
1847
1878
|
if (parts.length === 0) {
|
|
1848
|
-
throw new AIError(
|
|
1879
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `Each Content should have at least one part`);
|
|
1849
1880
|
}
|
|
1850
1881
|
const countFields = {
|
|
1851
1882
|
text: 0,
|
|
@@ -1863,13 +1894,13 @@ function validateChatHistory(history) {
|
|
|
1863
1894
|
const validParts = VALID_PARTS_PER_ROLE[role];
|
|
1864
1895
|
for (const key of VALID_PART_FIELDS) {
|
|
1865
1896
|
if (!validParts.includes(key) && countFields[key] > 0) {
|
|
1866
|
-
throw new AIError(
|
|
1897
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `Content with role '${role}' can't contain '${key}' part`);
|
|
1867
1898
|
}
|
|
1868
1899
|
}
|
|
1869
1900
|
if (prevContent) {
|
|
1870
1901
|
const validPreviousContentRoles = VALID_PREVIOUS_CONTENT_ROLES[role];
|
|
1871
1902
|
if (!validPreviousContentRoles.includes(prevContent.role)) {
|
|
1872
|
-
throw new AIError(
|
|
1903
|
+
throw new AIError(AIErrorCode.INVALID_CONTENT, `Content with role '${role}' can't follow '${prevContent.role}'. Valid previous roles: ${JSON.stringify(VALID_PREVIOUS_CONTENT_ROLES)}`);
|
|
1873
1904
|
}
|
|
1874
1905
|
}
|
|
1875
1906
|
prevContent = currContent;
|
|
@@ -1910,7 +1941,7 @@ class ChatSession {
|
|
|
1910
1941
|
this._history = [];
|
|
1911
1942
|
this._sendPromise = Promise.resolve();
|
|
1912
1943
|
this._apiSettings = apiSettings;
|
|
1913
|
-
if (params
|
|
1944
|
+
if (params?.history) {
|
|
1914
1945
|
validateChatHistory(params.history);
|
|
1915
1946
|
this._history = params.history;
|
|
1916
1947
|
}
|
|
@@ -1929,15 +1960,14 @@ class ChatSession {
|
|
|
1929
1960
|
* {@link GenerateContentResult}
|
|
1930
1961
|
*/
|
|
1931
1962
|
async sendMessage(request) {
|
|
1932
|
-
var _a, _b, _c, _d, _e;
|
|
1933
1963
|
await this._sendPromise;
|
|
1934
1964
|
const newContent = formatNewContent(request);
|
|
1935
1965
|
const generateContentRequest = {
|
|
1936
|
-
safetySettings:
|
|
1937
|
-
generationConfig:
|
|
1938
|
-
tools:
|
|
1939
|
-
toolConfig:
|
|
1940
|
-
systemInstruction:
|
|
1966
|
+
safetySettings: this.params?.safetySettings,
|
|
1967
|
+
generationConfig: this.params?.generationConfig,
|
|
1968
|
+
tools: this.params?.tools,
|
|
1969
|
+
toolConfig: this.params?.toolConfig,
|
|
1970
|
+
systemInstruction: this.params?.systemInstruction,
|
|
1941
1971
|
contents: [...this._history, newContent]
|
|
1942
1972
|
};
|
|
1943
1973
|
let finalResult = {};
|
|
@@ -1945,14 +1975,13 @@ class ChatSession {
|
|
|
1945
1975
|
this._sendPromise = this._sendPromise
|
|
1946
1976
|
.then(() => generateContent(this._apiSettings, this.model, generateContentRequest, this.requestOptions))
|
|
1947
1977
|
.then(result => {
|
|
1948
|
-
var _a, _b;
|
|
1949
1978
|
if (result.response.candidates &&
|
|
1950
1979
|
result.response.candidates.length > 0) {
|
|
1951
1980
|
this._history.push(newContent);
|
|
1952
1981
|
const responseContent = {
|
|
1953
|
-
parts:
|
|
1982
|
+
parts: result.response.candidates?.[0].content.parts || [],
|
|
1954
1983
|
// Response seems to come back without a role set.
|
|
1955
|
-
role:
|
|
1984
|
+
role: result.response.candidates?.[0].content.role || 'model'
|
|
1956
1985
|
};
|
|
1957
1986
|
this._history.push(responseContent);
|
|
1958
1987
|
}
|
|
@@ -1973,15 +2002,14 @@ class ChatSession {
|
|
|
1973
2002
|
* and a response promise.
|
|
1974
2003
|
*/
|
|
1975
2004
|
async sendMessageStream(request) {
|
|
1976
|
-
var _a, _b, _c, _d, _e;
|
|
1977
2005
|
await this._sendPromise;
|
|
1978
2006
|
const newContent = formatNewContent(request);
|
|
1979
2007
|
const generateContentRequest = {
|
|
1980
|
-
safetySettings:
|
|
1981
|
-
generationConfig:
|
|
1982
|
-
tools:
|
|
1983
|
-
toolConfig:
|
|
1984
|
-
systemInstruction:
|
|
2008
|
+
safetySettings: this.params?.safetySettings,
|
|
2009
|
+
generationConfig: this.params?.generationConfig,
|
|
2010
|
+
tools: this.params?.tools,
|
|
2011
|
+
toolConfig: this.params?.toolConfig,
|
|
2012
|
+
systemInstruction: this.params?.systemInstruction,
|
|
1985
2013
|
contents: [...this._history, newContent]
|
|
1986
2014
|
};
|
|
1987
2015
|
const streamPromise = generateContentStream(this._apiSettings, this.model, generateContentRequest, this.requestOptions);
|
|
@@ -1997,7 +2025,7 @@ class ChatSession {
|
|
|
1997
2025
|
.then(response => {
|
|
1998
2026
|
if (response.candidates && response.candidates.length > 0) {
|
|
1999
2027
|
this._history.push(newContent);
|
|
2000
|
-
const responseContent =
|
|
2028
|
+
const responseContent = { ...response.candidates[0].content };
|
|
2001
2029
|
// Response seems to come back without a role set.
|
|
2002
2030
|
if (!responseContent.role) {
|
|
2003
2031
|
responseContent.role = 'model';
|
|
@@ -2090,7 +2118,14 @@ class GenerativeModel extends AIModel {
|
|
|
2090
2118
|
*/
|
|
2091
2119
|
async generateContent(request) {
|
|
2092
2120
|
const formattedParams = formatGenerateContentInput(request);
|
|
2093
|
-
return generateContent(this._apiSettings, this.model,
|
|
2121
|
+
return generateContent(this._apiSettings, this.model, {
|
|
2122
|
+
generationConfig: this.generationConfig,
|
|
2123
|
+
safetySettings: this.safetySettings,
|
|
2124
|
+
tools: this.tools,
|
|
2125
|
+
toolConfig: this.toolConfig,
|
|
2126
|
+
systemInstruction: this.systemInstruction,
|
|
2127
|
+
...formattedParams
|
|
2128
|
+
}, this.requestOptions);
|
|
2094
2129
|
}
|
|
2095
2130
|
/**
|
|
2096
2131
|
* Makes a single streaming call to the model
|
|
@@ -2100,14 +2135,33 @@ class GenerativeModel extends AIModel {
|
|
|
2100
2135
|
*/
|
|
2101
2136
|
async generateContentStream(request) {
|
|
2102
2137
|
const formattedParams = formatGenerateContentInput(request);
|
|
2103
|
-
return generateContentStream(this._apiSettings, this.model,
|
|
2138
|
+
return generateContentStream(this._apiSettings, this.model, {
|
|
2139
|
+
generationConfig: this.generationConfig,
|
|
2140
|
+
safetySettings: this.safetySettings,
|
|
2141
|
+
tools: this.tools,
|
|
2142
|
+
toolConfig: this.toolConfig,
|
|
2143
|
+
systemInstruction: this.systemInstruction,
|
|
2144
|
+
...formattedParams
|
|
2145
|
+
}, this.requestOptions);
|
|
2104
2146
|
}
|
|
2105
2147
|
/**
|
|
2106
2148
|
* Gets a new {@link ChatSession} instance which can be used for
|
|
2107
2149
|
* multi-turn chats.
|
|
2108
2150
|
*/
|
|
2109
2151
|
startChat(startChatParams) {
|
|
2110
|
-
return new ChatSession(this._apiSettings, this.model,
|
|
2152
|
+
return new ChatSession(this._apiSettings, this.model, {
|
|
2153
|
+
tools: this.tools,
|
|
2154
|
+
toolConfig: this.toolConfig,
|
|
2155
|
+
systemInstruction: this.systemInstruction,
|
|
2156
|
+
generationConfig: this.generationConfig,
|
|
2157
|
+
safetySettings: this.safetySettings,
|
|
2158
|
+
/**
|
|
2159
|
+
* Overrides params inherited from GenerativeModel with those explicitly set in the
|
|
2160
|
+
* StartChatParams. For example, if startChatParams.generationConfig is set, it'll override
|
|
2161
|
+
* this.generationConfig.
|
|
2162
|
+
*/
|
|
2163
|
+
...startChatParams
|
|
2164
|
+
}, this.requestOptions);
|
|
2111
2165
|
}
|
|
2112
2166
|
/**
|
|
2113
2167
|
* Counts the tokens in the provided request.
|
|
@@ -2193,7 +2247,10 @@ class ImagenModel extends AIModel {
|
|
|
2193
2247
|
* @beta
|
|
2194
2248
|
*/
|
|
2195
2249
|
async generateImages(prompt) {
|
|
2196
|
-
const body = createPredictRequestBody(prompt,
|
|
2250
|
+
const body = createPredictRequestBody(prompt, {
|
|
2251
|
+
...this.generationConfig,
|
|
2252
|
+
...this.safetySettings
|
|
2253
|
+
});
|
|
2197
2254
|
const response = await makeRequest(this.model, Task.PREDICT, this._apiSettings,
|
|
2198
2255
|
/* stream */ false, JSON.stringify(body), this.requestOptions);
|
|
2199
2256
|
return handlePredictResponse(response);
|
|
@@ -2218,7 +2275,11 @@ class ImagenModel extends AIModel {
|
|
|
2218
2275
|
* If all images are filtered, the `images` array will be empty.
|
|
2219
2276
|
*/
|
|
2220
2277
|
async generateImagesGCS(prompt, gcsURI) {
|
|
2221
|
-
const body = createPredictRequestBody(prompt,
|
|
2278
|
+
const body = createPredictRequestBody(prompt, {
|
|
2279
|
+
gcsURI,
|
|
2280
|
+
...this.generationConfig,
|
|
2281
|
+
...this.safetySettings
|
|
2282
|
+
});
|
|
2222
2283
|
const response = await makeRequest(this.model, Task.PREDICT, this._apiSettings,
|
|
2223
2284
|
/* stream */ false, JSON.stringify(body), this.requestOptions);
|
|
2224
2285
|
return handlePredictResponse(response);
|
|
@@ -2250,12 +2311,19 @@ class ImagenModel extends AIModel {
|
|
|
2250
2311
|
*/
|
|
2251
2312
|
class Schema {
|
|
2252
2313
|
constructor(schemaParams) {
|
|
2314
|
+
// TODO(dlarocque): Enforce this with union types
|
|
2315
|
+
if (!schemaParams.type && !schemaParams.anyOf) {
|
|
2316
|
+
throw new AIError(AIErrorCode.INVALID_SCHEMA, "A schema must have either a 'type' or an 'anyOf' array of sub-schemas.");
|
|
2317
|
+
}
|
|
2253
2318
|
// eslint-disable-next-line guard-for-in
|
|
2254
2319
|
for (const paramKey in schemaParams) {
|
|
2255
2320
|
this[paramKey] = schemaParams[paramKey];
|
|
2256
2321
|
}
|
|
2257
2322
|
// Ensure these are explicitly set to avoid TS errors.
|
|
2258
2323
|
this.type = schemaParams.type;
|
|
2324
|
+
this.format = schemaParams.hasOwnProperty('format')
|
|
2325
|
+
? schemaParams.format
|
|
2326
|
+
: undefined;
|
|
2259
2327
|
this.nullable = schemaParams.hasOwnProperty('nullable')
|
|
2260
2328
|
? !!schemaParams.nullable
|
|
2261
2329
|
: false;
|
|
@@ -2271,7 +2339,7 @@ class Schema {
|
|
|
2271
2339
|
};
|
|
2272
2340
|
for (const prop in this) {
|
|
2273
2341
|
if (this.hasOwnProperty(prop) && this[prop] !== undefined) {
|
|
2274
|
-
if (prop !== 'required' || this.type ===
|
|
2342
|
+
if (prop !== 'required' || this.type === SchemaType.OBJECT) {
|
|
2275
2343
|
obj[prop] = this[prop];
|
|
2276
2344
|
}
|
|
2277
2345
|
}
|
|
@@ -2302,6 +2370,9 @@ class Schema {
|
|
|
2302
2370
|
static boolean(booleanParams) {
|
|
2303
2371
|
return new BooleanSchema(booleanParams);
|
|
2304
2372
|
}
|
|
2373
|
+
static anyOf(anyOfParams) {
|
|
2374
|
+
return new AnyOfSchema(anyOfParams);
|
|
2375
|
+
}
|
|
2305
2376
|
}
|
|
2306
2377
|
/**
|
|
2307
2378
|
* Schema class for "integer" types.
|
|
@@ -2309,7 +2380,10 @@ class Schema {
|
|
|
2309
2380
|
*/
|
|
2310
2381
|
class IntegerSchema extends Schema {
|
|
2311
2382
|
constructor(schemaParams) {
|
|
2312
|
-
super(
|
|
2383
|
+
super({
|
|
2384
|
+
type: SchemaType.INTEGER,
|
|
2385
|
+
...schemaParams
|
|
2386
|
+
});
|
|
2313
2387
|
}
|
|
2314
2388
|
}
|
|
2315
2389
|
/**
|
|
@@ -2318,7 +2392,10 @@ class IntegerSchema extends Schema {
|
|
|
2318
2392
|
*/
|
|
2319
2393
|
class NumberSchema extends Schema {
|
|
2320
2394
|
constructor(schemaParams) {
|
|
2321
|
-
super(
|
|
2395
|
+
super({
|
|
2396
|
+
type: SchemaType.NUMBER,
|
|
2397
|
+
...schemaParams
|
|
2398
|
+
});
|
|
2322
2399
|
}
|
|
2323
2400
|
}
|
|
2324
2401
|
/**
|
|
@@ -2327,7 +2404,10 @@ class NumberSchema extends Schema {
|
|
|
2327
2404
|
*/
|
|
2328
2405
|
class BooleanSchema extends Schema {
|
|
2329
2406
|
constructor(schemaParams) {
|
|
2330
|
-
super(
|
|
2407
|
+
super({
|
|
2408
|
+
type: SchemaType.BOOLEAN,
|
|
2409
|
+
...schemaParams
|
|
2410
|
+
});
|
|
2331
2411
|
}
|
|
2332
2412
|
}
|
|
2333
2413
|
/**
|
|
@@ -2337,7 +2417,10 @@ class BooleanSchema extends Schema {
|
|
|
2337
2417
|
*/
|
|
2338
2418
|
class StringSchema extends Schema {
|
|
2339
2419
|
constructor(schemaParams, enumValues) {
|
|
2340
|
-
super(
|
|
2420
|
+
super({
|
|
2421
|
+
type: SchemaType.STRING,
|
|
2422
|
+
...schemaParams
|
|
2423
|
+
});
|
|
2341
2424
|
this.enum = enumValues;
|
|
2342
2425
|
}
|
|
2343
2426
|
/**
|
|
@@ -2359,7 +2442,10 @@ class StringSchema extends Schema {
|
|
|
2359
2442
|
*/
|
|
2360
2443
|
class ArraySchema extends Schema {
|
|
2361
2444
|
constructor(schemaParams, items) {
|
|
2362
|
-
super(
|
|
2445
|
+
super({
|
|
2446
|
+
type: SchemaType.ARRAY,
|
|
2447
|
+
...schemaParams
|
|
2448
|
+
});
|
|
2363
2449
|
this.items = items;
|
|
2364
2450
|
}
|
|
2365
2451
|
/**
|
|
@@ -2378,7 +2464,10 @@ class ArraySchema extends Schema {
|
|
|
2378
2464
|
*/
|
|
2379
2465
|
class ObjectSchema extends Schema {
|
|
2380
2466
|
constructor(schemaParams, properties, optionalProperties = []) {
|
|
2381
|
-
super(
|
|
2467
|
+
super({
|
|
2468
|
+
type: SchemaType.OBJECT,
|
|
2469
|
+
...schemaParams
|
|
2470
|
+
});
|
|
2382
2471
|
this.properties = properties;
|
|
2383
2472
|
this.optionalProperties = optionalProperties;
|
|
2384
2473
|
}
|
|
@@ -2387,12 +2476,12 @@ class ObjectSchema extends Schema {
|
|
|
2387
2476
|
*/
|
|
2388
2477
|
toJSON() {
|
|
2389
2478
|
const obj = super.toJSON();
|
|
2390
|
-
obj.properties =
|
|
2479
|
+
obj.properties = { ...this.properties };
|
|
2391
2480
|
const required = [];
|
|
2392
2481
|
if (this.optionalProperties) {
|
|
2393
2482
|
for (const propertyKey of this.optionalProperties) {
|
|
2394
2483
|
if (!this.properties.hasOwnProperty(propertyKey)) {
|
|
2395
|
-
throw new AIError(
|
|
2484
|
+
throw new AIError(AIErrorCode.INVALID_SCHEMA, `Property "${propertyKey}" specified in "optionalProperties" does not exist.`);
|
|
2396
2485
|
}
|
|
2397
2486
|
}
|
|
2398
2487
|
}
|
|
@@ -2411,6 +2500,34 @@ class ObjectSchema extends Schema {
|
|
|
2411
2500
|
return obj;
|
|
2412
2501
|
}
|
|
2413
2502
|
}
|
|
2503
|
+
/**
|
|
2504
|
+
* Schema class representing a value that can conform to any of the provided sub-schemas. This is
|
|
2505
|
+
* useful when a field can accept multiple distinct types or structures.
|
|
2506
|
+
* @public
|
|
2507
|
+
*/
|
|
2508
|
+
class AnyOfSchema extends Schema {
|
|
2509
|
+
constructor(schemaParams) {
|
|
2510
|
+
if (schemaParams.anyOf.length === 0) {
|
|
2511
|
+
throw new AIError(AIErrorCode.INVALID_SCHEMA, "The 'anyOf' array must not be empty.");
|
|
2512
|
+
}
|
|
2513
|
+
super({
|
|
2514
|
+
...schemaParams,
|
|
2515
|
+
type: undefined // anyOf schemas do not have an explicit type
|
|
2516
|
+
});
|
|
2517
|
+
this.anyOf = schemaParams.anyOf;
|
|
2518
|
+
}
|
|
2519
|
+
/**
|
|
2520
|
+
* @internal
|
|
2521
|
+
*/
|
|
2522
|
+
toJSON() {
|
|
2523
|
+
const obj = super.toJSON();
|
|
2524
|
+
// Ensure the 'anyOf' property contains serialized SchemaRequest objects.
|
|
2525
|
+
if (this.anyOf && Array.isArray(this.anyOf)) {
|
|
2526
|
+
obj.anyOf = this.anyOf.map(s => s.toJSON());
|
|
2527
|
+
}
|
|
2528
|
+
return obj;
|
|
2529
|
+
}
|
|
2530
|
+
}
|
|
2414
2531
|
|
|
2415
2532
|
/**
|
|
2416
2533
|
* @license
|
|
@@ -2492,50 +2609,6 @@ class ImagenImageFormat {
|
|
|
2492
2609
|
* See the License for the specific language governing permissions and
|
|
2493
2610
|
* limitations under the License.
|
|
2494
2611
|
*/
|
|
2495
|
-
/**
|
|
2496
|
-
* @deprecated Use the new {@link AIModel} instead. The Vertex AI in Firebase SDK has been
|
|
2497
|
-
* replaced with the Firebase AI SDK to accommodate the evolving set of supported features and
|
|
2498
|
-
* services. For migration details, see the {@link https://firebase.google.com/docs/vertex-ai/migrate-to-latest-sdk | migration guide}.
|
|
2499
|
-
*
|
|
2500
|
-
* Base class for Firebase AI model APIs.
|
|
2501
|
-
*
|
|
2502
|
-
* @public
|
|
2503
|
-
*/
|
|
2504
|
-
const VertexAIModel = AIModel;
|
|
2505
|
-
/**
|
|
2506
|
-
* @deprecated Use the new {@link AIError} instead. The Vertex AI in Firebase SDK has been
|
|
2507
|
-
* replaced with the Firebase AI SDK to accommodate the evolving set of supported features and
|
|
2508
|
-
* services. For migration details, see the {@link https://firebase.google.com/docs/vertex-ai/migrate-to-latest-sdk | migration guide}.
|
|
2509
|
-
*
|
|
2510
|
-
* Error class for the Firebase AI SDK.
|
|
2511
|
-
*
|
|
2512
|
-
* @public
|
|
2513
|
-
*/
|
|
2514
|
-
const VertexAIError = AIError;
|
|
2515
|
-
/**
|
|
2516
|
-
* @deprecated Use the new {@link getAI | getAI()} instead. The Vertex AI in Firebase SDK has been
|
|
2517
|
-
* replaced with the Firebase AI SDK to accommodate the evolving set of supported features and
|
|
2518
|
-
* services. For migration details, see the {@link https://firebase.google.com/docs/vertex-ai/migrate-to-latest-sdk | migration guide}.
|
|
2519
|
-
*
|
|
2520
|
-
* Returns a {@link VertexAI} instance for the given app, configured to use the
|
|
2521
|
-
* Vertex AI Gemini API. This instance will be
|
|
2522
|
-
* configured to use the Vertex AI Gemini API.
|
|
2523
|
-
*
|
|
2524
|
-
* @param app - The {@link @firebase/app#FirebaseApp} to use.
|
|
2525
|
-
* @param options - Options to configure the Vertex AI instance, including the location.
|
|
2526
|
-
*
|
|
2527
|
-
* @public
|
|
2528
|
-
*/
|
|
2529
|
-
function getVertexAI(app$1 = app.getApp(), options) {
|
|
2530
|
-
app$1 = util.getModularInstance(app$1);
|
|
2531
|
-
// Dependencies
|
|
2532
|
-
const AIProvider = app._getProvider(app$1, AI_TYPE);
|
|
2533
|
-
const backend = new VertexAIBackend(options === null || options === void 0 ? void 0 : options.location);
|
|
2534
|
-
const identifier = encodeInstanceIdentifier(backend);
|
|
2535
|
-
return AIProvider.getImmediate({
|
|
2536
|
-
identifier
|
|
2537
|
-
});
|
|
2538
|
-
}
|
|
2539
2612
|
/**
|
|
2540
2613
|
* Returns the default {@link AI} instance that is associated with the provided
|
|
2541
2614
|
* {@link @firebase/app#FirebaseApp}. If no instance exists, initializes a new instance with the
|
|
@@ -2581,7 +2654,7 @@ function getAI(app$1 = app.getApp(), options = { backend: new GoogleAIBackend()
|
|
|
2581
2654
|
*/
|
|
2582
2655
|
function getGenerativeModel(ai, modelParams, requestOptions) {
|
|
2583
2656
|
if (!modelParams.model) {
|
|
2584
|
-
throw new AIError(
|
|
2657
|
+
throw new AIError(AIErrorCode.NO_MODEL, `Must provide a model name. Example: getGenerativeModel({ model: 'my-model-name' })`);
|
|
2585
2658
|
}
|
|
2586
2659
|
return new GenerativeModel(ai, modelParams, requestOptions);
|
|
2587
2660
|
}
|
|
@@ -2601,7 +2674,7 @@ function getGenerativeModel(ai, modelParams, requestOptions) {
|
|
|
2601
2674
|
*/
|
|
2602
2675
|
function getImagenModel(ai, modelParams, requestOptions) {
|
|
2603
2676
|
if (!modelParams.model) {
|
|
2604
|
-
throw new AIError(
|
|
2677
|
+
throw new AIError(AIErrorCode.NO_MODEL, `Must provide a model name. Example: getImagenModel({ model: 'my-model-name' })`);
|
|
2605
2678
|
}
|
|
2606
2679
|
return new ImagenModel(ai, modelParams, requestOptions);
|
|
2607
2680
|
}
|
|
@@ -2614,7 +2687,7 @@ function getImagenModel(ai, modelParams, requestOptions) {
|
|
|
2614
2687
|
function registerAI() {
|
|
2615
2688
|
app._registerComponent(new component.Component(AI_TYPE, (container, { instanceIdentifier }) => {
|
|
2616
2689
|
if (!instanceIdentifier) {
|
|
2617
|
-
throw new AIError(
|
|
2690
|
+
throw new AIError(AIErrorCode.ERROR, 'AIService instance identifier is undefined.');
|
|
2618
2691
|
}
|
|
2619
2692
|
const backend = decodeInstanceIdentifier(instanceIdentifier);
|
|
2620
2693
|
// getImmediate for FirebaseApp will always succeed
|
|
@@ -2624,34 +2697,46 @@ function registerAI() {
|
|
|
2624
2697
|
return new AIService(app, backend, auth, appCheckProvider);
|
|
2625
2698
|
}, "PUBLIC" /* ComponentType.PUBLIC */).setMultipleInstances(true));
|
|
2626
2699
|
app.registerVersion(name, version);
|
|
2627
|
-
// BUILD_TARGET will be replaced by values like
|
|
2628
|
-
app.registerVersion(name, version, '
|
|
2700
|
+
// BUILD_TARGET will be replaced by values like esm, cjs, etc during the compilation
|
|
2701
|
+
app.registerVersion(name, version, 'cjs2020');
|
|
2629
2702
|
}
|
|
2630
2703
|
registerAI();
|
|
2631
2704
|
|
|
2632
2705
|
exports.AIError = AIError;
|
|
2706
|
+
exports.AIErrorCode = AIErrorCode;
|
|
2633
2707
|
exports.AIModel = AIModel;
|
|
2708
|
+
exports.AnyOfSchema = AnyOfSchema;
|
|
2634
2709
|
exports.ArraySchema = ArraySchema;
|
|
2635
2710
|
exports.Backend = Backend;
|
|
2636
2711
|
exports.BackendType = BackendType;
|
|
2712
|
+
exports.BlockReason = BlockReason;
|
|
2637
2713
|
exports.BooleanSchema = BooleanSchema;
|
|
2638
2714
|
exports.ChatSession = ChatSession;
|
|
2715
|
+
exports.FinishReason = FinishReason;
|
|
2716
|
+
exports.FunctionCallingMode = FunctionCallingMode;
|
|
2639
2717
|
exports.GenerativeModel = GenerativeModel;
|
|
2640
2718
|
exports.GoogleAIBackend = GoogleAIBackend;
|
|
2719
|
+
exports.HarmBlockMethod = HarmBlockMethod;
|
|
2720
|
+
exports.HarmBlockThreshold = HarmBlockThreshold;
|
|
2721
|
+
exports.HarmCategory = HarmCategory;
|
|
2722
|
+
exports.HarmProbability = HarmProbability;
|
|
2723
|
+
exports.HarmSeverity = HarmSeverity;
|
|
2724
|
+
exports.ImagenAspectRatio = ImagenAspectRatio;
|
|
2641
2725
|
exports.ImagenImageFormat = ImagenImageFormat;
|
|
2642
2726
|
exports.ImagenModel = ImagenModel;
|
|
2727
|
+
exports.ImagenPersonFilterLevel = ImagenPersonFilterLevel;
|
|
2728
|
+
exports.ImagenSafetyFilterLevel = ImagenSafetyFilterLevel;
|
|
2643
2729
|
exports.IntegerSchema = IntegerSchema;
|
|
2730
|
+
exports.Modality = Modality;
|
|
2644
2731
|
exports.NumberSchema = NumberSchema;
|
|
2645
2732
|
exports.ObjectSchema = ObjectSchema;
|
|
2646
2733
|
exports.POSSIBLE_ROLES = POSSIBLE_ROLES;
|
|
2647
2734
|
exports.ResponseModality = ResponseModality;
|
|
2648
2735
|
exports.Schema = Schema;
|
|
2736
|
+
exports.SchemaType = SchemaType;
|
|
2649
2737
|
exports.StringSchema = StringSchema;
|
|
2650
2738
|
exports.VertexAIBackend = VertexAIBackend;
|
|
2651
|
-
exports.VertexAIError = VertexAIError;
|
|
2652
|
-
exports.VertexAIModel = VertexAIModel;
|
|
2653
2739
|
exports.getAI = getAI;
|
|
2654
2740
|
exports.getGenerativeModel = getGenerativeModel;
|
|
2655
2741
|
exports.getImagenModel = getImagenModel;
|
|
2656
|
-
exports.getVertexAI = getVertexAI;
|
|
2657
2742
|
//# sourceMappingURL=index.cjs.js.map
|