@jaypie/llm 1.2.23 → 1.2.25

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.
@@ -72,6 +72,7 @@ export interface GeminiGenerateContentConfig {
72
72
  };
73
73
  responseMimeType?: string;
74
74
  responseJsonSchema?: JsonObject;
75
+ responseSchema?: JsonObject;
75
76
  temperature?: number;
76
77
  topP?: number;
77
78
  topK?: number;
@@ -2,6 +2,7 @@ export * from "./determineModelProvider.js";
2
2
  export * from "./extractReasoning.js";
3
3
  export * from "./formatOperateInput.js";
4
4
  export * from "./formatOperateMessage.js";
5
+ export * from "./jsonSchemaToOpenApi3.js";
5
6
  export * from "./logger.js";
6
7
  export * from "./maxTurnsFromOptions.js";
7
8
  export * from "./naturalZodSchema.js";
@@ -0,0 +1,10 @@
1
+ import { JsonObject } from "@jaypie/types";
2
+ /**
3
+ * Converts a JSON Schema (Draft 2020-12) object to the OpenAPI 3.0 schema subset
4
+ * that Gemini's `responseSchema` accepts. This constrains generation (not just validation)
5
+ * and avoids the `items`-keyword leakage bug in `responseJsonSchema`.
6
+ *
7
+ * Strips: $schema, additionalProperties, $defs, $ref (inlines where possible), const
8
+ * Preserves: type, properties, required, items, enum, description, nullable
9
+ */
10
+ export declare function jsonSchemaToOpenApi3(schema: JsonObject): JsonObject;
@@ -1,2 +1 @@
1
1
  export declare const getLogger: () => import("@jaypie/logger/dist/esm/JaypieLogger").default;
2
- export declare const log: import("@jaypie/logger/dist/esm/JaypieLogger").default;
package/dist/esm/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { ConfigurationError, BadGatewayError, TooManyRequestsError, NotImplementedError } from '@jaypie/errors';
2
- import log$3, { log as log$2 } from '@jaypie/logger';
2
+ import log$2, { log as log$1 } from '@jaypie/logger';
3
3
  import { z } from 'zod/v4';
4
4
  import { placeholders, JAYPIE, resolveValue, sleep } from '@jaypie/kit';
5
5
  import RandomLib from 'random';
@@ -552,8 +552,51 @@ function formatOperateInput(input, options) {
552
552
  return [input];
553
553
  }
554
554
 
555
- const getLogger$5 = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
556
- const log$1 = getLogger$5();
555
+ /**
556
+ * Converts a JSON Schema (Draft 2020-12) object to the OpenAPI 3.0 schema subset
557
+ * that Gemini's `responseSchema` accepts. This constrains generation (not just validation)
558
+ * and avoids the `items`-keyword leakage bug in `responseJsonSchema`.
559
+ *
560
+ * Strips: $schema, additionalProperties, $defs, $ref (inlines where possible), const
561
+ * Preserves: type, properties, required, items, enum, description, nullable
562
+ */
563
+ function jsonSchemaToOpenApi3(schema) {
564
+ if (typeof schema !== "object" || schema === null || Array.isArray(schema)) {
565
+ return schema;
566
+ }
567
+ const result = {};
568
+ for (const [key, value] of Object.entries(schema)) {
569
+ // Strip JSON Schema keywords not in OpenAPI 3.0 subset
570
+ if (key === "$schema" ||
571
+ key === "$defs" ||
572
+ key === "additionalProperties" ||
573
+ key === "const" ||
574
+ key === "$ref") {
575
+ continue;
576
+ }
577
+ if (key === "properties" &&
578
+ typeof value === "object" &&
579
+ value !== null &&
580
+ !Array.isArray(value)) {
581
+ const convertedProps = {};
582
+ for (const [propKey, propValue] of Object.entries(value)) {
583
+ convertedProps[propKey] = jsonSchemaToOpenApi3(propValue);
584
+ }
585
+ result[key] = convertedProps;
586
+ }
587
+ else if (key === "items" &&
588
+ typeof value === "object" &&
589
+ value !== null) {
590
+ result[key] = jsonSchemaToOpenApi3(value);
591
+ }
592
+ else {
593
+ result[key] = value;
594
+ }
595
+ }
596
+ return result;
597
+ }
598
+
599
+ const getLogger$5 = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
557
600
 
