@byfriends/kosong 0.1.0 → 0.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.
Files changed (29) hide show
  1. package/dist/{anthropic-Dm_GqFgS.d.mts → anthropic-0CVG5rBE.d.mts} +1 -2
  2. package/dist/{provider-DiJKWMsQ.d.mts → errors-wlT14tC4.d.mts} +227 -2
  3. package/dist/{google-genai-hX0X6CF3.d.mts → google-genai-xKK8lI_R.d.mts} +1 -2
  4. package/dist/index.d.mts +66 -12
  5. package/dist/index.mjs +945 -21
  6. package/dist/{openai-common-08qin3UI.mjs → openai-common-Dl42y_vn.mjs} +27 -2
  7. package/dist/{openai-common-B6cK2ig3.d.mts → openai-common-DwkxUSyI.d.mts} +7 -3
  8. package/dist/{openai-responses-BxOwxtd3.d.mts → openai-responses-DZ9mQ5RA.d.mts} +2 -2
  9. package/dist/providers/anthropic.d.mts +1 -1
  10. package/dist/providers/anthropic.mjs +56 -68
  11. package/dist/providers/google-genai.d.mts +1 -1
  12. package/dist/providers/google-genai.mjs +1 -2
  13. package/dist/providers/openai-common.d.mts +1 -1
  14. package/dist/providers/openai-common.mjs +1 -1
  15. package/dist/providers/openai-responses.d.mts +1 -1
  16. package/dist/providers/openai-responses.mjs +21 -4
  17. package/dist/request-auth-BMXt8jRu.mjs +341 -0
  18. package/package.json +1 -11
  19. package/dist/capability-registry-CMBuEYcf.mjs +0 -161
  20. package/dist/chat-completions-stream-BuMu_xr9.mjs +0 -62
  21. package/dist/errors-DweKbIOf.d.mts +0 -42
  22. package/dist/openai-compat-CMrIk-ib.d.mts +0 -132
  23. package/dist/openai-compat-CWbwO4b7.mjs +0 -801
  24. package/dist/openai-legacy-B6CVfLlr.d.mts +0 -71
  25. package/dist/providers/openai-compat.d.mts +0 -2
  26. package/dist/providers/openai-compat.mjs +0 -2
  27. package/dist/providers/openai-legacy.d.mts +0 -2
  28. package/dist/providers/openai-legacy.mjs +0 -248
  29. package/dist/request-auth-DCWSyCKI.mjs +0 -63
