Add projects
This commit is contained in:
parent
2d3a9ad623
commit
8b607dd700
1802 changed files with 503346 additions and 2 deletions
|
|
@ -0,0 +1,199 @@
|
|||
package responses
|
||||
|
||||
import (
|
||||
"encoding/base64"
|
||||
"encoding/json"
|
||||
"strings"
|
||||
|
||||
sigcompat "github.com/router-for-me/CLIProxyAPI/v7/internal/signature"
|
||||
"github.com/tidwall/gjson"
|
||||
"github.com/tidwall/sjson"
|
||||
)
|
||||
|
||||
const (
|
||||
geminiResponsesCarrierPrefix = "cpa-gemini-responses-carrier-v1:"
|
||||
geminiResponsesCarrierNext = "next"
|
||||
geminiResponsesCarrierPrevious = "previous"
|
||||
geminiResponsesCarrierStandalone = "standalone"
|
||||
geminiResponsesCarrierText = "text"
|
||||
geminiResponsesCarrierFunction = "function"
|
||||
geminiResponsesCarrierAny = "any"
|
||||
|
||||
geminiResponsesCarrierDirectionField = "_cpa_reasoning_direction"
|
||||
geminiResponsesCarrierTargetField = "_cpa_reasoning_target"
|
||||
geminiResponsesCarrierSignatureField = "_cpa_reasoning_signature"
|
||||
geminiResponsesCarrierSummaryField = "_cpa_reasoning_summary"
|
||||
)
|
||||
|
||||
func encodeGeminiResponsesCarrier(rawSignature, direction, targetKind string) string {
|
||||
rawSignature = strings.TrimSpace(rawSignature)
|
||||
if rawSignature == "" {
|
||||
return ""
|
||||
}
|
||||
return geminiResponsesCarrierPrefix + direction + ":" + targetKind + ":" + base64.RawStdEncoding.EncodeToString([]byte(rawSignature))
|
||||
}
|
||||
|
||||
func decodeGeminiResponsesCarrier(rawSignature string) (signatureValue, direction, targetKind string, marked, ok bool) {
|
||||
rawSignature = strings.TrimSpace(rawSignature)
|
||||
if !strings.HasPrefix(rawSignature, geminiResponsesCarrierPrefix) {
|
||||
return rawSignature, "", "", false, true
|
||||
}
|
||||
marked = true
|
||||
if len(rawSignature) > (sigcompat.MaxGeminiThoughtSignatureLen*4/3)+1024 {
|
||||
return "", "", "", true, false
|
||||
}
|
||||
fields := strings.SplitN(strings.TrimPrefix(rawSignature, geminiResponsesCarrierPrefix), ":", 3)
|
||||
if len(fields) != 3 {
|
||||
return "", "", "", true, false
|
||||
}
|
||||
direction, targetKind = fields[0], fields[1]
|
||||
switch direction {
|
||||
case geminiResponsesCarrierNext, geminiResponsesCarrierPrevious, geminiResponsesCarrierStandalone:
|
||||
default:
|
||||
return "", "", "", true, false
|
||||
}
|
||||
switch targetKind {
|
||||
case geminiResponsesCarrierText, geminiResponsesCarrierFunction, geminiResponsesCarrierAny:
|
||||
default:
|
||||
return "", "", "", true, false
|
||||
}
|
||||
decoded, errDecode := base64.RawStdEncoding.DecodeString(fields[2])
|
||||
if errDecode != nil || len(decoded) == 0 || strings.HasPrefix(string(decoded), geminiResponsesCarrierPrefix) {
|
||||
return "", "", "", true, false
|
||||
}
|
||||
return string(decoded), direction, targetKind, true, true
|
||||
}
|
||||
|
||||
func compatibleGeminiResponsesCarrierSignature(rawSignature, targetKind string) (string, bool) {
|
||||
blockKind := sigcompat.SignatureBlockKindGeminiModelPart
|
||||
if targetKind == geminiResponsesCarrierFunction {
|
||||
blockKind = sigcompat.SignatureBlockKindGeminiFunctionCall
|
||||
}
|
||||
normalized, compatible := sigcompat.CompatibleSignatureForProviderBlock(sigcompat.SignatureProviderGemini, rawSignature, blockKind)
|
||||
if !compatible || sigcompat.IsGeminiThoughtSignatureBypass(sigcompat.SignaturePayloadWithoutProviderPrefix(normalized)) {
|
||||
return "", false
|
||||
}
|
||||
return normalized, true
|
||||
}
|
||||
|
||||
func geminiResponsesCarrierSemanticTarget(item gjson.Result) string {
|
||||
switch item.Get("type").String() {
|
||||
case "function_call", "custom_tool_call":
|
||||
return geminiResponsesCarrierFunction
|
||||
case "reasoning":
|
||||
if strings.TrimSpace(item.Get("summary.0.text").String()) != "" {
|
||||
return geminiResponsesCarrierText
|
||||
}
|
||||
}
|
||||
if _, ok := openAIResponsesAssistantVisibleText(item); ok {
|
||||
return geminiResponsesCarrierText
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func geminiResponsesCarrierMatchesAdjacent(items []gjson.Result, index int, direction, targetKind string) bool {
|
||||
step := 1
|
||||
if direction == geminiResponsesCarrierPrevious {
|
||||
step = -1
|
||||
}
|
||||
for adjacent := index + step; adjacent >= 0 && adjacent < len(items); adjacent += step {
|
||||
if kind := geminiResponsesCarrierSemanticTarget(items[adjacent]); kind != "" {
|
||||
return targetKind == geminiResponsesCarrierAny || targetKind == kind
|
||||
}
|
||||
if !isOpenAIResponsesDetachedCarrier(items[adjacent]) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
func hasInternalCarrierFields(item gjson.Result) bool {
|
||||
return item.Get(geminiResponsesCarrierDirectionField).Exists() ||
|
||||
item.Get(geminiResponsesCarrierTargetField).Exists() ||
|
||||
item.Get(geminiResponsesCarrierSignatureField).Exists() ||
|
||||
item.Get(geminiResponsesCarrierSummaryField).Exists()
|
||||
}
|
||||
|
||||
func stripGeminiResponsesCarrierMetadata(rawJSON string) ([]byte, bool) {
|
||||
var fields map[string]json.RawMessage
|
||||
if err := json.Unmarshal([]byte(rawJSON), &fields); err != nil {
|
||||
return []byte(rawJSON), false
|
||||
}
|
||||
delete(fields, geminiResponsesCarrierDirectionField)
|
||||
delete(fields, geminiResponsesCarrierTargetField)
|
||||
delete(fields, geminiResponsesCarrierSignatureField)
|
||||
delete(fields, geminiResponsesCarrierSummaryField)
|
||||
stripped, errMarshal := json.Marshal(fields)
|
||||
if errMarshal != nil {
|
||||
return []byte(rawJSON), false
|
||||
}
|
||||
return stripped, true
|
||||
}
|
||||
|
||||
func normalizeGeminiResponsesCarriers(items []gjson.Result) ([]gjson.Result, bool) {
|
||||
normalized := make([]gjson.Result, 0, len(items))
|
||||
hasValidCarrier := false
|
||||
for itemIndex, originalItem := range items {
|
||||
item := originalItem
|
||||
var itemJSON []byte
|
||||
if hasInternalCarrierFields(originalItem) {
|
||||
stripped, ok := stripGeminiResponsesCarrierMetadata(originalItem.Raw)
|
||||
if ok {
|
||||
itemJSON = stripped
|
||||
item = gjson.ParseBytes(itemJSON)
|
||||
}
|
||||
}
|
||||
if item.Get("type").String() != "reasoning" {
|
||||
normalized = append(normalized, item)
|
||||
continue
|
||||
}
|
||||
if len(itemJSON) == 0 {
|
||||
itemJSON = []byte(item.Raw)
|
||||
}
|
||||
rawSignature := strings.TrimSpace(item.Get("encrypted_content").String())
|
||||
signature, direction, targetKind, marked, ok := decodeGeminiResponsesCarrier(rawSignature)
|
||||
if !marked {
|
||||
if rawSignature != "" {
|
||||
_, hasCompatibleRawCarrier := compatibleGeminiResponsesCarrierSignature(rawSignature, geminiResponsesCarrierAny)
|
||||
hasValidCarrier = hasValidCarrier || hasCompatibleRawCarrier
|
||||
}
|
||||
normalized = append(normalized, item)
|
||||
continue
|
||||
}
|
||||
if ok {
|
||||
signature, ok = compatibleGeminiResponsesCarrierSignature(signature, targetKind)
|
||||
}
|
||||
if ok && direction != geminiResponsesCarrierStandalone {
|
||||
ok = geminiResponsesCarrierMatchesAdjacent(items, itemIndex, direction, targetKind)
|
||||
}
|
||||
isDetached := isOpenAIResponsesDetachedCarrier(item)
|
||||
hasSummary := strings.TrimSpace(item.Get("summary.0.text").String()) != ""
|
||||
validSummaryCarrier := hasSummary && ((direction == geminiResponsesCarrierStandalone && (targetKind == geminiResponsesCarrierText || targetKind == geminiResponsesCarrierAny)) || direction == geminiResponsesCarrierNext)
|
||||
if !ok || (!isDetached && !validSummaryCarrier) {
|
||||
if strings.TrimSpace(item.Get("summary.0.text").String()) == "" {
|
||||
continue
|
||||
}
|
||||
itemJSON, _ = sjson.DeleteBytes(itemJSON, "encrypted_content")
|
||||
normalized = append(normalized, gjson.ParseBytes(itemJSON))
|
||||
continue
|
||||
}
|
||||
hasValidCarrier = true
|
||||
itemJSON, _ = sjson.SetBytes(itemJSON, "encrypted_content", signature)
|
||||
itemJSON, _ = sjson.SetBytes(itemJSON, geminiResponsesCarrierDirectionField, direction)
|
||||
itemJSON, _ = sjson.SetBytes(itemJSON, geminiResponsesCarrierTargetField, targetKind)
|
||||
normalized = append(normalized, gjson.ParseBytes(itemJSON))
|
||||
}
|
||||
return normalized, hasValidCarrier
|
||||
}
|
||||
|
||||
func geminiResponsesCarrierDirection(item gjson.Result) string {
|
||||
return item.Get(geminiResponsesCarrierDirectionField).String()
|
||||
}
|
||||
|
||||
func geminiResponsesCarrierTarget(item gjson.Result) string {
|
||||
return item.Get(geminiResponsesCarrierTargetField).String()
|
||||
}
|
||||
|
||||
func isOpenAIResponsesDetachedCarrier(item gjson.Result) bool {
|
||||
return item.Get("type").String() == "reasoning" && strings.TrimSpace(item.Get("encrypted_content").String()) != "" && strings.TrimSpace(item.Get("summary.0.text").String()) == ""
|
||||
}
|
||||
Loading…
Reference in a new issue