558
601
  // Turn policy constants
559
602
  const MAX_TURNS_ABSOLUTE_LIMIT = 72;
@@ -1539,11 +1582,21 @@ class GeminiAdapter extends BaseProviderAdapter {
1539
1582
  // Gemini doesn't support combining function calling with responseMimeType: 'application/json'
1540
1583
  // When tools are present, structured output is handled via the structured_output tool
1541
1584
  if (request.format && !(request.tools && request.tools.length > 0)) {
1542
- geminiRequest.config = {
1543
- ...geminiRequest.config,
1544
- responseMimeType: "application/json",
1545
- responseJsonSchema: request.format,
1546
- };
1585
+ const useJsonSchema = request.providerOptions?.useJsonSchema === true;
1586
+ if (useJsonSchema) {
1587
+ geminiRequest.config = {
1588
+ ...geminiRequest.config,
1589
+ responseMimeType: "application/json",
1590
+ responseJsonSchema: request.format,
1591
+ };
1592
+ }
1593
+ else {
1594
+ geminiRequest.config = {
1595
+ ...geminiRequest.config,
1596
+ responseMimeType: "application/json",
1597
+ responseSchema: jsonSchemaToOpenApi3(request.format),
1598
+ };
1599
+ }
1547
1600
  }
1548
1601
  // When format is specified with tools, add instruction to use structured_output tool
1549
1602
  if (request.format && request.tools && request.tools.length > 0) {
@@ -1611,11 +1664,7 @@ class GeminiAdapter extends BaseProviderAdapter {
1611
1664
  : naturalZodSchema(schema);
1612
1665
  jsonSchema = z.toJSONSchema(zodSchema);
1613
1666
  }
1614
- // Remove $schema property (Gemini doesn't need it)
1615
- if (jsonSchema.$schema) {
1616
- delete jsonSchema.$schema;
1617
- }
1618
- return jsonSchema;
1667
+ return jsonSchemaToOpenApi3(jsonSchema);
1619
1668
  }
1620
1669
  //
1621
1670
  // API Execution
@@ -2660,16 +2709,16 @@ function convertContentToOpenRouter(content) {
2660
2709
  }
2661
2710
  // Image content - warn and discard
2662
2711
  if (item.type === LlmMessageType.InputImage) {
2663
- log$2.warn("OpenRouter does not support image uploads; image discarded");
2712
+ log$1.warn("OpenRouter does not support image uploads; image discarded");
2664
2713
  continue;
2665
2714
  }
2666
2715
  // File/Document content - warn and discard
2667
2716
  if (item.type === LlmMessageType.InputFile) {
2668
- log$2.warn({ filename: item.filename }, "OpenRouter does not support file uploads; file discarded");
2717
+ log$1.warn({ filename: item.filename }, "OpenRouter does not support file uploads; file discarded");
2669
2718
  continue;
2670
2719
  }
2671
2720
  // Unknown type - warn and skip
2672
- log$2.warn({ item }, "Unknown content type for OpenRouter; discarded");
2721
+ log$1.warn({ item }, "Unknown content type for OpenRouter; discarded");
2673
2722
  }
2674
2723
  // If no text parts remain, return empty string to avoid empty array
