mirror of
https://github.com/cline/cline.git
synced 2026-10-30 18:12:49 +08:00
feat: Add extended thinking for LiteLLM provider (#2615)
* feat: add extended thinking slider to LiteLLM provider Signed-off-by: Jorge García Rey <jorgegar@inditex.com> * feat: add changeset Signed-off-by: Jorge García Rey <jorgegar@inditex.com> * fix: format Signed-off-by: Jorge García Rey <jorgegar@inditex.com> --------- Signed-off-by: Jorge García Rey <jorgegar@inditex.com>
This commit is contained in:
@@ -0,0 +1,5 @@
|
||||
---
|
||||
"claude-dev": minor
|
||||
---
|
||||
|
||||
Add Enable extended thinking for LiteLLM provider
|
||||
@@ -59,10 +59,16 @@ export class LiteLlmHandler implements ApiHandler {
|
||||
}
|
||||
const modelId = this.options.liteLlmModelId || liteLlmDefaultModelId
|
||||
const isOminiModel = modelId.includes("o1-mini") || modelId.includes("o3-mini")
|
||||
|
||||
// Configuration for extended thinking
|
||||
const budgetTokens = this.options.thinkingBudgetTokens || 0
|
||||
const reasoningOn = budgetTokens !== 0 ? true : false
|
||||
const thinkingConfig = reasoningOn ? { type: "enabled", budget_tokens: budgetTokens } : undefined
|
||||
|
||||
let temperature: number | undefined = 0
|
||||
|
||||
if (isOminiModel) {
|
||||
temperature = undefined // does not support temperature
|
||||
if (isOminiModel && reasoningOn) {
|
||||
temperature = undefined // Thinking mode doesn't support temperature
|
||||
}
|
||||
|
||||
const stream = await this.client.chat.completions.create({
|
||||
@@ -71,6 +77,7 @@ export class LiteLlmHandler implements ApiHandler {
|
||||
temperature,
|
||||
stream: true,
|
||||
stream_options: { include_usage: true },
|
||||
...(thinkingConfig && { thinking: thinkingConfig }), // Add thinking configuration when applicable
|
||||
})
|
||||
|
||||
const inputCost = (await this.calculateCost(1e6, 0)) || 0
|
||||
@@ -78,6 +85,8 @@ export class LiteLlmHandler implements ApiHandler {
|
||||
|
||||
for await (const chunk of stream) {
|
||||
const delta = chunk.choices[0]?.delta
|
||||
|
||||
// Handle normal text content
|
||||
if (delta?.content) {
|
||||
yield {
|
||||
type: "text",
|
||||
@@ -85,6 +94,20 @@ export class LiteLlmHandler implements ApiHandler {
|
||||
}
|
||||
}
|
||||
|
||||
// Handle reasoning events (thinking)
|
||||
// Thinking is not in the standard types but may be in the response
|
||||
interface ThinkingDelta {
|
||||
thinking?: string
|
||||
}
|
||||
|
||||
if ((delta as ThinkingDelta)?.thinking) {
|
||||
yield {
|
||||
type: "reasoning",
|
||||
reasoning: (delta as ThinkingDelta).thinking || "",
|
||||
}
|
||||
}
|
||||
|
||||
// Handle token usage information
|
||||
if (chunk.usage) {
|
||||
const totalCost =
|
||||
(inputCost * chunk.usage.prompt_tokens) / 1e6 + (outputCost * chunk.usage.completion_tokens) / 1e6
|
||||
|
||||
@@ -1205,6 +1205,24 @@ const ApiOptions = ({ showModelOptions, apiErrorMessage, modelIdErrorMessage, is
|
||||
placeholder={"e.g. gpt-4"}>
|
||||
<span style={{ fontWeight: 500 }}>Model ID</span>
|
||||
</VSCodeTextField>
|
||||
|
||||
<>
|
||||
<ThinkingBudgetSlider apiConfiguration={apiConfiguration} setApiConfiguration={setApiConfiguration} />
|
||||
<p
|
||||
style={{
|
||||
fontSize: "12px",
|
||||
marginTop: "5px",
|
||||
color: "var(--vscode-charts-green)",
|
||||
}}>
|
||||
Extended thinking is available for models as Sonnet-3-7, o3-mini, Deepseek R1, etc. More info on{" "}
|
||||
<VSCodeLink
|
||||
href="https://docs.litellm.ai/docs/reasoning_content"
|
||||
style={{ display: "inline", fontSize: "inherit" }}>
|
||||
thinking mode configuration
|
||||
</VSCodeLink>
|
||||
</p>
|
||||
</>
|
||||
|
||||
<p
|
||||
style={{
|
||||
fontSize: "12px",
|
||||
|
||||
@@ -123,11 +123,12 @@ const ThinkingBudgetSlider = ({ apiConfiguration, setApiConfiguration }: Thinkin
|
||||
{isEnabled && (
|
||||
<>
|
||||
<LabelContainer>
|
||||
<Label>
|
||||
<Label htmlFor="thinking-budget-slider">
|
||||
<strong>Budget:</strong> {localValue.toLocaleString()} tokens
|
||||
</Label>
|
||||
</LabelContainer>
|
||||
<RangeInput
|
||||
id="thinking-budget-slider"
|
||||
type="range"
|
||||
min={MIN_VALID_TOKENS}
|
||||
max={maxSliderValue}
|
||||
@@ -139,9 +140,16 @@ const ThinkingBudgetSlider = ({ apiConfiguration, setApiConfiguration }: Thinkin
|
||||
$value={localValue}
|
||||
$min={MIN_VALID_TOKENS}
|
||||
$max={maxSliderValue}
|
||||
aria-label={`Thinking budget: ${localValue.toLocaleString()} tokens`}
|
||||
aria-valuemin={MIN_VALID_TOKENS}
|
||||
aria-valuemax={maxSliderValue}
|
||||
aria-valuenow={localValue}
|
||||
aria-describedby="thinking-budget-description"
|
||||
/>
|
||||
|
||||
<Description>Higher budgets may allow you to achieve more comprehensive and nuanced reasoning</Description>
|
||||
<Description id="thinking-budget-description">
|
||||
Higher budgets may allow you to achieve more comprehensive and nuanced reasoning
|
||||
</Description>
|
||||
</>
|
||||
)}
|
||||
</Container>
|
||||
|
||||
Reference in New Issue
Block a user