Files
team-api/relay/common/cache_hash.go
T
2026-05-10 12:21:27 +08:00

70 lines
1.9 KiB
Go

package common
import (
"crypto/sha256"
"encoding/hex"
"encoding/json"
"sort"
"strings"
)
// excludeCacheFields are request body fields that should be excluded from cache hash
// because they vary between requests but don't affect the model's output.
var excludeCacheFields = map[string]bool{
"stream": true,
"seed": true,
"user": true,
"request_id": true,
"top_logprobs": true,
"logprobs": true,
"n": true,
"frequency_penalty": false, // include - affects output
"presence_penalty": false, // include - affects output
"temperature": false, // include - affects output
"max_tokens": false, // include - affects output
"max_completion_tokens": false,
}
// ComputeCacheHash produces a deterministic SHA-256 hash from a normalized request body.
// It removes non-deterministic fields (stream, seed, user, request_id, top_logprobs, logprobs, n)
// and sorts JSON keys for consistent hashing.
func ComputeCacheHash(body []byte, modelName string) string {
var raw map[string]json.RawMessage
if err := json.Unmarshal(body, &raw); err != nil {
// Fallback: hash raw body + model name
h := sha256.New()
h.Write([]byte(modelName))
h.Write(body)
return hex.EncodeToString(h.Sum(nil))
}
// Remove excluded fields
for field := range excludeCacheFields {
delete(raw, field)
}
// Sort keys for deterministic ordering
keys := make([]string, 0, len(raw))
for k := range raw {
keys = append(keys, k)
}
sort.Strings(keys)
// Rebuild JSON with sorted keys
var buf strings.Builder
for _, k := range keys {
if buf.Len() > 0 {
buf.WriteByte(',')
}
keyBytes, _ := json.Marshal(k)
buf.Write(keyBytes)
buf.WriteByte(':')
buf.Write(raw[k])
}
h := sha256.New()
h.Write([]byte(modelName))
h.Write([]byte(buf.String()))
return hex.EncodeToString(h.Sum(nil))
}