@@ -1,71 +0,0 @@
1
- import { S as StreamedMessagePart, a as StreamedMessage, b as Message, c as TokenUsage, i as ProviderRequestAuth, m as ModelCapability, n as FinishReason, o as ThinkingEffort, p as Tool, r as GenerateOptions, t as ChatProvider } from "./provider-DiJKWMsQ.mjs";
2
- import { i as ToolMessageConversion } from "./openai-common-B6cK2ig3.mjs";
3
- import OpenAI from "openai";
4
-
5
- //#region src/providers/openai-legacy.d.ts
6
- interface OpenAILegacyOptions {
7
- apiKey?: string | undefined;
8
- baseUrl?: string | undefined;
9
- model: string;
10
- stream?: boolean | undefined;
11
- maxTokens?: number | undefined;
12
- reasoningKey?: string | undefined;
13
- httpClient?: unknown;
14
- defaultHeaders?: Record<string, string>;
15
- toolMessageConversion?: ToolMessageConversion | undefined;
16
- clientFactory?: (auth: ProviderRequestAuth) => OpenAI;
17
- }
18
- interface OpenAILegacyGenerationKwargs {
19
- max_tokens?: number | undefined;
20
- temperature?: number | undefined;
21
- top_p?: number | undefined;
22
- n?: number | undefined;
23
- presence_penalty?: number | undefined;
24
- frequency_penalty?: number | undefined;
25
- stop?: string | string[] | undefined;
26
- [key: string]: unknown;
27
- }
28
- declare class OpenAILegacyStreamedMessage implements StreamedMessage {
29
- private _id;
30
- private _usage;
31
- private _finishReason;
32
- private _rawFinishReason;
33
- private readonly _iter;
34
- constructor(response: OpenAI.Chat.ChatCompletion | AsyncIterable<OpenAI.Chat.ChatCompletionChunk>, isStream: boolean, reasoningKey: string | undefined);
35
- get id(): string | null;
36
- get usage(): TokenUsage | null;
37
- get finishReason(): FinishReason | null;
38
- get rawFinishReason(): string | null;
39
- [Symbol.asyncIterator](): AsyncIterator<StreamedMessagePart>;
40
- private _captureFinishReason;
41
- private _convertNonStreamResponse;
42
- private _convertStreamResponse;
43
- }
44
- declare class OpenAILegacyChatProvider implements ChatProvider {
45
- readonly name: string;
46
- private _model;
47
- private _stream;
48
- private _apiKey;
49
- private _baseUrl;
50
- private _defaultHeaders;
51
- private _reasoningKey;
52
- private _reasoningEffort;
53
- private _generationKwargs;
54
- private _toolMessageConversion;
55
- private _client;
56
- private _httpClient;
57
- private _clientFactory;
58
- constructor(options: OpenAILegacyOptions);
59
- get modelName(): string;
60
- get thinkingEffort(): ThinkingEffort | null;
61
- get modelParameters(): Record<string, unknown>;
62
- getCapability(model?: string): ModelCapability;
63
- generate(systemPrompt: string, tools: Tool[], history: Message[], options?: GenerateOptions): Promise<StreamedMessage>;
64
- withThinking(effort: ThinkingEffort): OpenAILegacyChatProvider;
65
- withGenerationKwargs(kwargs: OpenAILegacyGenerationKwargs): OpenAILegacyChatProvider;
66
- private _clone;
67
- private _createClient;
68
- private _buildClient;
69
- }
70
- //#endregion
71
- export { OpenAILegacyStreamedMessage as i, OpenAILegacyGenerationKwargs as n, OpenAILegacyOptions as r, OpenAILegacyChatProvider as t };
@@ -1,2 +0,0 @@
1
- import { a as ThinkingConfig, i as OpenAICompatOptions, n as GenerationKwargs, o as extractUsageFromChunk, r as OpenAICompatChatProvider, t as ExtraBody } from "../openai-compat-CMrIk-ib.mjs";
2
- export { ExtraBody, GenerationKwargs, OpenAICompatChatProvider, OpenAICompatOptions, ThinkingConfig, extractUsageFromChunk };
@@ -1,2 +0,0 @@
1
- import { n as extractUsageFromChunk, t as OpenAICompatChatProvider } from "../openai-compat-CWbwO4b7.mjs";
2
- export { OpenAICompatChatProvider, extractUsageFromChunk };
@@ -1,2 +0,0 @@
1
- import { i as OpenAILegacyStreamedMessage, n as OpenAILegacyGenerationKwargs, r as OpenAILegacyOptions, t as OpenAILegacyChatProvider } from "../openai-legacy-B6CVfLlr.mjs";
2
- export { OpenAILegacyChatProvider, OpenAILegacyGenerationKwargs, OpenAILegacyOptions, OpenAILegacyStreamedMessage };
@@ -1,248 +0,0 @@
1
- import { a as isFunctionToolCall, c as thinkingEffortToReasoningEffort, i as extractUsage, l as toolToOpenAI, n as convertOpenAIError, o as normalizeOpenAIFinishReason, r as convertToolMessageContent, s as reasoningEffortToThinkingEffort, t as convertContentPart } from "../openai-common-08qin3UI.mjs";
2
- import { n as requireProviderApiKey, r as resolveAuthBackedClient, t as mergeRequestHeaders } from "../request-auth-DCWSyCKI.mjs";
3
- import { r as getOpenAILegacyModelCapability } from "../capability-registry-CMBuEYcf.mjs";
4
- import { t as convertChatCompletionStreamToolCall } from "../chat-completions-stream-BuMu_xr9.mjs";
5
- import OpenAI from "openai";
6
- //#region src/providers/openai-legacy.ts
7
- const KNOWN_REASONING_KEYS = [
8
- "reasoning_content",
9
- "reasoning_details",
10
- "reasoning"
11
- ];
12
- const DEFAULT_OUTBOUND_REASONING_KEY = KNOWN_REASONING_KEYS[0];
13
- function extractReasoningContent(source, explicitKey) {
14
- if (typeof source !== "object" || source === null) return void 0;
15
- const record = source;
16
- const keys = explicitKey !== void 0 ? [explicitKey] : KNOWN_REASONING_KEYS;
17
- for (const key of keys) {
18
- const value = record[key];
19
- if (typeof value === "string" && value.length > 0) return value;
20
- }
21
- }
22
- function convertMessage(message, reasoningKey, toolMessageConversion) {
23
- let reasoningContent = "";
24
- const nonThinkParts = [];
25
- for (const part of message.content) if (part.type === "think") reasoningContent += part.think;
26
- else nonThinkParts.push(part);
27
- const result = { role: message.role };
28
- if (message.role === "tool") {
29
- const effectiveConversion = message.content.some((p) => p.type !== "text" && p.type !== "think") ? "extract_text" : toolMessageConversion;
30
- if (effectiveConversion !== null) result.content = convertToolMessageContent(message, effectiveConversion);
31
- else {
32
- const firstPart = nonThinkParts[0];
33
- if (nonThinkParts.length === 1 && firstPart?.type === "text") result.content = firstPart.text;
34
- else if (nonThinkParts.length > 0) result.content = nonThinkParts.map((p) => convertContentPart(p)).filter((p) => p !== null);
35
- }
36
- } else {
37
- const firstPart = nonThinkParts[0];
38
- if (nonThinkParts.length === 1 && firstPart?.type === "text") result.content = firstPart.text;
39
- else if (nonThinkParts.length > 0) result.content = nonThinkParts.map((p) => convertContentPart(p)).filter((p) => p !== null);
40
- }
41
- if (message.name !== void 0) result.name = message.name;
42
- if (message.toolCalls.length > 0) result.tool_calls = message.toolCalls.map((tc) => ({
43
- type: tc.type,
44
- id: tc.id,
45
- function: {
46
- name: tc.name,
47
- arguments: tc.arguments
48
- }
49
- }));
50
- if (message.toolCallId !== void 0) result.tool_call_id = message.toolCallId;
51
- if (reasoningContent) result[reasoningKey ?? DEFAULT_OUTBOUND_REASONING_KEY] = reasoningContent;
52
- return result;
53
- }
54
- var OpenAILegacyStreamedMessage = class {
55
- _id = null;
56
- _usage = null;
57
- _finishReason = null;
58
- _rawFinishReason = null;
59
- _iter;
60
- constructor(response, isStream, reasoningKey) {
61
- if (isStream) this._iter = this._convertStreamResponse(response, reasoningKey);
62
- else this._iter = this._convertNonStreamResponse(response, reasoningKey);
63
- }
64
- get id() {
65
- return this._id;
66
- }
67
- get usage() {
68
- return this._usage;
69
- }
70
- get finishReason() {
71
- return this._finishReason;
72
- }
73
- get rawFinishReason() {
74
- return this._rawFinishReason;
75
- }
76
- async *[Symbol.asyncIterator]() {
77
- yield* this._iter;
78
- }
79
- _captureFinishReason(raw) {
80
- const normalized = normalizeOpenAIFinishReason(raw);
81
- this._finishReason = normalized.finishReason;
82
- this._rawFinishReason = normalized.rawFinishReason;
83
- }
84
- async *_convertNonStreamResponse(response, reasoningKey) {
85
- this._id = response.id;
86
- if (response.usage) this._usage = extractUsage(response.usage) ?? null;
87
- this._captureFinishReason(response.choices[0]?.finish_reason ?? null);
88
- const message = response.choices[0]?.message;
89
- if (!message) return;
90
- const reasoning = extractReasoningContent(message, reasoningKey);
91
- if (reasoning) yield {
92
- type: "think",
93
- think: reasoning
94
- };
95
- if (message.content) yield {
96
- type: "text",
97
- text: message.content
98
- };
99
- if (message.tool_calls) for (const toolCall of message.tool_calls) {
100
- if (!isFunctionToolCall(toolCall)) continue;
101
- yield {
102
- type: "function",
103
- id: toolCall.id || crypto.randomUUID(),
104
- name: toolCall.function.name,
105
- arguments: toolCall.function.arguments
106
- };
107
- }
108
- }
109
- async *_convertStreamResponse(response, reasoningKey) {
110
- const bufferedToolCalls = /* @__PURE__ */ new Map();
111
- try {
112
- for await (const chunk of response) {
113
- if (chunk.id) this._id = chunk.id;
114
- if (chunk.usage) this._usage = extractUsage(chunk.usage) ?? null;
115
- if (!chunk.choices || chunk.choices.length === 0) continue;
116
- const choice = chunk.choices[0];
117
- if (!choice) continue;
118
- if (choice.finish_reason !== null && choice.finish_reason !== void 0) this._captureFinishReason(choice.finish_reason);
119
- const delta = choice.delta;
120
- const reasoning = extractReasoningContent(delta, reasoningKey);
121
- if (reasoning) yield {
122
- type: "think",
123
- think: reasoning
124
- };
125
- if (delta.content) yield {
126
- type: "text",
127
- text: delta.content
128
- };
129
- for (const toolCall of delta.tool_calls ?? []) for (const part of convertChatCompletionStreamToolCall(toolCall, bufferedToolCalls)) yield part;
130
- }
131
- } catch (error) {
132
- throw convertOpenAIError(error);
133
- }
134
- }
135
- };
136
- var OpenAILegacyChatProvider = class {
137
- name = "openai";
138
- _model;
139
- _stream;
140
- _apiKey;
141
- _baseUrl;
142
- _defaultHeaders;
143
- _reasoningKey;
144
- _reasoningEffort;
145
- _generationKwargs;
146
- _toolMessageConversion;
147
- _client;
148
- _httpClient;
149
- _clientFactory;
150
- constructor(options) {
151
- const apiKey = options.apiKey ?? process.env["OPENAI_API_KEY"];
152
- this._apiKey = apiKey === void 0 || apiKey.length === 0 ? void 0 : apiKey;
153
- this._baseUrl = options.baseUrl ?? "https://api.openai.com/v1";
154
- this._defaultHeaders = options.defaultHeaders;
155
- this._model = options.model;
156
- this._stream = options.stream ?? true;
157
- const normalizedReasoningKey = options.reasoningKey?.trim();
158
- this._reasoningKey = normalizedReasoningKey !== void 0 && normalizedReasoningKey.length > 0 ? normalizedReasoningKey : void 0;
159
- this._reasoningEffort = void 0;
160
- this._generationKwargs = {};
161
- if (options.maxTokens !== void 0) this._generationKwargs.max_tokens = options.maxTokens;
162
- this._toolMessageConversion = options.toolMessageConversion ?? null;
163
- this._httpClient = options.httpClient;
164
- this._clientFactory = options.clientFactory;
165
- this._client = this._apiKey === void 0 ? void 0 : this._buildClient(this._apiKey);
166
- }
167
- get modelName() {
168
- return this._model;
169
- }
170
- get thinkingEffort() {
171
- return reasoningEffortToThinkingEffort(this._reasoningEffort);
172
- }
173
- get modelParameters() {
174
- return {
175
- model: this._model,
176
- baseUrl: this._baseUrl,
177
- ...this._generationKwargs
178
- };
179
- }
180
- getCapability(model) {
181
- return getOpenAILegacyModelCapability(model ?? this._model);
182
- }
183
- async generate(systemPrompt, tools, history, options) {
184
- const messages = [];
185
- if (systemPrompt) messages.push({
186
- role: "system",
187
- content: systemPrompt
188
- });
189
- for (const msg of history) messages.push(convertMessage(msg, this._reasoningKey, this._toolMessageConversion));
190
- const kwargs = { ...this._generationKwargs };
191
- let reasoningEffort = this._reasoningEffort;
192
- if (reasoningEffort === void 0 && kwargs["reasoning_effort"] === void 0) {
193
- if (history.some((message) => message.content.some((part) => part.type === "think"))) reasoningEffort = "medium";
194
- }
195
- for (const key of Object.keys(kwargs)) if (kwargs[key] === void 0) delete kwargs[key];
196
- const createParams = {
197
- model: this._model,
198
- messages,
199
- stream: this._stream,
200
- ...kwargs
201
- };
202
- if (tools.length > 0) createParams["tools"] = tools.map((t) => toolToOpenAI(t));
203
- if (this._stream) createParams["stream_options"] = { include_usage: true };
204
- if (reasoningEffort !== void 0) createParams["reasoning_effort"] = reasoningEffort;
205
- try {
206
- return new OpenAILegacyStreamedMessage(await this._createClient(options?.auth).chat.completions.create(createParams, options?.signal ? { signal: options.signal } : void 0), this._stream, this._reasoningKey);
207
- } catch (error) {
208
- throw convertOpenAIError(error);
209
- }
210
- }
211
- withThinking(effort) {
212
- const reasoningEffort = thinkingEffortToReasoningEffort(effort);
213
- const clone = this._clone();
214
- clone._reasoningEffort = reasoningEffort;
215
- return clone;
216
- }
217
- withGenerationKwargs(kwargs) {
218
- const clone = this._clone();
219
- clone._generationKwargs = {
220
- ...clone._generationKwargs,
221
- ...kwargs
222
- };
223
- return clone;
224
- }
225
- _clone() {
226
- const clone = Object.assign(Object.create(Object.getPrototypeOf(this)), this);
227
- clone._generationKwargs = { ...this._generationKwargs };
228
- return clone;
229
- }
230
- _createClient(auth) {
231
- return resolveAuthBackedClient({
232
- cachedClient: this._client,
233
- clientFactory: this._clientFactory
234
- }, auth, (a) => this._buildClient(requireProviderApiKey("OpenAILegacyChatProvider", a, this._apiKey), a));
235
- }
236
- _buildClient(apiKey, auth) {
237
- const clientOpts = {
238
- apiKey,
239
- baseURL: this._baseUrl
240
- };
241
- const defaultHeaders = mergeRequestHeaders(this._defaultHeaders, auth?.headers);
242
- if (defaultHeaders !== void 0) clientOpts["defaultHeaders"] = defaultHeaders;
243
- if (this._httpClient !== void 0) clientOpts["httpClient"] = this._httpClient;
244
- return new OpenAI(clientOpts);
245
- }
246
- };
247
- //#endregion
248
- export { OpenAILegacyChatProvider, OpenAILegacyStreamedMessage };
@@ -1,63 +0,0 @@
1
- import { o as ChatProviderError } from "./errors-WFxxzL1B.mjs";
2
- //#region src/capability.ts
3
- const UNKNOWN_CAPABILITY_MARKER = Symbol.for("byf.kosong.UNKNOWN_CAPABILITY");
4
- /**
5
- * Shared read-only default returned when a provider has not catalogued a
6
- * given model. Frozen so accidental mutation at one call site cannot leak
7
- * into another.
8
- */
9
- const UNKNOWN_CAPABILITY = Object.freeze(Object.defineProperty({
10
- image_in: false,
11
- video_in: false,
12
- audio_in: false,
13
- thinking: false,
14
- tool_use: false,
15
- max_context_tokens: 0
16
- }, UNKNOWN_CAPABILITY_MARKER, { value: true }));
17
- function isUnknownCapability(capability) {
18
- if (capability === UNKNOWN_CAPABILITY) return true;
19
- if (capability[UNKNOWN_CAPABILITY_MARKER] === true) return true;
20
- return !capability.image_in && !capability.video_in && !capability.audio_in && !capability.thinking && !capability.tool_use && capability.max_context_tokens === 0;
21
- }
22
- //#endregion
23
- //#region src/providers/request-auth.ts
24
- function requireProviderApiKey(providerName, auth, defaultApiKey) {
25
- const apiKey = auth?.apiKey ?? defaultApiKey;
26
- if (apiKey === void 0 || apiKey.length === 0) throw new ChatProviderError(`${providerName}: apiKey is required. Provide it via the constructor options, the provider's API-key environment variable, options.auth.apiKey on each request, or an OAuth login.`);
27
- return apiKey;
28
- }
29
- function mergeRequestHeaders(defaultHeaders, requestHeaders) {
30
- const merged = {};
31
- if (defaultHeaders !== void 0) Object.assign(merged, defaultHeaders);
32
- if (requestHeaders !== void 0) Object.assign(merged, requestHeaders);
33
- return Object.keys(merged).length > 0 ? merged : void 0;
34
- }
35
- /**
36
- * Resolve the SDK client to use for a single provider request, applying the
37
- * standard precedence shared by every provider adapter:
38
- *
39
- * 1. If a `clientFactory` was supplied, delegate to it (it receives the
40
- * per-request {@link ProviderRequestAuth}, defaulting to `{}`).
41
- * 2. Otherwise, if no per-request auth is needed AND a constructor-time
42
- * client was cached, reuse the cached instance.
43
- * 3. Otherwise, call `build(auth)` to construct a fresh client for this
44
- * request — typically using `requireProviderApiKey` plus
45
- * `mergeRequestHeaders`.
46
- *
47
- * Note: when per-request `auth` is provided (e.g. an OAuth bearer token
48
- * resolved immediately before each call), step 3 fires and a brand-new SDK
49
- * client is constructed per request. This is intentional — it keeps short-lived
50
- * credentials out of any long-lived shared state and avoids racing concurrent
51
- * requests on a mutable client. The trade-off is that connection-pool / keep-
52
- * alive state inside the SDK client isn't reused across requests on the OAuth
53
- * path. For the current agent-CLI workload (one LLM call per turn step) this
54
- * is fine; if a future host needs high-throughput per-request auth, the
55
- * obvious optimization is a small LRU keyed on `(apiKey, headers digest)`.
56
- */
57
- function resolveAuthBackedClient(state, auth, build) {
58
- if (state.clientFactory !== void 0) return state.clientFactory(auth ?? {});
59
- if (auth === void 0 && state.cachedClient !== void 0) return state.cachedClient;
60
- return build(auth);
61
- }
62
- //#endregion
63
- export { isUnknownCapability as a, UNKNOWN_CAPABILITY as i, requireProviderApiKey as n, resolveAuthBackedClient as r, mergeRequestHeaders as t };