@mupt-ai/dari-gateway 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -4
- package/dist/bun.d.ts +2 -0
- package/dist/bun.js +4 -0
- package/dist/context/eval_catalog.d.ts +3 -0
- package/dist/context/eval_catalog.js +7 -0
- package/dist/context/interaction_fingerprint.d.ts +27 -0
- package/dist/context/interaction_fingerprint.js +519 -0
- package/dist/context/interaction_fingerprint_format.d.ts +42 -0
- package/dist/context/interaction_fingerprint_format.js +113 -0
- package/dist/context/interaction_lease_depth.d.ts +2 -0
- package/dist/context/interaction_lease_depth.js +110 -0
- package/dist/context/lease_history.d.ts +7 -0
- package/dist/context/lease_history.js +158 -0
- package/dist/context/pricing.d.ts +4 -0
- package/dist/context/pricing.js +27 -0
- package/dist/context/provider_prompt_accounting.d.ts +14 -0
- package/dist/context/provider_prompt_accounting.js +187 -0
- package/dist/context/routing_context.d.ts +40 -0
- package/dist/context/routing_context.js +211 -0
- package/dist/http/auth.d.ts +2 -0
- package/dist/http/auth.js +35 -0
- package/dist/http/errors.d.ts +19 -0
- package/dist/http/errors.js +89 -0
- package/dist/http/handler.d.ts +12 -0
- package/dist/http/handler.js +88 -0
- package/dist/http/http2_server.d.ts +6 -0
- package/dist/http/http2_server.js +103 -0
- package/dist/http/serve.d.ts +20 -0
- package/dist/http/serve.js +78 -0
- package/dist/index.d.ts +7 -0
- package/dist/index.js +9 -0
- package/dist/ingress/anthropic_messages.d.ts +3 -0
- package/dist/ingress/anthropic_messages.js +122 -0
- package/dist/ingress/anthropic_models.d.ts +1 -0
- package/dist/ingress/anthropic_models.js +23 -0
- package/dist/ingress/chat_completions.d.ts +2 -0
- package/dist/ingress/chat_completions.js +44 -0
- package/dist/ingress/claude_code/request_context.d.ts +2 -0
- package/dist/ingress/claude_code/request_context.js +31 -0
- package/dist/ingress/codex.d.ts +3 -0
- package/dist/ingress/codex.js +69 -0
- package/dist/ingress/codex_models.d.ts +2 -0
- package/dist/ingress/codex_models.js +89 -0
- package/dist/ingress/json.d.ts +1 -0
- package/dist/ingress/json.js +95 -0
- package/dist/ingress/models.d.ts +1 -0
- package/dist/ingress/models.js +65 -0
- package/dist/ingress/muse_code.d.ts +2 -0
- package/dist/ingress/muse_code.js +8 -0
- package/dist/ingress/muse_models.d.ts +9 -0
- package/dist/ingress/muse_models.js +32 -0
- package/dist/interaction/capabilities.d.ts +3 -0
- package/dist/interaction/capabilities.js +24 -0
- package/dist/interaction/image.d.ts +4 -0
- package/dist/interaction/image.js +13 -0
- package/dist/interaction/portable_reasoning_state.d.ts +4 -0
- package/dist/interaction/portable_reasoning_state.js +18 -0
- package/dist/interaction/provider_continuation_state.d.ts +6 -0
- package/dist/interaction/provider_continuation_state.js +27 -0
- package/dist/interaction/tool_identity.d.ts +10 -0
- package/dist/interaction/tool_identity.js +41 -0
- package/dist/interaction/types.d.ts +204 -0
- package/dist/interaction/types.js +5 -0
- package/dist/models/catalog.d.ts +35 -0
- package/dist/models/catalog.js +232 -0
- package/dist/models/context_limits.d.ts +2 -0
- package/dist/models/context_limits.js +7 -0
- package/dist/models/execution_provider.d.ts +9 -0
- package/dist/models/execution_provider.js +17 -0
- package/dist/models/gateways.d.ts +11 -0
- package/dist/models/gateways.js +45 -0
- package/dist/models/ids.d.ts +1 -0
- package/dist/models/ids.js +15 -0
- package/dist/models/provider_defaults.d.ts +4 -0
- package/dist/models/provider_defaults.js +44 -0
- package/dist/models/runtime_overrides.d.ts +7 -0
- package/dist/models/runtime_overrides.js +226 -0
- package/dist/models/subscriptions.d.ts +8 -0
- package/dist/models/subscriptions.js +37 -0
- package/dist/observability/errors.d.ts +8 -0
- package/dist/observability/errors.js +11 -0
- package/dist/platform/platform.d.ts +156 -0
- package/dist/platform/platform.js +11 -0
- package/dist/platform/routing_contract.d.ts +2 -0
- package/dist/platform/routing_contract.js +5 -0
- package/dist/protocol/input/anthropic_messages.d.ts +2 -0
- package/dist/protocol/input/anthropic_messages.js +494 -0
- package/dist/protocol/input/chat_completions.d.ts +4 -0
- package/dist/protocol/input/chat_completions.js +214 -0
- package/dist/protocol/input/chat_completions_validation.d.ts +2 -0
- package/dist/protocol/input/chat_completions_validation.js +258 -0
- package/dist/protocol/input/openai_responses.d.ts +2 -0
- package/dist/protocol/input/openai_responses.js +666 -0
- package/dist/protocol/input/router_model.d.ts +7 -0
- package/dist/protocol/input/router_model.js +43 -0
- package/dist/protocol/output/anthropic_messages.d.ts +10 -0
- package/dist/protocol/output/anthropic_messages.js +15 -0
- package/dist/protocol/output/anthropic_messages_output.d.ts +10 -0
- package/dist/protocol/output/anthropic_messages_output.js +124 -0
- package/dist/protocol/output/anthropic_messages_stream.d.ts +16 -0
- package/dist/protocol/output/anthropic_messages_stream.js +267 -0
- package/dist/protocol/output/chat_completions.d.ts +29 -0
- package/dist/protocol/output/chat_completions.js +406 -0
- package/dist/protocol/output/chat_reasoning_detail.d.ts +2 -0
- package/dist/protocol/output/chat_reasoning_detail.js +13 -0
- package/dist/protocol/output/delivered_stream_snapshot.d.ts +10 -0
- package/dist/protocol/output/delivered_stream_snapshot.js +31 -0
- package/dist/protocol/output/openai_responses.d.ts +10 -0
- package/dist/protocol/output/openai_responses.js +14 -0
- package/dist/protocol/output/openai_responses_output.d.ts +14 -0
- package/dist/protocol/output/openai_responses_output.js +125 -0
- package/dist/protocol/output/openai_responses_stream.d.ts +18 -0
- package/dist/protocol/output/openai_responses_stream.js +546 -0
- package/dist/protocol/output/sse_stream.d.ts +31 -0
- package/dist/protocol/output/sse_stream.js +67 -0
- package/dist/providers/anthropic_safeguards.d.ts +11 -0
- package/dist/providers/anthropic_safeguards.js +81 -0
- package/dist/providers/aws_assume_role.d.ts +17 -0
- package/dist/providers/aws_assume_role.js +107 -0
- package/dist/providers/cancel_estimate.d.ts +43 -0
- package/dist/providers/cancel_estimate.js +89 -0
- package/dist/providers/execution.d.ts +72 -0
- package/dist/providers/execution.js +491 -0
- package/dist/providers/model_capabilities.d.ts +11 -0
- package/dist/providers/model_capabilities.js +29 -0
- package/dist/providers/pi.d.ts +65 -0
- package/dist/providers/pi.js +325 -0
- package/dist/providers/pi_context.d.ts +7 -0
- package/dist/providers/pi_context.js +405 -0
- package/dist/providers/pi_options.d.ts +11 -0
- package/dist/providers/pi_options.js +410 -0
- package/dist/providers/pi_output.d.ts +2 -0
- package/dist/providers/pi_output.js +453 -0
- package/dist/providers/provider_attempt_runner.d.ts +55 -0
- package/dist/providers/provider_attempt_runner.js +90 -0
- package/dist/providers/provider_call.d.ts +77 -0
- package/dist/providers/provider_call.js +296 -0
- package/dist/providers/provider_reported_cost.d.ts +10 -0
- package/dist/providers/provider_reported_cost.js +123 -0
- package/dist/providers/reasoning.d.ts +12 -0
- package/dist/providers/reasoning.js +30 -0
- package/dist/providers/response_capture.d.ts +23 -0
- package/dist/providers/response_capture.js +47 -0
- package/dist/providers/stream_finalization.d.ts +46 -0
- package/dist/providers/stream_finalization.js +165 -0
- package/dist/providers/subscription_limits.d.ts +33 -0
- package/dist/providers/subscription_limits.js +179 -0
- package/dist/providers/subscription_usage.d.ts +10 -0
- package/dist/providers/subscription_usage.js +79 -0
- package/dist/runtime/claude_code/auxiliary_routing.d.ts +3 -0
- package/dist/runtime/claude_code/auxiliary_routing.js +60 -0
- package/dist/runtime/customer_disconnect.d.ts +20 -0
- package/dist/runtime/customer_disconnect.js +49 -0
- package/dist/runtime/explicit_model.d.ts +7 -0
- package/dist/runtime/explicit_model.js +57 -0
- package/dist/runtime/harness_identity/conversation.d.ts +33 -0
- package/dist/runtime/harness_identity/conversation.js +39 -0
- package/dist/runtime/harness_identity/extract.d.ts +8 -0
- package/dist/runtime/harness_identity/extract.js +214 -0
- package/dist/runtime/harness_identity/index.d.ts +2 -0
- package/dist/runtime/harness_identity/index.js +2 -0
- package/dist/runtime/prepare_routed_completion.d.ts +33 -0
- package/dist/runtime/prepare_routed_completion.js +186 -0
- package/dist/runtime/provider_stream_lifecycle.d.ts +31 -0
- package/dist/runtime/provider_stream_lifecycle.js +88 -0
- package/dist/runtime/provider_stream_outcome.d.ts +23 -0
- package/dist/runtime/provider_stream_outcome.js +55 -0
- package/dist/runtime/request_tags.d.ts +7 -0
- package/dist/runtime/request_tags.js +33 -0
- package/dist/runtime/routed_completion.d.ts +17 -0
- package/dist/runtime/routed_completion.js +80 -0
- package/dist/runtime/routed_protocol.d.ts +30 -0
- package/dist/runtime/routed_protocol.js +1 -0
- package/dist/runtime/routed_runtime.d.ts +40 -0
- package/dist/runtime/routed_runtime.js +535 -0
- package/dist/runtime/routing_lease.d.ts +26 -0
- package/dist/runtime/routing_lease.js +210 -0
- package/dist/runtime/runtime_reporter.d.ts +71 -0
- package/dist/runtime/runtime_reporter.js +35 -0
- package/dist/runtime/strict_provider_access.d.ts +6 -0
- package/dist/runtime/strict_provider_access.js +40 -0
- package/dist/self_host/config.d.ts +46 -0
- package/dist/self_host/config.js +105 -0
- package/dist/self_host/main.d.ts +16 -0
- package/dist/self_host/main.js +95 -0
- package/dist/self_host/platform.d.ts +13 -0
- package/dist/self_host/platform.js +50 -0
- package/dist/self_host/prefix_store.d.ts +46 -0
- package/dist/self_host/prefix_store.js +261 -0
- package/dist/self_host/resolve.d.ts +28 -0
- package/dist/self_host/resolve.js +167 -0
- package/dist/self_host/subscriptions/access.d.ts +10 -0
- package/dist/self_host/subscriptions/access.js +37 -0
- package/dist/self_host/subscriptions/http.d.ts +15 -0
- package/dist/self_host/subscriptions/http.js +187 -0
- package/dist/self_host/subscriptions/index.d.ts +24 -0
- package/dist/self_host/subscriptions/index.js +24 -0
- package/dist/self_host/subscriptions/oauth.d.ts +59 -0
- package/dist/self_host/subscriptions/oauth.js +376 -0
- package/dist/self_host/subscriptions/store.d.ts +78 -0
- package/dist/self_host/subscriptions/store.js +236 -0
- package/dist/strategies/auto_routing_selector.d.ts +12 -0
- package/dist/strategies/auto_routing_selector.js +61 -0
- package/dist/strategies/eval_relevance.d.ts +17 -0
- package/dist/strategies/eval_relevance.js +32 -0
- package/dist/strategies/fallback_decision.d.ts +8 -0
- package/dist/strategies/fallback_decision.js +17 -0
- package/dist/strategies/priority_selector.d.ts +7 -0
- package/dist/strategies/priority_selector.js +37 -0
- package/dist/strategies/route_decision.d.ts +22 -0
- package/dist/strategies/route_decision.js +65 -0
- package/dist/strategies/routing.d.ts +74 -0
- package/dist/strategies/routing.js +280 -0
- package/dist/strategies/selector_projection.d.ts +15 -0
- package/dist/strategies/selector_projection.js +161 -0
- package/dist/telemetry/background.d.ts +7 -0
- package/dist/telemetry/background.js +33 -0
- package/dist/telemetry/benchmark_replay.d.ts +37 -0
- package/dist/telemetry/benchmark_replay.js +108 -0
- package/dist/telemetry/billing_finalization.d.ts +64 -0
- package/dist/telemetry/billing_finalization.js +96 -0
- package/dist/telemetry/ingest_values.d.ts +4 -0
- package/dist/telemetry/ingest_values.js +12 -0
- package/dist/telemetry/model_cost.d.ts +3 -0
- package/dist/telemetry/model_cost.js +15 -0
- package/dist/telemetry/prefix_state.d.ts +47 -0
- package/dist/telemetry/prefix_state.js +116 -0
- package/dist/telemetry/report.d.ts +88 -0
- package/dist/telemetry/report.js +621 -0
- package/dist/telemetry/requests/interaction_observability.d.ts +45 -0
- package/dist/telemetry/requests/interaction_observability.js +180 -0
- package/dist/telemetry/requests/retained_interaction_request.d.ts +8 -0
- package/dist/telemetry/requests/retained_interaction_request.js +10 -0
- package/dist/telemetry/scrub.d.ts +2 -0
- package/dist/telemetry/scrub.js +31 -0
- package/dist/telemetry/skills/claude/catalog.d.ts +6 -0
- package/dist/telemetry/skills/claude/catalog.js +99 -0
- package/dist/telemetry/skills/claude/file_reads.d.ts +4 -0
- package/dist/telemetry/skills/claude/file_reads.js +110 -0
- package/dist/telemetry/skills/claude/observations.d.ts +3 -0
- package/dist/telemetry/skills/claude/observations.js +366 -0
- package/dist/telemetry/skills/codex/catalog.d.ts +11 -0
- package/dist/telemetry/skills/codex/catalog.js +138 -0
- package/dist/telemetry/skills/codex/exec_file_reads.d.ts +9 -0
- package/dist/telemetry/skills/codex/exec_file_reads.js +36 -0
- package/dist/telemetry/skills/codex/explicit.d.ts +3 -0
- package/dist/telemetry/skills/codex/explicit.js +90 -0
- package/dist/telemetry/skills/codex/file_reads.d.ts +4 -0
- package/dist/telemetry/skills/codex/file_reads.js +37 -0
- package/dist/telemetry/skills/codex/identity.d.ts +2 -0
- package/dist/telemetry/skills/codex/identity.js +20 -0
- package/dist/telemetry/skills/observations.d.ts +21 -0
- package/dist/telemetry/skills/observations.js +41 -0
- package/dist/telemetry/skills/paths.d.ts +11 -0
- package/dist/telemetry/skills/paths.js +61 -0
- package/dist/telemetry/skills/pi.d.ts +6 -0
- package/dist/telemetry/skills/pi.js +223 -0
- package/dist/telemetry/skills/shell_file_reads.d.ts +7 -0
- package/dist/telemetry/skills/shell_file_reads.js +226 -0
- package/dist/telemetry/skills/shell_words.d.ts +13 -0
- package/dist/telemetry/skills/shell_words.js +189 -0
- package/dist/telemetry/tools/input.d.ts +2 -0
- package/dist/telemetry/tools/input.js +14 -0
- package/dist/telemetry/tools/observations.d.ts +29 -0
- package/dist/telemetry/tools/observations.js +247 -0
- package/dist/telemetry/usage.d.ts +57 -0
- package/dist/telemetry/usage.js +136 -0
- package/dist/types.d.ts +97 -0
- package/dist/types.js +1 -0
- package/package.json +22 -7
- package/src/bun.ts +2 -2
- package/src/context/eval_catalog.ts +1 -1
- package/src/context/interaction_fingerprint.ts +9 -9
- package/src/context/interaction_fingerprint_format.ts +1 -1
- package/src/context/interaction_lease_depth.ts +1 -1
- package/src/context/pricing.ts +6 -3
- package/src/context/provider_prompt_accounting.ts +5 -5
- package/src/context/routing_context.ts +16 -16
- package/src/http/auth.ts +1 -1
- package/src/http/handler.ts +15 -8
- package/src/http/serve.ts +3 -3
- package/src/index.ts +14 -6
- package/src/ingress/anthropic_messages.ts +12 -12
- package/src/ingress/anthropic_models.ts +1 -1
- package/src/ingress/chat_completions.ts +17 -10
- package/src/ingress/claude_code/request_context.ts +2 -2
- package/src/ingress/codex.ts +14 -10
- package/src/ingress/codex_models.ts +4 -4
- package/src/ingress/json.ts +1 -1
- package/src/ingress/models.ts +22 -10
- package/src/ingress/muse_code.ts +9 -0
- package/src/ingress/muse_models.ts +36 -0
- package/src/interaction/capabilities.ts +1 -1
- package/src/interaction/portable_reasoning_state.ts +1 -1
- package/src/interaction/provider_continuation_state.ts +1 -1
- package/src/interaction/tool_identity.ts +2 -2
- package/src/interaction/types.ts +2 -0
- package/src/models/catalog.ts +310 -0
- package/src/models/context_limits.ts +1 -1
- package/src/models/execution_provider.ts +5 -2
- package/src/models/ids.ts +1 -1
- package/src/models/provider_defaults.ts +4 -1
- package/src/models/runtime_overrides.ts +23 -1
- package/src/models/subscriptions.ts +54 -0
- package/src/observability/errors.ts +2 -2
- package/src/platform/platform.ts +9 -5
- package/src/protocol/input/anthropic_messages.ts +7 -7
- package/src/protocol/input/chat_completions.ts +8 -6
- package/src/protocol/input/chat_completions_validation.ts +6 -5
- package/src/protocol/input/openai_responses.ts +6 -6
- package/src/protocol/output/anthropic_messages.ts +3 -3
- package/src/protocol/output/anthropic_messages_output.ts +6 -4
- package/src/protocol/output/anthropic_messages_stream.ts +7 -7
- package/src/protocol/output/chat_completions.ts +13 -13
- package/src/protocol/output/chat_reasoning_detail.ts +1 -1
- package/src/protocol/output/openai_responses.ts +3 -3
- package/src/protocol/output/openai_responses_output.ts +4 -2
- package/src/protocol/output/openai_responses_stream.ts +6 -6
- package/src/protocol/output/sse_stream.ts +3 -3
- package/src/providers/anthropic_safeguards.ts +2 -2
- package/src/providers/aws_assume_role.ts +2 -2
- package/src/providers/cancel_estimate.ts +1 -1
- package/src/providers/execution.ts +17 -17
- package/src/providers/pi.ts +34 -19
- package/src/providers/pi_context.ts +6 -6
- package/src/providers/pi_options.ts +27 -11
- package/src/providers/pi_output.ts +5 -5
- package/src/providers/provider_attempt_runner.ts +1 -1
- package/src/providers/provider_call.ts +21 -17
- package/src/providers/provider_reported_cost.ts +3 -3
- package/src/providers/reasoning.ts +2 -2
- package/src/providers/stream_finalization.ts +9 -9
- package/src/providers/subscription_limits.ts +24 -7
- package/src/runtime/claude_code/auxiliary_routing.ts +5 -5
- package/src/runtime/customer_disconnect.ts +1 -1
- package/src/runtime/explicit_model.ts +19 -20
- package/src/runtime/harness_identity/conversation.ts +1 -1
- package/src/runtime/harness_identity/extract.ts +3 -3
- package/src/runtime/harness_identity/index.ts +2 -2
- package/src/runtime/prepare_routed_completion.ts +35 -16
- package/src/runtime/provider_stream_lifecycle.ts +1 -1
- package/src/runtime/provider_stream_outcome.ts +2 -2
- package/src/runtime/request_tags.ts +2 -2
- package/src/runtime/routed_completion.ts +11 -11
- package/src/runtime/routed_protocol.ts +2 -2
- package/src/runtime/routed_runtime.ts +20 -19
- package/src/runtime/routing_lease.ts +7 -7
- package/src/runtime/runtime_reporter.ts +3 -3
- package/src/runtime/strict_provider_access.ts +42 -0
- package/src/self_host/main.ts +12 -12
- package/src/self_host/platform.ts +5 -5
- package/src/self_host/prefix_store.ts +2 -2
- package/src/self_host/resolve.ts +17 -31
- package/src/self_host/subscriptions/access.ts +2 -2
- package/src/self_host/subscriptions/http.ts +2 -2
- package/src/self_host/subscriptions/index.ts +4 -4
- package/src/self_host/subscriptions/oauth.ts +139 -8
- package/src/self_host/subscriptions/store.ts +2 -1
- package/src/strategies/auto_routing_selector.ts +2 -2
- package/src/strategies/eval_relevance.ts +3 -3
- package/src/strategies/priority_selector.ts +1 -1
- package/src/strategies/route_decision.ts +7 -7
- package/src/strategies/routing.ts +10 -10
- package/src/strategies/selector_projection.ts +2 -2
- package/src/telemetry/billing_finalization.ts +3 -3
- package/src/telemetry/model_cost.ts +1 -1
- package/src/telemetry/prefix_state.ts +4 -4
- package/src/telemetry/report.ts +21 -21
- package/src/telemetry/requests/interaction_observability.ts +1 -1
- package/src/telemetry/requests/retained_interaction_request.ts +1 -1
- package/src/telemetry/skills/claude/catalog.ts +1 -1
- package/src/telemetry/skills/claude/file_reads.ts +6 -6
- package/src/telemetry/skills/claude/observations.ts +3 -3
- package/src/telemetry/skills/codex/catalog.ts +3 -3
- package/src/telemetry/skills/codex/exec_file_reads.ts +4 -4
- package/src/telemetry/skills/codex/explicit.ts +3 -3
- package/src/telemetry/skills/codex/file_reads.ts +5 -5
- package/src/telemetry/skills/observations.ts +7 -7
- package/src/telemetry/skills/pi.ts +3 -3
- package/src/telemetry/skills/shell_file_reads.ts +2 -2
- package/src/telemetry/skills/shell_words.ts +1 -1
- package/src/telemetry/tools/input.ts +1 -1
- package/src/telemetry/tools/observations.ts +9 -9
- package/src/telemetry/usage.ts +5 -5
- package/src/types.ts +20 -3
|
@@ -8,8 +8,8 @@ import {
|
|
|
8
8
|
type RoutingDecision,
|
|
9
9
|
} from "@mupt-ai/dari-router/policy-engine";
|
|
10
10
|
|
|
11
|
-
import { buildRoutingContext } from "../context/routing_context";
|
|
12
|
-
import type { InteractionRequest } from "../interaction/types";
|
|
11
|
+
import { buildRoutingContext } from "../context/routing_context.js";
|
|
12
|
+
import type { InteractionRequest } from "../interaction/types.js";
|
|
13
13
|
import {
|
|
14
14
|
completeNonStreaming,
|
|
15
15
|
executeNonStreaming,
|
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
prepareStreamingExecution,
|
|
18
18
|
type CompletedNonStreamingExecution,
|
|
19
19
|
type ProviderChoice,
|
|
20
|
-
} from "../providers/execution";
|
|
20
|
+
} from "../providers/execution.js";
|
|
21
21
|
import {
|
|
22
22
|
prepareProviderExecution,
|
|
23
23
|
startProviderCompletion,
|
|
@@ -25,16 +25,16 @@ import {
|
|
|
25
25
|
type ProviderExecution,
|
|
26
26
|
type StartedCompletion,
|
|
27
27
|
type StartedStream,
|
|
28
|
-
} from "../providers/provider_call";
|
|
29
|
-
import type { SelectorBackend } from "../strategies/routing";
|
|
30
|
-
import { routeDecision, type RoutedDecision } from "../strategies/route_decision";
|
|
31
|
-
import { executionProviderForModel } from "../models/execution_provider";
|
|
32
|
-
import { trackBackgroundTelemetry } from "../telemetry/background";
|
|
33
|
-
import { estimateBenchmarkReplay } from "../telemetry/benchmark_replay";
|
|
34
|
-
import { buildCompletedPrefixHit } from "../telemetry/prefix_state";
|
|
35
|
-
import { scrubSecrets } from "../telemetry/scrub";
|
|
36
|
-
import type { ResolvedRouter } from "../types";
|
|
37
|
-
import type { PreparedRoutedCompletion } from "./prepare_routed_completion";
|
|
28
|
+
} from "../providers/provider_call.js";
|
|
29
|
+
import type { SelectorBackend } from "../strategies/routing.js";
|
|
30
|
+
import { routeDecision, type RoutedDecision } from "../strategies/route_decision.js";
|
|
31
|
+
import { executionProviderForModel } from "../models/execution_provider.js";
|
|
32
|
+
import { trackBackgroundTelemetry } from "../telemetry/background.js";
|
|
33
|
+
import { estimateBenchmarkReplay } from "../telemetry/benchmark_replay.js";
|
|
34
|
+
import { buildCompletedPrefixHit } from "../telemetry/prefix_state.js";
|
|
35
|
+
import { scrubSecrets } from "../telemetry/scrub.js";
|
|
36
|
+
import type { ResolvedRouter } from "../types.js";
|
|
37
|
+
import type { PreparedRoutedCompletion } from "./prepare_routed_completion.js";
|
|
38
38
|
import { auxiliaryDecision } from "./claude_code/auxiliary_routing.js";
|
|
39
39
|
import { explicitModelDecision, strictModelDecision } from "./explicit_model.js";
|
|
40
40
|
import {
|
|
@@ -47,12 +47,12 @@ import {
|
|
|
47
47
|
prefetchNextLease,
|
|
48
48
|
selectorNegotiatesLeases,
|
|
49
49
|
} from "./routing_lease.js";
|
|
50
|
-
import type { RoutedProtocol } from "./routed_protocol";
|
|
50
|
+
import type { RoutedProtocol } from "./routed_protocol.js";
|
|
51
51
|
import {
|
|
52
52
|
createExperimentRoutedRuntimeReporter,
|
|
53
53
|
type RoutedRuntimeReporter,
|
|
54
|
-
} from "./runtime_reporter";
|
|
55
|
-
import { HttpError } from "../http/errors";
|
|
54
|
+
} from "./runtime_reporter.js";
|
|
55
|
+
import { HttpError } from "../http/errors.js";
|
|
56
56
|
|
|
57
57
|
type SpeculativeExecution = {
|
|
58
58
|
decision: RoutingDecision;
|
|
@@ -113,12 +113,12 @@ export type {
|
|
|
113
113
|
SelectorAdapterArgs,
|
|
114
114
|
SelectorBackend,
|
|
115
115
|
SelectorRun,
|
|
116
|
-
} from "../strategies/routing";
|
|
116
|
+
} from "../strategies/routing.js";
|
|
117
117
|
export type {
|
|
118
118
|
ExperimentRoutedRuntimeReporter,
|
|
119
119
|
RoutedRuntimeReporter,
|
|
120
|
-
} from "./runtime_reporter";
|
|
121
|
-
export { createExperimentRoutedRuntimeReporter } from "./runtime_reporter";
|
|
120
|
+
} from "./runtime_reporter.js";
|
|
121
|
+
export { createExperimentRoutedRuntimeReporter } from "./runtime_reporter.js";
|
|
122
122
|
|
|
123
123
|
export async function runPreparedRoutedCompletion(args: {
|
|
124
124
|
prepared: PreparedRoutedCompletion;
|
|
@@ -709,6 +709,7 @@ const inProcessProtocol: RoutedProtocol = {
|
|
|
709
709
|
selected_model: args.routing.selectedModel,
|
|
710
710
|
reasoning_effort: args.routing.reasoningEffort,
|
|
711
711
|
reason: args.routing.reason,
|
|
712
|
+
request_id: args.id,
|
|
712
713
|
...(args.conversationId ? { conversation_id: args.conversationId } : {}),
|
|
713
714
|
},
|
|
714
715
|
}),
|
|
@@ -6,16 +6,16 @@ import {
|
|
|
6
6
|
type RoutingDecision,
|
|
7
7
|
} from "@mupt-ai/dari-router/policy-engine";
|
|
8
8
|
|
|
9
|
-
import { deriveFallbackDecision } from "../strategies/fallback_decision";
|
|
10
|
-
import { executionProviderForModel } from "../models/execution_provider";
|
|
11
|
-
import type { SelectorBackend } from "../strategies/routing";
|
|
9
|
+
import { deriveFallbackDecision } from "../strategies/fallback_decision.js";
|
|
10
|
+
import { executionProviderForModel } from "../models/execution_provider.js";
|
|
11
|
+
import type { SelectorBackend } from "../strategies/routing.js";
|
|
12
12
|
import {
|
|
13
13
|
routeDecision,
|
|
14
14
|
type RoutedDecision,
|
|
15
|
-
} from "../strategies/route_decision";
|
|
16
|
-
import { reportPendingLease } from "../telemetry/prefix_state";
|
|
17
|
-
import { scrubSecrets } from "../telemetry/scrub";
|
|
18
|
-
import type { PreparedRoutedCompletion } from "./prepare_routed_completion";
|
|
15
|
+
} from "../strategies/route_decision.js";
|
|
16
|
+
import { reportPendingLease } from "../telemetry/prefix_state.js";
|
|
17
|
+
import { scrubSecrets } from "../telemetry/scrub.js";
|
|
18
|
+
import type { PreparedRoutedCompletion } from "./prepare_routed_completion.js";
|
|
19
19
|
|
|
20
20
|
export type RoutingLeaseDecision = {
|
|
21
21
|
decision: RoutingDecision;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { RoutingDecision } from "@mupt-ai/dari-router/policy-engine";
|
|
2
|
-
import type { InteractionOutput } from "../interaction/types";
|
|
3
|
-
import type { SelectorRun } from "../strategies/routing";
|
|
4
|
-
import type { ProviderKeySource } from "../types";
|
|
2
|
+
import type { InteractionOutput } from "../interaction/types.js";
|
|
3
|
+
import type { SelectorRun } from "../strategies/routing.js";
|
|
4
|
+
import type { ProviderKeySource } from "../types.js";
|
|
5
5
|
|
|
6
6
|
export type ReportedProviderExecution = {
|
|
7
7
|
provider: string;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { getBuiltinModels, getBuiltinProviders } from "@mupt-ai/pi-ai/providers/all";
|
|
2
|
+
import { HttpError } from "../http/errors.js";
|
|
3
|
+
import type { InteractionRequest } from "../interaction/types.js";
|
|
4
|
+
import { explicitModelId } from "../protocol/input/router_model.js";
|
|
5
|
+
import type { ResolvedRouter } from "../types.js";
|
|
6
|
+
import { modelNotEnabled, strictModelRequired } from "./explicit_model.js";
|
|
7
|
+
|
|
8
|
+
// Resolve only the requested catalog model, never turn a provider grant into
|
|
9
|
+
// selector candidates. Unknown IDs fail closed; a grant-only router has no
|
|
10
|
+
// candidates to route among, so it refuses them here with the strict errors.
|
|
11
|
+
export function strictProviderAccess(
|
|
12
|
+
credentials: ResolvedRouter,
|
|
13
|
+
interaction: InteractionRequest,
|
|
14
|
+
): { credentials: ResolvedRouter; interaction: InteractionRequest } {
|
|
15
|
+
const providers = credentials.strict_providers;
|
|
16
|
+
if (credentials.strict !== true || !providers?.length) return { credentials, interaction };
|
|
17
|
+
const requested = explicitModelId(interaction.model);
|
|
18
|
+
const grantOnly = credentials.enabled_models.length === 0;
|
|
19
|
+
if (requested === null) {
|
|
20
|
+
if (grantOnly) throw strictModelRequired();
|
|
21
|
+
return { credentials, interaction };
|
|
22
|
+
}
|
|
23
|
+
const matches = new Set<string>();
|
|
24
|
+
for (const provider of providers) {
|
|
25
|
+
if (!(getBuiltinProviders() as readonly string[]).includes(provider)) {
|
|
26
|
+
throw new HttpError(400, `Unknown strict provider '${provider}'.`, "unknown_provider");
|
|
27
|
+
}
|
|
28
|
+
for (const model of getBuiltinModels(provider as never)) {
|
|
29
|
+
const id = `${provider}/${model.id}`;
|
|
30
|
+
if (requested === id) matches.add(id);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
const model = [...matches][0];
|
|
34
|
+
if (model === undefined) {
|
|
35
|
+
if (grantOnly) throw modelNotEnabled(requested);
|
|
36
|
+
return { credentials, interaction };
|
|
37
|
+
}
|
|
38
|
+
return {
|
|
39
|
+
credentials: { ...credentials, enabled_models: [...new Set([...credentials.enabled_models, model])] },
|
|
40
|
+
interaction: { ...interaction, model: `dari/model/${model}` },
|
|
41
|
+
};
|
|
42
|
+
}
|
package/src/self_host/main.ts
CHANGED
|
@@ -3,18 +3,18 @@ import { chmodSync, existsSync } from "node:fs";
|
|
|
3
3
|
import { Database } from "bun:sqlite";
|
|
4
4
|
import { builtinModels } from "@mupt-ai/pi-ai/providers/all";
|
|
5
5
|
|
|
6
|
-
import { bearerToken } from "../http/auth";
|
|
7
|
-
import { errorResponse, HttpError } from "../http/errors";
|
|
8
|
-
import { createRequestHandler } from "../http/handler";
|
|
9
|
-
import { installShutdownHandlers, startServer } from "../http/serve";
|
|
10
|
-
import { createAutoRoutingSelectorBackend } from "../strategies/auto_routing_selector";
|
|
11
|
-
import { createPrioritySelectorBackend } from "../strategies/priority_selector";
|
|
12
|
-
import type { SelectorBackend } from "../strategies/routing";
|
|
13
|
-
import { loadGatewayConfig } from "./config";
|
|
14
|
-
import { createSelfHostedPlatform } from "./platform";
|
|
15
|
-
import { gatewayKeyIndex } from "./resolve";
|
|
16
|
-
import { PrefixStore } from "./prefix_store";
|
|
17
|
-
import { handleSubscriptionRequest, SubscriptionStore } from "./subscriptions";
|
|
6
|
+
import { bearerToken } from "../http/auth.js";
|
|
7
|
+
import { errorResponse, HttpError } from "../http/errors.js";
|
|
8
|
+
import { createRequestHandler } from "../http/handler.js";
|
|
9
|
+
import { installShutdownHandlers, startServer } from "../http/serve.js";
|
|
10
|
+
import { createAutoRoutingSelectorBackend } from "../strategies/auto_routing_selector.js";
|
|
11
|
+
import { createPrioritySelectorBackend } from "../strategies/priority_selector.js";
|
|
12
|
+
import type { SelectorBackend } from "../strategies/routing.js";
|
|
13
|
+
import { loadGatewayConfig } from "./config.js";
|
|
14
|
+
import { createSelfHostedPlatform } from "./platform.js";
|
|
15
|
+
import { gatewayKeyIndex } from "./resolve.js";
|
|
16
|
+
import { PrefixStore } from "./prefix_store.js";
|
|
17
|
+
import { handleSubscriptionRequest, SubscriptionStore } from "./subscriptions/index.js";
|
|
18
18
|
|
|
19
19
|
const SUBSCRIPTION_ROUTES = "/v1/organizations/current/credentials";
|
|
20
20
|
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { errorCode } from "../http/errors";
|
|
2
|
-
import type { GatewayPlatform } from "../platform/platform";
|
|
3
|
-
import type { PrefixStore } from "./prefix_store";
|
|
4
|
-
import { resolveSelfHostedRouter, type SelfHostedResolverDeps } from "./resolve";
|
|
5
|
-
import type { SubscriptionStore } from "./subscriptions";
|
|
1
|
+
import { errorCode } from "../http/errors.js";
|
|
2
|
+
import type { GatewayPlatform } from "../platform/platform.js";
|
|
3
|
+
import type { PrefixStore } from "./prefix_store.js";
|
|
4
|
+
import { resolveSelfHostedRouter, type SelfHostedResolverDeps } from "./resolve.js";
|
|
5
|
+
import type { SubscriptionStore } from "./subscriptions/index.js";
|
|
6
6
|
|
|
7
7
|
/**
|
|
8
8
|
* The self-hosted platform: routers from the config file, subscriptions and
|
|
@@ -14,8 +14,8 @@
|
|
|
14
14
|
import type { Database } from "bun:sqlite";
|
|
15
15
|
import type { ReasoningEffort, RouterPrefixHit } from "@mupt-ai/dari-router/policy-engine";
|
|
16
16
|
|
|
17
|
-
import type { PendingLeaseWrite, PrefixStateWrite } from "../platform/platform";
|
|
18
|
-
import { ROUTING_PREFIX_HASHES_MAX_COUNT } from "../platform/routing_contract";
|
|
17
|
+
import type { PendingLeaseWrite, PrefixStateWrite } from "../platform/platform.js";
|
|
18
|
+
import { ROUTING_PREFIX_HASHES_MAX_COUNT } from "../platform/routing_contract.js";
|
|
19
19
|
|
|
20
20
|
// Resolve returns entries up to this age so a continuation after a pause still
|
|
21
21
|
// recovers its conversation id and previous decision; the runtime itself
|
package/src/self_host/resolve.ts
CHANGED
|
@@ -4,33 +4,27 @@ import {
|
|
|
4
4
|
nativeModelId,
|
|
5
5
|
providerForModel,
|
|
6
6
|
type ReasoningEffort,
|
|
7
|
-
type RouterModelPrice,
|
|
8
7
|
type RouterPrefixHit,
|
|
9
8
|
} from "@mupt-ai/dari-router/policy-engine";
|
|
10
|
-
import { HttpError } from "../http/errors";
|
|
11
|
-
import type { ResolveRouterRequest } from "../platform/platform";
|
|
12
|
-
import {
|
|
13
|
-
import
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
ResolvedRouterModelConfig,
|
|
17
|
-
} from "../types";
|
|
18
|
-
import type { GatewayConfig, RouterConfig } from "./config";
|
|
9
|
+
import { HttpError } from "../http/errors.js";
|
|
10
|
+
import type { ResolveRouterRequest } from "../platform/platform.js";
|
|
11
|
+
import { codexModelConfig } from "../models/subscriptions.js";
|
|
12
|
+
import { registeredModelPrice } from "../providers/pi.js";
|
|
13
|
+
import type { ProviderKeySource, ResolvedRouter } from "../types.js";
|
|
14
|
+
import type { GatewayConfig, RouterConfig } from "./config.js";
|
|
19
15
|
import {
|
|
20
16
|
freshAccessToken,
|
|
21
17
|
type OAuthFetch,
|
|
22
18
|
type SubscriptionCredential,
|
|
23
19
|
type SubscriptionProvider,
|
|
24
20
|
type SubscriptionStore,
|
|
25
|
-
} from "./subscriptions";
|
|
21
|
+
} from "./subscriptions/index.js";
|
|
26
22
|
|
|
27
23
|
// A self-hosted gateway is one tenant; these stand in for the hosted
|
|
28
24
|
// organization and the user a personal subscription belongs to.
|
|
29
25
|
export const SELF_HOSTED_ORGANIZATION_ID = "self-hosted";
|
|
30
26
|
export const SELF_HOSTED_USER_ID = "self-hosted";
|
|
31
27
|
|
|
32
|
-
const CODEX_BACKEND_URL = "https://chatgpt.com/backend-api";
|
|
33
|
-
|
|
34
28
|
export type SelfHostedResolverDeps = {
|
|
35
29
|
config: GatewayConfig;
|
|
36
30
|
gatewayKeys: readonly string[];
|
|
@@ -176,8 +170,8 @@ export function gatewayKeyIndex(keys: readonly string[], presented: string): num
|
|
|
176
170
|
return null;
|
|
177
171
|
}
|
|
178
172
|
|
|
179
|
-
// Claude Code plans serve only Claude Code itself
|
|
180
|
-
// client through the Codex backend.
|
|
173
|
+
// Claude Code plans serve only Claude Code itself and Muse Code plans only
|
|
174
|
+
// Muse Code; ChatGPT plans serve any client through the Codex backend.
|
|
181
175
|
function subscriptionProviderFor(
|
|
182
176
|
provider: string,
|
|
183
177
|
clientHarness: ResolveRouterRequest["clientHarness"],
|
|
@@ -185,6 +179,7 @@ function subscriptionProviderFor(
|
|
|
185
179
|
if (provider === "anthropic") {
|
|
186
180
|
return clientHarness === "claude_code" ? "anthropic_claude_code" : null;
|
|
187
181
|
}
|
|
182
|
+
if (provider === "meta") return clientHarness === "muse_code" ? "meta_muse" : null;
|
|
188
183
|
if (provider === "openai") return "openai_codex";
|
|
189
184
|
return null;
|
|
190
185
|
}
|
|
@@ -197,34 +192,25 @@ function servingProviders(provider: string, credential: ProviderCredential): str
|
|
|
197
192
|
: [provider];
|
|
198
193
|
}
|
|
199
194
|
|
|
200
|
-
function codexModelConfig(
|
|
201
|
-
modelId: string,
|
|
202
|
-
price: RouterModelPrice | null,
|
|
203
|
-
): ResolvedRouterModelConfig {
|
|
204
|
-
return {
|
|
205
|
-
provider: "openai-codex",
|
|
206
|
-
native_model_id: nativeModelId(modelId),
|
|
207
|
-
api: "openai-codex-responses",
|
|
208
|
-
base_url: CODEX_BACKEND_URL,
|
|
209
|
-
// A plan bills no tokens; the catalog price only feeds cost estimates.
|
|
210
|
-
cost: price ?? { input: 0, output: 0 },
|
|
211
|
-
fast_mode: false,
|
|
212
|
-
};
|
|
213
|
-
}
|
|
214
|
-
|
|
215
195
|
function thinkingLevels(router: RouterConfig): Record<string, ReasoningEffort[]> {
|
|
216
196
|
return Object.fromEntries(
|
|
217
197
|
router.models.flatMap((model) => model.thinking ? [[model.id, model.thinking]] : []),
|
|
218
198
|
);
|
|
219
199
|
}
|
|
220
200
|
|
|
201
|
+
const SUBSCRIPTION_PLAN_NAMES: Record<SubscriptionProvider, string> = {
|
|
202
|
+
anthropic_claude_code: "Claude Code",
|
|
203
|
+
openai_codex: "ChatGPT",
|
|
204
|
+
meta_muse: "Muse Code",
|
|
205
|
+
};
|
|
206
|
+
|
|
221
207
|
function unavailableRouterError(
|
|
222
208
|
routerId: string,
|
|
223
209
|
exhausted: ReadonlySet<SubscriptionProvider>,
|
|
224
210
|
): HttpError {
|
|
225
211
|
if (exhausted.size > 0) {
|
|
226
212
|
const plans = [...exhausted]
|
|
227
|
-
.map((provider) => provider
|
|
213
|
+
.map((provider) => SUBSCRIPTION_PLAN_NAMES[provider])
|
|
228
214
|
.join(" and ");
|
|
229
215
|
return new HttpError(
|
|
230
216
|
424,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { refreshOAuth, type OAuthFetch } from "./oauth";
|
|
2
|
-
import type { SubscriptionCredential, SubscriptionStore } from "./store";
|
|
1
|
+
import { refreshOAuth, type OAuthFetch } from "./oauth.js";
|
|
2
|
+
import type { SubscriptionCredential, SubscriptionStore } from "./store.js";
|
|
3
3
|
|
|
4
4
|
const REFRESH_MARGIN_MS = 5 * 60_000;
|
|
5
5
|
|
|
@@ -12,8 +12,8 @@ import {
|
|
|
12
12
|
startOAuth,
|
|
13
13
|
type OAuthFetch,
|
|
14
14
|
type SubscriptionProvider,
|
|
15
|
-
} from "./oauth";
|
|
16
|
-
import { isHeld, type SubscriptionCredential, type SubscriptionStore } from "./store";
|
|
15
|
+
} from "./oauth.js";
|
|
16
|
+
import { isHeld, type SubscriptionCredential, type SubscriptionStore } from "./store.js";
|
|
17
17
|
|
|
18
18
|
export type SubscriptionHttpDeps = {
|
|
19
19
|
store: SubscriptionStore;
|
|
@@ -18,8 +18,8 @@
|
|
|
18
18
|
* `store.markUnavailable` holds that subscription until its reset and says
|
|
19
19
|
* whether another one can serve the retry.
|
|
20
20
|
*/
|
|
21
|
-
export { freshAccessToken } from "./access";
|
|
22
|
-
export { handleSubscriptionRequest, type SubscriptionHttpDeps } from "./http";
|
|
21
|
+
export { freshAccessToken } from "./access.js";
|
|
22
|
+
export { handleSubscriptionRequest, type SubscriptionHttpDeps } from "./http.js";
|
|
23
23
|
export {
|
|
24
24
|
CODEX_APPROVAL_PENDING,
|
|
25
25
|
SUBSCRIPTION_PROVIDERS,
|
|
@@ -34,10 +34,10 @@ export {
|
|
|
34
34
|
type OAuthOptions,
|
|
35
35
|
type OAuthTokens,
|
|
36
36
|
type SubscriptionProvider,
|
|
37
|
-
} from "./oauth";
|
|
37
|
+
} from "./oauth.js";
|
|
38
38
|
export {
|
|
39
39
|
SubscriptionStore,
|
|
40
40
|
isHeld,
|
|
41
41
|
type PendingOAuthSession,
|
|
42
42
|
type SubscriptionCredential,
|
|
43
|
-
} from "./store";
|
|
43
|
+
} from "./store.js";
|
|
@@ -2,16 +2,18 @@ import { createHash, randomBytes } from "node:crypto";
|
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* OAuth protocols for personal subscriptions: Claude Code (PKCE, the user
|
|
5
|
-
* pastes back the `code#state` Anthropic shows)
|
|
6
|
-
*
|
|
7
|
-
*
|
|
5
|
+
* pastes back the `code#state` Anthropic shows), ChatGPT/Codex (device code,
|
|
6
|
+
* the gateway polls for approval), and Muse Code (Meta's device code, then the
|
|
7
|
+
* subscription's Model API key minted from the sign-in token). Every network
|
|
8
|
+
* call goes through the injected `fetch`.
|
|
8
9
|
*/
|
|
9
10
|
|
|
10
|
-
export type SubscriptionProvider = "anthropic_claude_code" | "openai_codex";
|
|
11
|
+
export type SubscriptionProvider = "anthropic_claude_code" | "openai_codex" | "meta_muse";
|
|
11
12
|
|
|
12
13
|
export const SUBSCRIPTION_PROVIDERS: readonly SubscriptionProvider[] = [
|
|
13
14
|
"anthropic_claude_code",
|
|
14
15
|
"openai_codex",
|
|
16
|
+
"meta_muse",
|
|
15
17
|
];
|
|
16
18
|
|
|
17
19
|
export type OAuthFetch = (url: string, init: RequestInit) => Promise<Response>;
|
|
@@ -20,7 +22,8 @@ export type OAuthOptions = { fetch: OAuthFetch; now?: Date };
|
|
|
20
22
|
|
|
21
23
|
/** The provider refused or could not be reached (HTTP 502 at the edge). */
|
|
22
24
|
export class SubscriptionOAuthProviderError extends Error {
|
|
23
|
-
|
|
25
|
+
// `errorCode` is the provider's OAuth `error` code, such as `authorization_pending`.
|
|
26
|
+
constructor(message: string, readonly status?: number, readonly errorCode?: string) {
|
|
24
27
|
super(message);
|
|
25
28
|
this.name = "SubscriptionOAuthProviderError";
|
|
26
29
|
}
|
|
@@ -43,6 +46,8 @@ export type OAuthAuthorization = {
|
|
|
43
46
|
flow: Record<string, string>;
|
|
44
47
|
};
|
|
45
48
|
|
|
49
|
+
// A Muse Code plan's access token is the Model API key minted for it, and its
|
|
50
|
+
// refresh token the Meta sign-in token the key is minted from.
|
|
46
51
|
export type OAuthTokens = {
|
|
47
52
|
provider: SubscriptionProvider;
|
|
48
53
|
accessToken: string;
|
|
@@ -76,6 +81,23 @@ const CODEX_ACCOUNT_CLAIM = "https://api.openai.com/auth";
|
|
|
76
81
|
export const CODEX_APPROVAL_PENDING =
|
|
77
82
|
"OpenAI approval is still pending. Enter the code at OpenAI, finish approval, then try again.";
|
|
78
83
|
|
|
84
|
+
// Muse Code's own device sign-in (`muse login`), as its public launcher runs it.
|
|
85
|
+
export const MUSE_CODE_CLIENT_ID = "1031625952748946";
|
|
86
|
+
const META_AUTH_BASE_URL = "https://auth.meta.com";
|
|
87
|
+
const META_DEVICE_AUTHORIZATION_URL = `${META_AUTH_BASE_URL}/oidc/device/authorization/`;
|
|
88
|
+
const META_TOKEN_URL = `${META_AUTH_BASE_URL}/oidc/device/token/`;
|
|
89
|
+
// Muse Code mints its subscription's Model API key from the sign-in token here.
|
|
90
|
+
const MUSE_MINT_URL = "https://api.meta.ai/muse-code/key";
|
|
91
|
+
// Meta states no lifetime for a minted key, and Muse Code mints a fresh one at
|
|
92
|
+
// every start, so the key is minted again on this cadence.
|
|
93
|
+
const MUSE_KEY_LIFETIME_MS = 12 * 60 * 60_000;
|
|
94
|
+
// Marks a stored sign-in refresh token, which is exchanged for a fresh sign-in
|
|
95
|
+
// token before each mint. Without it the stored value is the sign-in token.
|
|
96
|
+
const MUSE_SIGN_IN_REFRESH_PREFIX = "refresh:";
|
|
97
|
+
|
|
98
|
+
export const META_APPROVAL_PENDING =
|
|
99
|
+
"Meta approval is still pending. Enter the code at Meta, finish approval, then try again.";
|
|
100
|
+
|
|
79
101
|
export async function startOAuth(
|
|
80
102
|
provider: SubscriptionProvider,
|
|
81
103
|
options: OAuthOptions,
|
|
@@ -103,6 +125,23 @@ export async function startOAuth(
|
|
|
103
125
|
flow: { code_verifier: verifier, state },
|
|
104
126
|
};
|
|
105
127
|
}
|
|
128
|
+
if (provider === "meta_muse") {
|
|
129
|
+
const payload = await postForm(
|
|
130
|
+
options.fetch,
|
|
131
|
+
META_DEVICE_AUTHORIZATION_URL,
|
|
132
|
+
{ client_id: MUSE_CODE_CLIENT_ID },
|
|
133
|
+
"Meta device code request",
|
|
134
|
+
);
|
|
135
|
+
const complete = payload.verification_uri_complete;
|
|
136
|
+
return {
|
|
137
|
+
authorizationUrl: typeof complete === "string" && complete.startsWith("https://")
|
|
138
|
+
? complete
|
|
139
|
+
: requiredString(payload, "verification_uri"),
|
|
140
|
+
expiresAt,
|
|
141
|
+
userCode: requiredString(payload, "user_code"),
|
|
142
|
+
flow: { device_code: requiredString(payload, "device_code") },
|
|
143
|
+
};
|
|
144
|
+
}
|
|
106
145
|
const payload = await postJson(
|
|
107
146
|
options.fetch,
|
|
108
147
|
`${CODEX_DEVICE_AUTH_URL}/usercode`,
|
|
@@ -120,7 +159,7 @@ export async function startOAuth(
|
|
|
120
159
|
|
|
121
160
|
/**
|
|
122
161
|
* Finish a flow. Claude Code needs the pasted authorization response; the
|
|
123
|
-
* device-code
|
|
162
|
+
* device-code flows ignore it and ask the provider whether the user approved.
|
|
124
163
|
*/
|
|
125
164
|
export async function completeOAuth(
|
|
126
165
|
provider: SubscriptionProvider,
|
|
@@ -154,6 +193,35 @@ export async function completeOAuth(
|
|
|
154
193
|
);
|
|
155
194
|
return claudeTokens(token, now, null);
|
|
156
195
|
}
|
|
196
|
+
if (provider === "meta_muse") {
|
|
197
|
+
let token: Record<string, unknown>;
|
|
198
|
+
try {
|
|
199
|
+
token = await postForm(
|
|
200
|
+
options.fetch,
|
|
201
|
+
META_TOKEN_URL,
|
|
202
|
+
{
|
|
203
|
+
grant_type: "urn:ietf:params:oauth:grant-type:device_code",
|
|
204
|
+
device_code: requiredString(flow, "device_code"),
|
|
205
|
+
client_id: MUSE_CODE_CLIENT_ID,
|
|
206
|
+
},
|
|
207
|
+
"Meta device approval check",
|
|
208
|
+
);
|
|
209
|
+
} catch (error) {
|
|
210
|
+
if (error instanceof SubscriptionOAuthProviderError) {
|
|
211
|
+
if (error.errorCode === "authorization_pending" || error.errorCode === "slow_down") {
|
|
212
|
+
throw new SubscriptionOAuthInputError(META_APPROVAL_PENDING);
|
|
213
|
+
}
|
|
214
|
+
if (error.errorCode === "access_denied") {
|
|
215
|
+
throw new SubscriptionOAuthInputError("The sign-in was declined on Meta. Start again to retry.");
|
|
216
|
+
}
|
|
217
|
+
if (error.errorCode === "expired_token") {
|
|
218
|
+
throw new SubscriptionOAuthInputError("The Meta sign-in code expired. Start again.");
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
throw error;
|
|
222
|
+
}
|
|
223
|
+
return await museTokens(requiredString(token, "access_token"), museRefreshToken(token), options.fetch, now);
|
|
224
|
+
}
|
|
157
225
|
|
|
158
226
|
// The provider, not user-supplied input, supplies the authorization code.
|
|
159
227
|
let approval: Record<string, unknown>;
|
|
@@ -207,6 +275,28 @@ export async function refreshOAuth(
|
|
|
207
275
|
);
|
|
208
276
|
return claudeTokens(token, now, credential.refreshToken);
|
|
209
277
|
}
|
|
278
|
+
if (credential.provider === "meta_muse") {
|
|
279
|
+
let stored = credential.refreshToken;
|
|
280
|
+
let signInToken = stored;
|
|
281
|
+
if (stored.startsWith(MUSE_SIGN_IN_REFRESH_PREFIX)) {
|
|
282
|
+
const token = await postForm(
|
|
283
|
+
options.fetch,
|
|
284
|
+
META_TOKEN_URL,
|
|
285
|
+
{
|
|
286
|
+
grant_type: "refresh_token",
|
|
287
|
+
refresh_token: stored.slice(MUSE_SIGN_IN_REFRESH_PREFIX.length),
|
|
288
|
+
client_id: MUSE_CODE_CLIENT_ID,
|
|
289
|
+
},
|
|
290
|
+
"Meta sign-in refresh",
|
|
291
|
+
);
|
|
292
|
+
signInToken = requiredString(token, "access_token");
|
|
293
|
+
stored = museRefreshToken(token) ?? stored;
|
|
294
|
+
}
|
|
295
|
+
// A lapsed plan fails routing like any other refresh failure.
|
|
296
|
+
return await museTokens(signInToken, stored, options.fetch, now).catch((error: unknown) => {
|
|
297
|
+
throw error instanceof SubscriptionOAuthInputError ? new SubscriptionOAuthProviderError(error.message) : error;
|
|
298
|
+
});
|
|
299
|
+
}
|
|
210
300
|
const token = await postJson(
|
|
211
301
|
options.fetch,
|
|
212
302
|
CODEX_TOKEN_URL,
|
|
@@ -258,6 +348,43 @@ function claudeTokens(
|
|
|
258
348
|
};
|
|
259
349
|
}
|
|
260
350
|
|
|
351
|
+
function museRefreshToken(token: Record<string, unknown>): string | null {
|
|
352
|
+
const value = token.refresh_token;
|
|
353
|
+
return typeof value === "string" && value ? MUSE_SIGN_IN_REFRESH_PREFIX + value : null;
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
// Mints the plan's Model API key from the Meta sign-in token.
|
|
357
|
+
async function museTokens(
|
|
358
|
+
signInToken: string,
|
|
359
|
+
refreshToken: string | null,
|
|
360
|
+
fetch: OAuthFetch,
|
|
361
|
+
now: Date,
|
|
362
|
+
): Promise<OAuthTokens> {
|
|
363
|
+
const minted = await requestJson(
|
|
364
|
+
fetch,
|
|
365
|
+
MUSE_MINT_URL,
|
|
366
|
+
"{}",
|
|
367
|
+
"application/json",
|
|
368
|
+
"Muse Code subscription key mint",
|
|
369
|
+
{ Authorization: `Bearer ${signInToken}`, "x-api-version": "1.0.0" },
|
|
370
|
+
);
|
|
371
|
+
// A key minted without an active plan bills Model API pay-as-you-go.
|
|
372
|
+
if (minted.is_subs_active !== true) {
|
|
373
|
+
throw new SubscriptionOAuthInputError(
|
|
374
|
+
"This Meta account has no active Muse Code subscription. Subscribe at https://accountscenter.meta.com/muse_code/, then connect again.",
|
|
375
|
+
);
|
|
376
|
+
}
|
|
377
|
+
const email = minted.user_email;
|
|
378
|
+
return {
|
|
379
|
+
provider: "meta_muse",
|
|
380
|
+
accessToken: requiredString(minted, "api_key"),
|
|
381
|
+
refreshToken: refreshToken ?? signInToken,
|
|
382
|
+
expiresAt: new Date(now.getTime() + MUSE_KEY_LIFETIME_MS),
|
|
383
|
+
accountId: null,
|
|
384
|
+
accountEmail: typeof email === "string" && email ? email : null,
|
|
385
|
+
};
|
|
386
|
+
}
|
|
387
|
+
|
|
261
388
|
function codexTokens(
|
|
262
389
|
payload: Record<string, unknown>,
|
|
263
390
|
now: Date,
|
|
@@ -353,12 +480,13 @@ async function requestJson(
|
|
|
353
480
|
body: string,
|
|
354
481
|
contentType: string,
|
|
355
482
|
operation: string,
|
|
483
|
+
headers: Record<string, string> = {},
|
|
356
484
|
): Promise<Record<string, unknown>> {
|
|
357
485
|
let response: Response;
|
|
358
486
|
try {
|
|
359
487
|
response = await fetch(url, {
|
|
360
488
|
method: "POST",
|
|
361
|
-
headers: { Accept: "application/json", "Content-Type": contentType, "User-Agent": "Dari/1.0" },
|
|
489
|
+
headers: { Accept: "application/json", "Content-Type": contentType, "User-Agent": "Dari/1.0", ...headers },
|
|
362
490
|
body,
|
|
363
491
|
signal: AbortSignal.timeout(REQUEST_TIMEOUT_MS),
|
|
364
492
|
});
|
|
@@ -366,10 +494,13 @@ async function requestJson(
|
|
|
366
494
|
throw new SubscriptionOAuthProviderError(`${operation} could not reach the provider.`);
|
|
367
495
|
}
|
|
368
496
|
if (!response.ok) {
|
|
369
|
-
|
|
497
|
+
// Only the RFC 6749 `error` code is kept; the rest may carry provider detail.
|
|
498
|
+
const failure: unknown = await response.json().catch(() => undefined);
|
|
499
|
+
const errorCode = isRecord(failure) && typeof failure.error === "string" ? failure.error : undefined;
|
|
370
500
|
throw new SubscriptionOAuthProviderError(
|
|
371
501
|
`${operation} failed with provider status ${response.status}.`,
|
|
372
502
|
response.status,
|
|
503
|
+
errorCode,
|
|
373
504
|
);
|
|
374
505
|
}
|
|
375
506
|
let decoded: unknown;
|
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
import type { Database } from "bun:sqlite";
|
|
14
14
|
import { randomBytes, randomUUID } from "node:crypto";
|
|
15
15
|
|
|
16
|
-
import type { OAuthTokens, SubscriptionProvider } from "./oauth";
|
|
16
|
+
import type { OAuthTokens, SubscriptionProvider } from "./oauth.js";
|
|
17
17
|
|
|
18
18
|
export type SubscriptionCredential = {
|
|
19
19
|
id: string;
|
|
@@ -47,6 +47,7 @@ export type PendingOAuthSession = {
|
|
|
47
47
|
const BASE_NAMES: Record<SubscriptionProvider, string> = {
|
|
48
48
|
anthropic_claude_code: "ANTHROPIC_CLAUDE_CODE_OAUTH_TOKEN",
|
|
49
49
|
openai_codex: "OPENAI_CODEX_OAUTH_TOKEN",
|
|
50
|
+
meta_muse: "META_MUSE_OAUTH_TOKEN",
|
|
50
51
|
};
|
|
51
52
|
|
|
52
53
|
type CredentialRow = {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { parseSelectorDecision } from "@mupt-ai/dari-router/policy-engine";
|
|
2
|
-
import { HttpError } from "../http/errors";
|
|
3
|
-
import type { SelectorBackend } from "./routing";
|
|
2
|
+
import { HttpError } from "../http/errors.js";
|
|
3
|
+
import type { SelectorBackend } from "./routing.js";
|
|
4
4
|
|
|
5
5
|
export const DARI_AUTO_ROUTING_ENDPOINT = "https://routing.dari.dev/v1/auto-router";
|
|
6
6
|
// Same selector identity and input budget as `createAutoRouter` in
|
|
@@ -8,9 +8,9 @@ import {
|
|
|
8
8
|
type RouterEval,
|
|
9
9
|
} from "@mupt-ai/dari-router/policy-engine";
|
|
10
10
|
|
|
11
|
-
import { publicCatalogSelectorEvals } from "../context/eval_catalog";
|
|
12
|
-
import { scrubSecrets } from "../telemetry/scrub";
|
|
13
|
-
import type { ResolvedRouter } from "../types";
|
|
11
|
+
import { publicCatalogSelectorEvals } from "../context/eval_catalog.js";
|
|
12
|
+
import { scrubSecrets } from "../telemetry/scrub.js";
|
|
13
|
+
import type { ResolvedRouter } from "../types.js";
|
|
14
14
|
|
|
15
15
|
export type EvalRelevanceDetails =
|
|
16
16
|
| {
|