2675
2724
  if (parts.length === 0) {
@@ -3247,7 +3296,7 @@ class XaiAdapter extends OpenAiAdapter {
3247
3296
  const xaiAdapter = new XaiAdapter();
3248
3297
 
3249
3298
  const DEFAULT_TOOL_TYPE = "function";
3250
- const log = log$2.lib({ lib: JAYPIE.LIB.LLM });
3299
+ const log = log$1.lib({ lib: JAYPIE.LIB.LLM });
3251
3300
  function logToolMessage(message, context) {
3252
3301
  log.trace.var({ [context.name]: message });
3253
3302
  }
@@ -4053,6 +4102,7 @@ class RetryExecutor {
4053
4102
  * @throws BadGatewayError if all retries are exhausted or error is not retryable
4054
4103
  */
4055
4104
  async execute(operation, options) {
4105
+ const log = getLogger$5();
4056
4106
  let attempt = 0;
4057
4107
  // Persistent guard against stale socket errors (TypeError: terminated).
4058
4108
  // Installed after the first abort and kept alive through subsequent attempts
@@ -4064,7 +4114,7 @@ class RetryExecutor {
4064
4114
  return;
4065
4115
  staleGuard = (reason) => {
4066
4116
  if (isTransientNetworkError(reason)) {
4067
- log$1.trace("Suppressed stale socket error during retry");
4117
+ log.trace("Suppressed stale socket error during retry");
4068
4118
  }
4069
4119
  };
4070
4120
  process.on("unhandledRejection", staleGuard);
@@ -4081,7 +4131,7 @@ class RetryExecutor {
4081
4131
  try {
4082
4132
  const result = await operation(controller.signal);
4083
4133
  if (attempt > 0) {
4084
- log$1.debug(`API call succeeded after ${attempt} retries`);
4134
+ log.debug(`API call succeeded after ${attempt} retries`);
4085
4135
  }
4086
4136
  return result;
4087
4137
  }
@@ -4094,8 +4144,8 @@ class RetryExecutor {
4094
4144
  installGuard();
4095
4145
  // Check if we've exhausted retries
4096
4146
  if (!this.policy.shouldRetry(attempt)) {
4097
- log$1.error(`API call failed after ${this.policy.maxRetries} retries`);
4098
- log$1.var({ error });
4147
+ log.error(`API call failed after ${this.policy.maxRetries} retries`);
4148
+ log.var({ error });
4099
4149
  await this.hookRunner.runOnUnrecoverableError(options.hooks, {
4100
4150
  input: options.context.input,
4101
4151
  options: options.context.options,
@@ -4107,8 +4157,8 @@ class RetryExecutor {
4107
4157
  }
4108
4158
  // Check if error is not retryable
4109
4159
  if (!this.errorClassifier.isRetryable(error)) {
4110
- log$1.error("API call failed with non-retryable error");
4111
- log$1.var({ error });
4160
+ log.error("API call failed with non-retryable error");
4161
+ log.var({ error });
4112
4162
  await this.hookRunner.runOnUnrecoverableError(options.hooks, {
4113
4163
  input: options.context.input,
4114
4164
  options: options.context.options,
@@ -4120,11 +4170,11 @@ class RetryExecutor {
4120
4170
  }
4121
4171
  // Warn if this is an unknown error type
4122
4172
  if (!this.errorClassifier.isKnownError(error)) {
4123
- log$1.warn("API returned unknown error type, will retry");
4124
- log$1.var({ error });
4173
+ log.warn("API returned unknown error type, will retry");
4174
+ log.var({ error });
4125
4175
  }
4126
4176
  const delay = this.policy.getDelayForAttempt(attempt);
4127
- log$1.warn(`API call failed. Retrying in ${delay}ms...`);
4177
+ log.warn(`API call failed. Retrying in ${delay}ms...`);
4128
4178
  await this.hookRunner.runOnRetryableError(options.hooks, {
4129
4179
  input: options.context.input,
4130
4180
  options: options.context.options,
@@ -4190,10 +4240,11 @@ class OperateLoop {
4190
4240
  * Execute the operate loop for multi-turn conversations with tool calling.
4191
4241
  */
4192
4242
  async execute(input, options = {}) {
4243
+ const log = getLogger$5();
4193
4244
  // Log what was passed to operate
4194
- log$1.trace("[operate] Starting operate loop");
4195
- log$1.var({ "operate.input": input });
4196
- log$1.var({ "operate.options": options });
4245
+ log.trace("[operate] Starting operate loop");
4246
+ log.var({ "operate.input": input });
4247
+ log.var({ "operate.options": options });
4197
4248
  // Initialize state
4198
4249
  const state = await this.initializeState(input, options);
4199
4250
  const context = this.createContext(options);
@@ -4302,6 +4353,7 @@ class OperateLoop {
4302
4353
  };
4303
4354
  }
4304
4355
  async executeOneTurn(request, state, context, options) {
4356
+ const log = getLogger$5();
4305
4357
  // Create error classifier from adapter
4306
4358
  const errorClassifier = createErrorClassifier(this.adapter);
4307
4359
  // Create retry executor for this turn
@@ -4313,8 +4365,8 @@ class OperateLoop {
4313
4365
  // Build provider-specific request
4314
4366
  const providerRequest = this.adapter.buildRequest(request);
4315
4367
  // Log what was passed to the model
4316
- log$1.trace("[operate] Calling model");
4317
- log$1.var({ "operate.request": providerRequest });
4368
+ log.trace("[operate] Calling model");
4369
+ log.var({ "operate.request": providerRequest });
4318
4370
  // Execute beforeEachModelRequest hook
4319
4371
  await this.hookRunnerInstance.runBeforeModelRequest(context.hooks, {
4320
4372
  input: state.currentInput,
@@ -4331,8 +4383,8 @@ class OperateLoop {
4331
4383
  hooks: context.hooks,
4332
4384
  });
4333
4385
  // Log what was returned from the model
4334
- log$1.trace("[operate] Model response received");
4335
- log$1.var({ "operate.response": response });
4386
+ log.trace("[operate] Model response received");
4387
+ log.var({ "operate.response": response });
4336
4388
  // Parse response
4337
4389
  const parsed = this.adapter.parseResponse(response, options);
4338
4390
  // Track usage
@@ -4380,7 +4432,7 @@ class OperateLoop {
4380
4432
  toolName: toolCall.name,
4381
4433
  });
4382
4434
  // Call the tool
4383
- log$1.trace(`[operate] Calling tool - ${toolCall.name}`);
4435
+ log.trace(`[operate] Calling tool - ${toolCall.name}`);
4384
4436
  const result = await state.toolkit.call({
4385
4437
  arguments: toolCall.arguments,
4386
4438
  name: toolCall.name,
@@ -4438,13 +4490,13 @@ class OperateLoop {
4438
4490
  };
4439
4491
  const toolResultFormatted = this.adapter.formatToolResult(toolCall, errorResult);
4440
4492
  state.responseBuilder.appendToHistory(toolResultFormatted);
4441
- log$1.error(`Error executing function call ${toolCall.name}`);
4442
- log$1.var({ error });
4493
+ log.error(`Error executing function call ${toolCall.name}`);
4494
+ log.var({ error });
4443
4495
  // Track consecutive errors and stop if threshold reached
4444
4496
  state.consecutiveToolErrors++;
4445
4497
  if (state.consecutiveToolErrors >= MAX_CONSECUTIVE_TOOL_ERRORS) {
4446
4498
  const detail = `Stopped after ${MAX_CONSECUTIVE_TOOL_ERRORS} consecutive tool errors`;
4447
- log$1.warn(detail);
4499
+ log.warn(detail);
4448
4500
  state.responseBuilder.setError({
4449
4501
  detail,
4450
4502
  status: 502,
@@ -4459,7 +4511,7 @@ class OperateLoop {
4459
4511
  if (state.currentTurn >= state.maxTurns) {
4460
4512
  const error = new TooManyRequestsError();
4461
4513
  const detail = `Model requested function call but exceeded ${state.maxTurns} turns`;
4462
- log$1.warn(detail);
4514
+ log.warn(detail);
4463
4515
  state.responseBuilder.setError({
4464
4516
  detail,
4465
4517
  status: error.status,
@@ -4613,6 +4665,7 @@ class StreamLoop {
4613
4665
  * Yields stream chunks as they become available.
4614
4666
  */
4615
4667
  async *execute(input, options = {}) {
4668
+ const log = getLogger$5();
4616
4669
  // Verify adapter supports streaming
4617
4670
  if (!this.adapter.executeStreamRequest) {
4618
4671
  throw new BadGatewayError(`Provider ${this.adapter.name} does not support streaming`);
@@ -4637,7 +4690,7 @@ class StreamLoop {
4637
4690
  if (state.currentTurn >= state.maxTurns) {
4638
4691
  const error = new TooManyRequestsError();
4639
4692
  const detail = `Model requested function call but exceeded ${state.maxTurns} turns`;
4640
- log$1.warn(detail);
4693
+ log.warn(detail);
4641
4694
  yield {
4642
4695
  type: LlmStreamChunkType.Error,
4643
4696
  error: {
@@ -4730,6 +4783,7 @@ class StreamLoop {
4730
4783
  };
4731
4784
  }
4732
4785
  async *executeOneStreamingTurn(request, state, context, options) {
4786
+ const log = getLogger$5();
4733
4787
  // Build provider-specific request
4734
4788
  const providerRequest = this.adapter.buildRequest(request);
4735
4789
  // Execute beforeEachModelRequest hook
@@ -4751,7 +4805,7 @@ class StreamLoop {
4751
4805
  return;
4752
4806
  staleGuard = (reason) => {
4753
4807
  if (isTransientNetworkError(reason)) {
4754
- log$1.trace("Suppressed stale socket error during retry");
4808
+ log.trace("Suppressed stale socket error during retry");
4755
4809
  }
4756
4810
  };
4757
4811
  process.on("unhandledRejection", staleGuard);
@@ -4797,7 +4851,7 @@ class StreamLoop {
4797
4851
  }
4798
4852
  // Stream completed successfully
4799
4853
  if (attempt > 0) {
4800
- log$1.debug(`Stream request succeeded after ${attempt} retries`);
4854
+ log.debug(`Stream request succeeded after ${attempt} retries`);
4801
4855
  }
4802
4856
  break;
4803
4857
  }
@@ -4809,8 +4863,8 @@ class StreamLoop {
4809
4863
  // If chunks were already yielded, we can't transparently retry
4810
4864
  if (chunksYielded) {
4811
4865
  const errorMessage = error instanceof Error ? error.message : String(error);
4812
- log$1.error("Stream failed after partial data was delivered");
4813
- log$1.var({ error });
4866
+ log.error("Stream failed after partial data was delivered");
4867
+ log.var({ error });
4814
4868
  yield {
4815
4869
  type: LlmStreamChunkType.Error,
4816
4870
  error: {
@@ -4824,14 +4878,14 @@ class StreamLoop {
4824
4878
  // Check if we've exhausted retries or error is not retryable
4825
4879
  if (!this.retryPolicy.shouldRetry(attempt) ||
4826
4880
  !this.adapter.isRetryableError(error)) {
4827
- log$1.error(`Stream request failed after ${this.retryPolicy.maxRetries} retries`);
4828
- log$1.var({ error });
4881
+ log.error(`Stream request failed after ${this.retryPolicy.maxRetries} retries`);
4882
+ log.var({ error });
4829
4883
  const errorMessage = error instanceof Error ? error.message : String(error);
4830
4884
  throw new BadGatewayError(errorMessage);
4831
4885
  }
4832
4886
  const delay = this.retryPolicy.getDelayForAttempt(attempt);
4833
- log$1.warn(`Stream request failed. Retrying in ${delay}ms...`);
4834
- log$1.var({ error });
4887
+ log.warn(`Stream request failed. Retrying in ${delay}ms...`);
4888
+ log.var({ error });
4835
4889
  await sleep(delay);
4836
4890
  attempt++;
4837
4891
  }
@@ -4875,6 +4929,7 @@ class StreamLoop {
4875
4929
  return { shouldContinue: false };
4876
4930
  }
4877
4931
  async *processToolCalls(toolCalls, state, context, _options) {
4932
+ const log = getLogger$5();
4878
4933
  for (const toolCall of toolCalls) {
4879
4934
  try {
4880
4935
  // Execute beforeEachTool hook
@@ -4883,7 +4938,7 @@ class StreamLoop {
4883
4938
  toolName: toolCall.name,
4884
4939
  });
4885
4940
  // Call the tool
4886
- log$1.trace(`[stream] Calling tool - ${toolCall.name}`);
4941
+ log.trace(`[stream] Calling tool - ${toolCall.name}`);
4887
4942
  const result = await state.toolkit.call({
4888
4943
  arguments: toolCall.arguments,
4889
4944
  name: toolCall.name,
@@ -4946,13 +5001,13 @@ class StreamLoop {
4946
5001
  call_id: toolCall.callId,
4947
5002
  name: toolCall.name,
4948
5003
  });
4949
- log$1.error(`Error executing function call ${toolCall.name}`);
4950
- log$1.var({ error });
5004
+ log.error(`Error executing function call ${toolCall.name}`);
5005
+ log.var({ error });
4951
5006
  // Track consecutive errors and stop if threshold reached
4952
5007
  state.consecutiveToolErrors++;
4953
5008
  if (state.consecutiveToolErrors >= MAX_CONSECUTIVE_TOOL_ERRORS) {
4954
5009
  const stopDetail = `Stopped after ${MAX_CONSECUTIVE_TOOL_ERRORS} consecutive tool errors`;
4955
- log$1.warn(stopDetail);
5010
+ log.warn(stopDetail);
4956
5011
  yield {
4957
5012
  type: LlmStreamChunkType.Error,
4958
5013
  error: {
@@ -5033,7 +5088,7 @@ async function loadSdk$2() {
5033
5088
  }
5034
5089
  }
5035
5090
  // Logger
5036
- const getLogger$4 = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
5091
+ const getLogger$4 = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
5037
5092
  // Client initialization
5038
5093
  async function initializeClient$4({ apiKey, } = {}) {
5039
5094
  const logger = getLogger$4();
@@ -5072,7 +5127,7 @@ function prepareMessages$3(message, { data, placeholders } = {}) {
5072
5127
  }
5073
5128
  // Basic text completion
5074
5129
  async function createTextCompletion$1(client, messages, model, systemMessage) {
5075
- log$2.trace("Using text output (unstructured)");
5130
+ log$1.trace("Using text output (unstructured)");
5076
5131
  const params = {
5077
5132
  model,
5078
5133
  messages,
@@ -5081,17 +5136,17 @@ async function createTextCompletion$1(client, messages, model, systemMessage) {
5081
5136
  // Add system instruction if provided
5082
5137
  if (systemMessage) {
5083
5138
  params.system = systemMessage;
5084
- log$2.trace(`System message: ${systemMessage.length} characters`);
5139
+ log$1.trace(`System message: ${systemMessage.length} characters`);
5085
5140
  }
5086
5141
  const response = await client.messages.create(params);
5087
5142
  const firstContent = response.content[0];
5088
5143
  const text = firstContent && "text" in firstContent ? firstContent.text : "";
5089
- log$2.trace(`Assistant reply: ${text.length} characters`);
5144
+ log$1.trace(`Assistant reply: ${text.length} characters`);
5090
5145
  return text;
5091
5146
  }
5092
5147
  // Structured output completion
5093
5148
  async function createStructuredCompletion$1(client, messages, model, responseSchema, systemMessage) {
5094
- log$2.trace("Using structured output");
5149
+ log$1.trace("Using structured output");
5095
5150
  // Get the JSON schema for the response
5096
5151
  const schema = responseSchema instanceof z.ZodType
5097
5152
  ? responseSchema
@@ -5124,7 +5179,7 @@ async function createStructuredCompletion$1(client, messages, model, responseSch
5124
5179
  if (!schema.parse(result)) {
5125
5180
  throw new Error(`JSON response from Anthropic does not match schema: ${responseText}`);
5126
5181
  }
5127
- log$2.trace("Received structured response", { result });
5182
+ log$1.trace("Received structured response", { result });
5128
5183
  return result;
5129
5184
  }
5130
5185
  catch {
@@ -5135,7 +5190,7 @@ async function createStructuredCompletion$1(client, messages, model, responseSch
5135
5190
  throw new Error("Failed to parse structured response from Anthropic");
5136
5191
  }
5137
5192
  catch (error) {
5138
- log$2.error("Error creating structured completion", { error });
5193
+ log$1.error("Error creating structured completion", { error });
5139
5194
  throw error;
5140
5195
  }
5141
5196
  }
@@ -5249,7 +5304,7 @@ async function loadSdk$1() {
5249
5304
  }
5250
5305
  }
5251
5306
  // Logger
5252
- const getLogger$3 = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
5307
+ const getLogger$3 = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
5253
5308
  // Client initialization
5254
5309
  async function initializeClient$3({ apiKey, } = {}) {
5255
5310
  const logger = getLogger$3();
@@ -5400,7 +5455,7 @@ class GeminiProvider {
5400
5455
  }
5401
5456
 
5402
5457
  // Logger
5403
- const getLogger$2 = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
5458
+ const getLogger$2 = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
5404
5459
  // Client initialization
5405
5460
  async function initializeClient$2({ apiKey, } = {}) {
5406
5461
  const logger = getLogger$2();
@@ -5584,7 +5639,7 @@ async function loadSdk() {
5584
5639
  }
5585
5640
  }
5586
5641
  // Logger
5587
- const getLogger$1 = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
5642
+ const getLogger$1 = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
5588
5643
  // Client initialization
5589
5644
  async function initializeClient$1({ apiKey, } = {}) {
5590
5645
  const logger = getLogger$1();
@@ -5733,7 +5788,7 @@ class OpenRouterProvider {
5733
5788
  }
5734
5789
 
5735
5790
  // Logger
5736
- const getLogger = () => log$2.lib({ lib: JAYPIE.LIB.LLM });
5791
+ const getLogger = () => log$1.lib({ lib: JAYPIE.LIB.LLM });
5737
5792
  // Client initialization
5738
5793
  async function initializeClient({ apiKey, } = {}) {
5739
5794
  const logger = getLogger();
@@ -5840,7 +5895,7 @@ class Llm {
5840
5895
  let finalModel = model;
5841
5896
  // Legacy: accept "gemini" but warn
5842
5897
  if (providerName === "gemini") {
5843
- log$3.warn(`Provider "gemini" is deprecated, use "${PROVIDER.GEMINI.NAME}" instead`);
5898
+ log$2.warn(`Provider "gemini" is deprecated, use "${PROVIDER.GEMINI.NAME}" instead`);
5844
5899
  }
5845
5900
  if (model) {
5846
5901
  const modelDetermined = determineModelProvider(model);
@@ -5952,7 +6007,7 @@ class Llm {
5952
6007
  }
5953
6008
  catch (error) {
5954
6009
  lastError = error;
5955
- log$3.warn(`Provider ${this._provider} failed`, {
6010
+ log$2.warn(`Provider ${this._provider} failed`, {
5956
6011
  error: lastError.message,
5957
6012
  fallbacksRemaining: fallbackChain.length,
5958
6013
  });
@@ -5972,7 +6027,7 @@ class Llm {
5972
6027
  }
5973
6028
  catch (error) {
5974
6029
  lastError = error;
5975
- log$3.warn(`Fallback provider ${fallbackConfig.provider} failed`, {
6030
+ log$2.warn(`Fallback provider ${fallbackConfig.provider} failed`, {
5976
6031
  error: lastError.message,
5977
6032
  fallbacksRemaining: fallbackChain.length - attempts + 1,
5978
6033
  });
@@ -6141,16 +6196,17 @@ const roll = {
6141
6196
  },
6142
6197
  type: "function",
6143
6198
  call: ({ number = 1, sides = 6 } = {}) => {
6199
+ const log = getLogger$5();
6144
6200
  const rng = random$1();
6145
6201
  const rolls = [];
6146
6202
  let total = 0;
6147
6203
  const parsedNumber = tryParseNumber(number, {
6148
6204
  defaultValue: 1,
6149
- warnFunction: log$1.warn,
6205
+ warnFunction: log.warn,
6150
6206
  });
6151
6207
  const parsedSides = tryParseNumber(sides, {
6152
6208
  defaultValue: 6,
6153
- warnFunction: log$1.warn,
6209
+ warnFunction: log.warn,
6154
6210
  });
6155
6211
  for (let i = 0; i < parsedNumber; i++) {
6156
6212
  const rollValue = rng({ min: 1, max: parsedSides, integer: true });