Merge branch 'dev' of github.com:anomalyco/opencode into dev

This commit is contained in:
Frank 2026-07-19 23:30:38 -04:00
commit cfa134f042
28 changed files with 151 additions and 72 deletions

View file

@ -60,6 +60,8 @@ export function PromptInputV2Composer(props: PromptInputV2ComposerProps) {
controller={props.controller} controller={props.controller}
borderUnderlay={props.borderUnderlay} borderUnderlay={props.borderUnderlay}
class={props.class} class={props.class}
attachKeybind={command.keybindParts("file.attach")}
attachShortcut={command.keybind("file.attach")}
modelControl={ modelControl={
<PromptInputV2ModelControl <PromptInputV2ModelControl
loading={props.controller.model.loading} loading={props.controller.model.loading}
@ -451,12 +453,14 @@ export function usePromptInputV2Controller(props: PromptInputV2ControllerProps):
options: () => props.controls.agents.options.map((name) => ({ id: name, label: name })), options: () => props.controls.agents.options.map((name) => ({ id: name, label: name })),
current: () => props.controls.agents.current, current: () => props.controls.agents.current,
onSelect: props.controls.agents.select, onSelect: props.controls.agents.select,
keybind: () => command.keybindParts("agent.cycle"),
} }
: undefined, : undefined,
variant: { variant: {
options: () => variants().map((value) => ({ id: value, label: value })), options: () => variants().map((value) => ({ id: value, label: value })),
current: () => props.controls.model.selection.variant.current() ?? "default", current: () => props.controls.model.selection.variant.current() ?? "default",
onSelect: (value) => props.controls.model.selection.variant.set(value === "default" ? undefined : value), onSelect: (value) => props.controls.model.selection.variant.set(value === "default" ? undefined : value),
keybind: () => command.keybindParts("model.variant.cycle"),
}, },
submit: { submit: {
stopping, stopping,

View file

@ -67,7 +67,7 @@ export function useTitlebarRightMount() {
return mount return mount
} }
export function Titlebar(props: { update?: TitlebarUpdate }) { export function Titlebar(props: { update?: TitlebarUpdate; debugTools?: { visible: boolean; toggle: () => void } }) {
const layout = useLayout() const layout = useLayout()
const platform = usePlatform() const platform = usePlatform()
const command = useCommand() const command = useCommand()
@ -462,7 +462,7 @@ export function Titlebar(props: { update?: TitlebarUpdate }) {
"md:pl-4": !mac(), "md:pl-4": !mac(),
}} }}
> >
<ChannelIndicator /> <ChannelIndicator debugTools={props.debugTools} />
<Show when={windows() || linux()}> <Show when={windows() || linux()}>
<WindowsAppMenu command={command} platform={platform} variant="v2" /> <WindowsAppMenu command={command} platform={platform} variant="v2" />
</Show> </Show>
@ -660,9 +660,9 @@ export function Titlebar(props: { update?: TitlebarUpdate }) {
</div> </div>
</Show> </Show>
<div id="opencode-titlebar-left" class="flex items-center gap-3 min-w-0 px-2" /> <div id="opencode-titlebar-left" class="flex items-center gap-3 min-w-0 px-2" />
<ChannelIndicator />
</div> </div>
</div> </div>
<ChannelIndicator debugTools={props.debugTools} />
</div> </div>
</div> </div>
@ -747,12 +747,27 @@ function TitlebarUpdateIconButton(props: { state: TitlebarUpdatePillState }) {
) )
} }
function ChannelIndicator() { function ChannelIndicator(props: { debugTools?: { visible: boolean; toggle: () => void } }) {
const channel = import.meta.env.VITE_OPENCODE_CHANNEL
if (channel === "dev" && props.debugTools) {
return (
<button
type="button"
class="bg-icon-interactive-base text-[#FFF] font-medium px-2 rounded-sm uppercase font-mono cursor-pointer"
onClick={props.debugTools.toggle}
aria-label="Toggle debug tools"
aria-pressed={props.debugTools.visible}
>
DEV
</button>
)
}
return ( return (
<> <>
{["beta", "dev"].includes(import.meta.env.VITE_OPENCODE_CHANNEL) && ( {["beta", "dev"].includes(channel) && (
<div class="bg-icon-interactive-base text-[#FFF] font-medium px-2 rounded-sm uppercase font-mono"> <div class="bg-icon-interactive-base text-[#FFF] font-medium px-2 rounded-sm uppercase font-mono">
{import.meta.env.VITE_OPENCODE_CHANNEL.toUpperCase()} {channel.toUpperCase()}
</div> </div>
)} )}
</> </>

View file

@ -1,4 +1,5 @@
import { createEffect, Suspense, type ParentProps } from "solid-js" import { createEffect, Suspense, type ParentProps } from "solid-js"
import { createStore } from "solid-js/store"
import { useNavigate } from "@solidjs/router" import { useNavigate } from "@solidjs/router"
import { DebugBar } from "@/components/debug-bar" import { DebugBar } from "@/components/debug-bar"
import { TabsInfoPopup } from "@/components/help-button" import { TabsInfoPopup } from "@/components/help-button"
@ -11,6 +12,7 @@ export default function NewLayout(props: ParentProps) {
const platform = usePlatform() const platform = usePlatform()
const navigate = useNavigate() const navigate = useNavigate()
setNavigate(navigate) setNavigate(navigate)
const [state, setState] = createStore({ debugTools: true })
createEffect(() => setV2Toast(true)) createEffect(() => setV2Toast(true))
@ -32,11 +34,18 @@ export default function NewLayout(props: ParentProps) {
"padding-bottom": "env(safe-area-inset-bottom, 0px)", "padding-bottom": "env(safe-area-inset-bottom, 0px)",
}} }}
> >
<Titlebar update={update} /> <Titlebar
update={update}
debugTools={
import.meta.env.DEV
? { visible: state.debugTools, toggle: () => setState("debugTools", (value) => !value) }
: undefined
}
/>
<main class="flex-1 min-h-0 min-w-0 overflow-x-hidden flex flex-col items-start contain-strict"> <main class="flex-1 min-h-0 min-w-0 overflow-x-hidden flex flex-col items-start contain-strict">
<Suspense>{props.children}</Suspense> <Suspense>{props.children}</Suspense>
</main> </main>
{import.meta.env.DEV && <DebugBar inline />} {import.meta.env.DEV && state.debugTools && <DebugBar inline />}
<TabsInfoPopup /> <TabsInfoPopup />
<ToastRegion v2 /> <ToastRegion v2 />
</div> </div>

View file

@ -156,6 +156,7 @@ export default function LegacyLayout(props: ParentProps) {
sizing: false, sizing: false,
peek: undefined as string | undefined, peek: undefined as string | undefined,
peeked: false, peeked: false,
debugTools: true,
}) })
const updateVersion = () => { const updateVersion = () => {
@ -2248,7 +2249,14 @@ export default function LegacyLayout(props: ParentProps) {
return ( return (
<div class="relative bg-background-base flex-1 min-h-0 min-w-0 flex flex-col select-none [&_input]:select-text [&_textarea]:select-text [&_[contenteditable]]:select-text"> <div class="relative bg-background-base flex-1 min-h-0 min-w-0 flex flex-col select-none [&_input]:select-text [&_textarea]:select-text [&_[contenteditable]]:select-text">
{autoselecting() ?? ""} {autoselecting() ?? ""}
<Titlebar update={titlebarUpdate} /> <Titlebar
update={titlebarUpdate}
debugTools={
import.meta.env.DEV && import.meta.env.VITE_DISABLE_DEBUG_BAR !== "1"
? { visible: state.debugTools, toggle: () => setState("debugTools", (value) => !value) }
: undefined
}
/>
<Show when={updateVersion() !== undefined}> <Show when={updateVersion() !== undefined}>
<UpdateAvailableToast version={updateVersion() ?? ""} install={installUpdate} language={language} /> <UpdateAvailableToast version={updateVersion() ?? ""} install={installUpdate} language={language} />
</Show> </Show>
@ -2393,7 +2401,7 @@ export default function LegacyLayout(props: ParentProps) {
</div> </div>
</div> </div>
</div> </div>
{import.meta.env.DEV && import.meta.env.VITE_DISABLE_DEBUG_BAR !== "1" && <DebugBar />} {import.meta.env.DEV && import.meta.env.VITE_DISABLE_DEBUG_BAR !== "1" && state.debugTools && <DebugBar />}
</div> </div>
<TabsInfoPopup /> <TabsInfoPopup />
<ToastRegion v2={false} /> <ToastRegion v2={false} />

View file

@ -3,13 +3,17 @@ import { LLMError, ProviderErrorEvent } from "./schema"
const patterns = [ const patterns = [
/prompt is too long/i, /prompt is too long/i,
/request_too_large/i,
/input is too long for requested model/i, /input is too long for requested model/i,
/exceeds the context window/i, /exceeds the context window/i,
/exceeds (?:the )?(?:model'?s )?maximum context length(?: of [\d,]+ tokens?|\s*\([\d,]+\))/i,
/input token count.*exceeds the maximum/i, /input token count.*exceeds the maximum/i,
/tokens in request more than max tokens allowed/i, /tokens in request more than max tokens allowed/i,
/maximum prompt length is \d+/i, /maximum prompt length is \d+/i,
/reduce the length of the messages/i, /reduce the length of the messages/i,
/maximum context length is \d+ tokens/i, /maximum context length is \d+ tokens/i,
/exceeds (?:the )?maximum allowed input length of [\d,]+ tokens?/i,
/input \(\d+ tokens\) is longer than the model'?s context length \(\d+ tokens\)/i,
/exceeds the limit of \d+/i, /exceeds the limit of \d+/i,
/exceeds the available context size/i, /exceeds the available context size/i,
/greater than the context length/i, /greater than the context length/i,
@ -21,11 +25,17 @@ const patterns = [
/input length.*exceeds.*context length/i, /input length.*exceeds.*context length/i,
/prompt too long; exceeded (?:max )?context length/i, /prompt too long; exceeded (?:max )?context length/i,
/too large for model with \d+ maximum context length/i, /too large for model with \d+ maximum context length/i,
/prompt has [\d,]+ tokens?, but the configured context size is [\d,]+ tokens?/i,
/model_context_window_exceeded/i, /model_context_window_exceeded/i,
/too many tokens/i,
/token limit exceeded/i,
] ]
const exclusions = [/^(throttling error|service unavailable):/i, /rate limit/i, /too many requests/i]
export const isContextOverflow = (message: string) => export const isContextOverflow = (message: string) =>
patterns.some((pattern) => pattern.test(message)) || /^4(00|13)\s*(status code)?\s*\(no body\)/i.test(message) !exclusions.some((pattern) => pattern.test(message)) &&
(patterns.some((pattern) => pattern.test(message)) || /^4(00|13)\s*(status code)?\s*\(no body\)/i.test(message))
export const isContextOverflowFailure = (failure: unknown) => export const isContextOverflowFailure = (failure: unknown) =>
failure instanceof LLMError failure instanceof LLMError

View file

@ -2,7 +2,29 @@ import { describe, expect, test } from "bun:test"
import { isContextOverflow } from "../src" import { isContextOverflow } from "../src"
describe("provider error classification", () => { describe("provider error classification", () => {
test("classifies Z.AI GLM token limit messages as context overflow", () => { test("classifies provider token limit messages as context overflow", () => {
expect(isContextOverflow("tokens in request more than max tokens allowed")).toBe(true) const messages = [
"tokens in request more than max tokens allowed",
'{"error":{"type":"request_too_large","message":"Request exceeds the maximum size"}}',
"Requested token count exceeds the model's maximum context length of 131072 tokens.",
"Input length (265330) exceeds model's maximum context length (262144).",
"Input length 131393 exceeds the maximum allowed input length of 131040 tokens.",
"The input (516368 tokens) is longer than the model's context length (262144 tokens).",
"Prompt has 5,958,968 tokens, but the configured context size is 256,000 tokens",
"Too many tokens",
"Token limit exceeded",
]
expect(messages.every(isContextOverflow)).toBe(true)
})
test("does not classify rate limits as context overflow", () => {
const messages = [
"Throttling error: Too many tokens, please wait before trying again.",
"Rate limit exceeded, please retry after 30 seconds.",
"Too many requests. Please slow down.",
]
expect(messages.some(isContextOverflow)).toBe(false)
}) })
}) })

View file

@ -32,7 +32,7 @@ import { ModelStatus } from "./model-status"
import { RuntimeFlags } from "@/effect/runtime-flags" import { RuntimeFlags } from "@/effect/runtime-flags"
import { ProviderError } from "./error" import { ProviderError } from "./error"
const OPENAI_HEADER_TIMEOUT_DEFAULT = 10_000 const OPENAI_HEADER_TIMEOUT_DEFAULT = 300_000
function wrapSSE(res: Response, ms: number, ctl: AbortController) { function wrapSSE(res: Response, ms: number, ctl: AbortController) {
if (typeof ms !== "number" || ms <= 0) return res if (typeof ms !== "number" || ms <= 0) return res

View file

@ -162,7 +162,7 @@ it.live("OpenAI API auth gets default headerTimeout", () =>
Effect.gen(function* () { Effect.gen(function* () {
const provider = yield* Provider.Service const provider = yield* Provider.Service
const openai = yield* provider.getProvider(ProviderV2.ID.openai) const openai = yield* provider.getProvider(ProviderV2.ID.openai)
expect(openai.options.headerTimeout).toBe(10_000) expect(openai.options.headerTimeout).toBe(300_000)
}), }),
) )
}), }),

View file

@ -891,7 +891,7 @@
width: 16px; width: 16px;
height: 2px; height: 2px;
border-radius: 999px; border-radius: 999px;
background-color: var(--icon-weak-base); background-color: var(--v2-icon-icon-muted);
transition: background-color 0.2s ease; transition: background-color 0.2s ease;
} }

View file

@ -39,6 +39,8 @@ export type PromptInputV2Props = {
borderUnderlay?: boolean borderUnderlay?: boolean
class?: string class?: string
modelControl?: JSX.Element modelControl?: JSX.Element
attachKeybind?: string[]
attachShortcut?: string
} }
export function PromptInputV2(props: PromptInputV2Props) { export function PromptInputV2(props: PromptInputV2Props) {
@ -197,9 +199,9 @@ export function PromptInputV2(props: PromptInputV2Props) {
<PromptInputV2AddMenu <PromptInputV2AddMenu
disabled={state.mode === "shell"} disabled={state.mode === "shell"}
title="Add images and files" title="Add images and files"
keybind={["Mod", "U"]} keybind={props.attachKeybind ?? ["Mod", "U"]}
attachLabel="Images and files" attachLabel="Images and files"
attachShortcut="Mod+U" attachShortcut={props.attachShortcut ?? "Mod+U"}
commandsLabel="Commands" commandsLabel="Commands"
contextLabel="Context" contextLabel="Context"
shellLabel="Shell command" shellLabel="Shell command"
@ -233,7 +235,11 @@ export function PromptInputV2(props: PromptInputV2Props) {
<Show when={view.variant}> <Show when={view.variant}>
{(control) => ( {(control) => (
<Show when={control().options().length > 1}> <Show when={control().options().length > 1}>
<PromptInputV2ConfiguredSelect title="Choose model variant" control={control()} /> <PromptInputV2ConfiguredSelect
title="Choose model variant"
keybind={["Shift", "Mod", "D"]}
control={control()}
/>
</Show> </Show>
)} )}
</Show> </Show>
@ -512,7 +518,7 @@ function PromptInputV2ConfiguredSelect(props: {
return ( return (
<PromptInputV2Select <PromptInputV2Select
title={props.title} title={props.title}
keybind={props.keybind} keybind={props.control.keybind?.() ?? props.keybind}
options={props.control.options()} options={props.control.options()}
current={current()} current={current()}
currentIcon={ currentIcon={
@ -536,36 +542,45 @@ export function PromptInputV2Select(props: {
onSelect: (id: string) => void onSelect: (id: string) => void
}) { }) {
return ( return (
<MenuV2 gutter={6} modal={false} placement="top-start" onOpenChange={props.onOpenChange}> <TooltipV2
<MenuV2.Trigger placement="top"
as={ButtonV2} value={
variant="ghost-muted" <>
size="normal" {props.title}
class={`max-w-[220px] justify-start ![font-weight:440] ${props.class ?? ""}`} <KeybindV2 keys={props.keybind ?? []} variant="neutral" />
title={keybindTitle(props.title, props.keybind)} </>
> }
{props.currentIcon} >
<span class="truncate capitalize leading-5"> <MenuV2 gutter={6} modal={false} placement="top-start" onOpenChange={props.onOpenChange}>
{props.options.find((option) => option.id === props.current)?.label ?? props.current} <MenuV2.Trigger
</span> as={ButtonV2}
<span class="-ml-0.5 -mr-1 flex shrink-0"> variant="ghost-muted"
<IconV2 name="chevron-down" /> size="normal"
</span> class={`max-w-[220px] justify-start ![font-weight:440] ${props.class ?? ""}`}
</MenuV2.Trigger> >
<MenuV2.Portal> {props.currentIcon}
<MenuV2.Content> <span class="truncate capitalize leading-5">
<MenuV2.RadioGroup value={props.current} onChange={props.onSelect}> {props.options.find((option) => option.id === props.current)?.label ?? props.current}
<For each={props.options}> </span>
{(option) => ( <span class="-ml-0.5 -mr-1 flex shrink-0">
<MenuV2.RadioItem value={option.id} class="capitalize" closeOnSelect> <IconV2 name="chevron-down" />
{option.label} </span>
</MenuV2.RadioItem> </MenuV2.Trigger>
)} <MenuV2.Portal>
</For> <MenuV2.Content>
</MenuV2.RadioGroup> <MenuV2.RadioGroup value={props.current} onChange={props.onSelect}>
</MenuV2.Content> <For each={props.options}>
</MenuV2.Portal> {(option) => (
</MenuV2> <MenuV2.RadioItem value={option.id} class="capitalize" closeOnSelect>
{option.label}
</MenuV2.RadioItem>
)}
</For>
</MenuV2.RadioGroup>
</MenuV2.Content>
</MenuV2.Portal>
</MenuV2>
</TooltipV2>
) )
} }
@ -688,8 +703,3 @@ function PromptInputV2SuggestionIcon(props: { item: PromptInputV2Suggestion }) {
/> />
) )
} }
function keybindTitle(label: string, keybind?: string[]) {
if (!keybind?.length) return label
return `${label} (${keybind.join("+")})`
}

View file

@ -23,6 +23,7 @@ export type PromptInputV2SelectControl = {
options: Accessor<PromptInputV2Option[]> options: Accessor<PromptInputV2Option[]>
current: Accessor<string> current: Accessor<string>
onSelect: (id: string) => void onSelect: (id: string) => void
keybind?: Accessor<string[]>
} }
export type PromptInputV2ViewConfig = { export type PromptInputV2ViewConfig = {

View file

@ -86,7 +86,7 @@ OpenCode Go هو اشتراك منخفض التكلفة — **$5 للشهر ال
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ Tabela ispod pruža procijenjeni broj zahtjeva na osnovu tipičnih obrazaca kori
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ Tabellen nedenfor giver et estimeret antal anmodninger baseret på typiske Go-fo
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -88,7 +88,7 @@ Die folgende Tabelle zeigt eine geschätzte Anzahl von Anfragen basierend auf ty
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ La siguiente tabla proporciona una cantidad estimada de peticiones basada en los
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ Le tableau ci-dessous fournit une estimation du nombre de requêtes basée sur d
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -94,7 +94,7 @@ La tabella seguente fornisce una stima del conteggio delle richieste in base a p
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ OpenCode Goには以下の制限が含まれています
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ OpenCode Go에는 다음과 같은 한도가 포함됩니다.
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ Tabellen nedenfor gir et estimert antall forespørsler basert på typiske bruksm
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -90,7 +90,7 @@ Poniższa tabela przedstawia szacunkową liczbę żądań na podstawie typowych
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ A tabela abaixo fornece uma contagem estimada de requisições com base nos padr
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -96,7 +96,7 @@ OpenCode Go включает следующие лимиты:
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ OpenCode Go มีขีดจำกัดดังต่อไปนี้:
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ Aşağıdaki tablo, tipik Go kullanım modellerine dayalı tahmini bir istek say
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ OpenCode Go 包含以下限制:
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |

View file

@ -86,7 +86,7 @@ OpenCode Go 包含以下限制:
| Grok 4.5 | 120 | 300 | 600 | | Grok 4.5 | 120 | 300 | 600 |
| GLM-5.2 | 880 | 2,150 | 4,300 | | GLM-5.2 | 880 | 2,150 | 4,300 |
| GLM-5.1 | 880 | 2,150 | 4,300 | | GLM-5.1 | 880 | 2,150 | 4,300 |
| Kimi K3 | 110 | 250 | 490 | | Kimi K3 | 110 | 250 | 490 |
| Kimi K2.7 Code | 1,350 | 4,630 | 9,250 | | Kimi K2.7 Code | 1,350 | 4,630 | 9,250 |
| Kimi K2.6 | 1,150 | 2,880 | 5,750 | | Kimi K2.6 | 1,150 | 2,880 | 5,750 |
| MiMo-V2.5 | 30,100 | 75,200 | 150,400 | | MiMo-V2.5 | 30,100 | 75,200 | 150,400 |