Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
phsl
/
new-api
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Snippets
Members
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit
e69f4199
authored
Jun 21, 2025
by
t0ng7u
Browse files
Options
Browse Files
Download
Plain Diff
Merge remote-tracking branch 'origin/alpha' into alpha
parents
8da8c2f5
7de52a0c
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
70 additions
and
30 deletions
+70
-30
controller/channel.go
+0
-7
relay/channel/gemini/relay-gemini.go
+24
-20
relay/gemini_handler.go
+46
-3
No files found.
controller/channel.go
View file @
e69f4199
...
@@ -134,13 +134,6 @@ func FetchUpstreamModels(c *gin.Context) {
...
@@ -134,13 +134,6 @@ func FetchUpstreamModels(c *gin.Context) {
return
return
}
}
//if channel.Type != common.ChannelTypeOpenAI {
// c.JSON(http.StatusOK, gin.H{
// "success": false,
// "message": "仅支持 OpenAI 类型渠道",
// })
// return
//}
baseURL
:=
common
.
ChannelBaseURLs
[
channel
.
Type
]
baseURL
:=
common
.
ChannelBaseURLs
[
channel
.
Type
]
if
channel
.
GetBaseURL
()
!=
""
{
if
channel
.
GetBaseURL
()
!=
""
{
baseURL
=
channel
.
GetBaseURL
()
baseURL
=
channel
.
GetBaseURL
()
...
...
relay/channel/gemini/relay-gemini.go
View file @
e69f4199
...
@@ -78,26 +78,7 @@ func clampThinkingBudget(modelName string, budget int) int {
...
@@ -78,26 +78,7 @@ func clampThinkingBudget(modelName string, budget int) int {
return
budget
return
budget
}
}
// Setting safety to the lowest possible values since Gemini is already powerless enough
func
ThinkingAdaptor
(
geminiRequest
*
GeminiChatRequest
,
info
*
relaycommon
.
RelayInfo
)
{
func
CovertGemini2OpenAI
(
textRequest
dto
.
GeneralOpenAIRequest
,
info
*
relaycommon
.
RelayInfo
)
(
*
GeminiChatRequest
,
error
)
{
geminiRequest
:=
GeminiChatRequest
{
Contents
:
make
([]
GeminiChatContent
,
0
,
len
(
textRequest
.
Messages
)),
GenerationConfig
:
GeminiChatGenerationConfig
{
Temperature
:
textRequest
.
Temperature
,
TopP
:
textRequest
.
TopP
,
MaxOutputTokens
:
textRequest
.
MaxTokens
,
Seed
:
int64
(
textRequest
.
Seed
),
},
}
if
model_setting
.
IsGeminiModelSupportImagine
(
info
.
UpstreamModelName
)
{
geminiRequest
.
GenerationConfig
.
ResponseModalities
=
[]
string
{
"TEXT"
,
"IMAGE"
,
}
}
if
model_setting
.
GetGeminiSettings
()
.
ThinkingAdapterEnabled
{
if
model_setting
.
GetGeminiSettings
()
.
ThinkingAdapterEnabled
{
modelName
:=
info
.
UpstreamModelName
modelName
:=
info
.
UpstreamModelName
isNew25Pro
:=
strings
.
HasPrefix
(
modelName
,
"gemini-2.5-pro"
)
&&
isNew25Pro
:=
strings
.
HasPrefix
(
modelName
,
"gemini-2.5-pro"
)
&&
...
@@ -150,6 +131,29 @@ func CovertGemini2OpenAI(textRequest dto.GeneralOpenAIRequest, info *relaycommon
...
@@ -150,6 +131,29 @@ func CovertGemini2OpenAI(textRequest dto.GeneralOpenAIRequest, info *relaycommon
}
}
}
}
}
}
}
// Setting safety to the lowest possible values since Gemini is already powerless enough
func
CovertGemini2OpenAI
(
textRequest
dto
.
GeneralOpenAIRequest
,
info
*
relaycommon
.
RelayInfo
)
(
*
GeminiChatRequest
,
error
)
{
geminiRequest
:=
GeminiChatRequest
{
Contents
:
make
([]
GeminiChatContent
,
0
,
len
(
textRequest
.
Messages
)),
GenerationConfig
:
GeminiChatGenerationConfig
{
Temperature
:
textRequest
.
Temperature
,
TopP
:
textRequest
.
TopP
,
MaxOutputTokens
:
textRequest
.
MaxTokens
,
Seed
:
int64
(
textRequest
.
Seed
),
},
}
if
model_setting
.
IsGeminiModelSupportImagine
(
info
.
UpstreamModelName
)
{
geminiRequest
.
GenerationConfig
.
ResponseModalities
=
[]
string
{
"TEXT"
,
"IMAGE"
,
}
}
ThinkingAdaptor
(
&
geminiRequest
,
info
)
safetySettings
:=
make
([]
GeminiChatSafetySettings
,
0
,
len
(
SafetySettingList
))
safetySettings
:=
make
([]
GeminiChatSafetySettings
,
0
,
len
(
SafetySettingList
))
for
_
,
category
:=
range
SafetySettingList
{
for
_
,
category
:=
range
SafetySettingList
{
...
...
relay/gemini_handler.go
View file @
e69f4199
...
@@ -13,6 +13,7 @@ import (
...
@@ -13,6 +13,7 @@ import (
"one-api/relay/helper"
"one-api/relay/helper"
"one-api/service"
"one-api/service"
"one-api/setting"
"one-api/setting"
"one-api/setting/model_setting"
"strings"
"strings"
"github.com/gin-gonic/gin"
"github.com/gin-gonic/gin"
...
@@ -76,6 +77,33 @@ func getGeminiInputTokens(req *gemini.GeminiChatRequest, info *relaycommon.Relay
...
@@ -76,6 +77,33 @@ func getGeminiInputTokens(req *gemini.GeminiChatRequest, info *relaycommon.Relay
return
inputTokens
return
inputTokens
}
}
func
isNoThinkingRequest
(
req
*
gemini
.
GeminiChatRequest
)
bool
{
if
req
.
GenerationConfig
.
ThinkingConfig
!=
nil
&&
req
.
GenerationConfig
.
ThinkingConfig
.
ThinkingBudget
!=
nil
{
return
*
req
.
GenerationConfig
.
ThinkingConfig
.
ThinkingBudget
<=
0
}
return
false
}
func
trimModelThinking
(
modelName
string
)
string
{
// 去除模型名称中的 -nothinking 后缀
if
strings
.
HasSuffix
(
modelName
,
"-nothinking"
)
{
return
strings
.
TrimSuffix
(
modelName
,
"-nothinking"
)
}
// 去除模型名称中的 -thinking 后缀
if
strings
.
HasSuffix
(
modelName
,
"-thinking"
)
{
return
strings
.
TrimSuffix
(
modelName
,
"-thinking"
)
}
// 去除模型名称中的 -thinking-number
if
strings
.
Contains
(
modelName
,
"-thinking-"
)
{
parts
:=
strings
.
Split
(
modelName
,
"-thinking-"
)
if
len
(
parts
)
>
1
{
return
parts
[
0
]
+
"-thinking"
}
}
return
modelName
}
func
GeminiHelper
(
c
*
gin
.
Context
)
(
openaiErr
*
dto
.
OpenAIErrorWithStatusCode
)
{
func
GeminiHelper
(
c
*
gin
.
Context
)
(
openaiErr
*
dto
.
OpenAIErrorWithStatusCode
)
{
req
,
err
:=
getAndValidateGeminiRequest
(
c
)
req
,
err
:=
getAndValidateGeminiRequest
(
c
)
if
err
!=
nil
{
if
err
!=
nil
{
...
@@ -107,12 +135,27 @@ func GeminiHelper(c *gin.Context) (openaiErr *dto.OpenAIErrorWithStatusCode) {
...
@@ -107,12 +135,27 @@ func GeminiHelper(c *gin.Context) (openaiErr *dto.OpenAIErrorWithStatusCode) {
relayInfo
.
SetPromptTokens
(
promptTokens
)
relayInfo
.
SetPromptTokens
(
promptTokens
)
}
else
{
}
else
{
promptTokens
:=
getGeminiInputTokens
(
req
,
relayInfo
)
promptTokens
:=
getGeminiInputTokens
(
req
,
relayInfo
)
if
err
!=
nil
{
return
service
.
OpenAIErrorWrapperLocal
(
err
,
"count_input_tokens_error"
,
http
.
StatusBadRequest
)
}
c
.
Set
(
"prompt_tokens"
,
promptTokens
)
c
.
Set
(
"prompt_tokens"
,
promptTokens
)
}
}
if
model_setting
.
GetGeminiSettings
()
.
ThinkingAdapterEnabled
{
if
isNoThinkingRequest
(
req
)
{
// check is thinking
if
!
strings
.
Contains
(
relayInfo
.
OriginModelName
,
"-nothinking"
)
{
// try to get no thinking model price
noThinkingModelName
:=
relayInfo
.
OriginModelName
+
"-nothinking"
containPrice
:=
helper
.
ContainPriceOrRatio
(
noThinkingModelName
)
if
containPrice
{
relayInfo
.
OriginModelName
=
noThinkingModelName
relayInfo
.
UpstreamModelName
=
noThinkingModelName
}
}
}
if
req
.
GenerationConfig
.
ThinkingConfig
==
nil
{
gemini
.
ThinkingAdaptor
(
req
,
relayInfo
)
}
}
priceData
,
err
:=
helper
.
ModelPriceHelper
(
c
,
relayInfo
,
relayInfo
.
PromptTokens
,
int
(
req
.
GenerationConfig
.
MaxOutputTokens
))
priceData
,
err
:=
helper
.
ModelPriceHelper
(
c
,
relayInfo
,
relayInfo
.
PromptTokens
,
int
(
req
.
GenerationConfig
.
MaxOutputTokens
))
if
err
!=
nil
{
if
err
!=
nil
{
return
service
.
OpenAIErrorWrapperLocal
(
err
,
"model_price_error"
,
http
.
StatusInternalServerError
)
return
service
.
OpenAIErrorWrapperLocal
(
err
,
"model_price_error"
,
http
.
StatusInternalServerError
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment