|
|
|
|
@@ -33,6 +33,10 @@ type GeminiClient struct {
|
|
|
|
|
accountLabel string
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var NanoBananaModel = map[string]struct{}{
|
|
|
|
|
"gemini-2.5-flash-image-preview": {},
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// NewGeminiClient creates a client. Pass empty strings to auto-detect via browser cookies (not implemented in Go port).
|
|
|
|
|
func NewGeminiClient(secure1psid string, secure1psidts string, proxy string, opts ...func(*GeminiClient)) *GeminiClient {
|
|
|
|
|
c := &GeminiClient{
|
|
|
|
|
@@ -239,6 +243,14 @@ func (c *GeminiClient) GenerateContent(prompt string, files []string, model Mode
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func ensureAnyLen(slice []any, index int) []any {
|
|
|
|
|
if index < len(slice) {
|
|
|
|
|
return slice
|
|
|
|
|
}
|
|
|
|
|
gap := index + 1 - len(slice)
|
|
|
|
|
return append(slice, make([]any, gap)...)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func (c *GeminiClient) generateOnce(prompt string, files []string, model Model, gem *Gem, chat *ChatSession) (ModelOutput, error) {
|
|
|
|
|
var empty ModelOutput
|
|
|
|
|
// Build f.req
|
|
|
|
|
@@ -266,6 +278,14 @@ func (c *GeminiClient) generateOnce(prompt string, files []string, model Model,
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
inner := []any{item0, nil, item2}
|
|
|
|
|
requestedModel := strings.ToLower(model.Name)
|
|
|
|
|
if chat != nil && chat.RequestedModel() != "" {
|
|
|
|
|
requestedModel = chat.RequestedModel()
|
|
|
|
|
}
|
|
|
|
|
if _, ok := NanoBananaModel[requestedModel]; ok {
|
|
|
|
|
inner = ensureAnyLen(inner, 49)
|
|
|
|
|
inner[49] = 14
|
|
|
|
|
}
|
|
|
|
|
if gem != nil {
|
|
|
|
|
// pad with 16 nils then gem ID
|
|
|
|
|
for i := 0; i < 16; i++ {
|
|
|
|
|
@@ -674,16 +694,17 @@ func truncateForLog(s string, n int) string {
|
|
|
|
|
|
|
|
|
|
// StartChat returns a ChatSession attached to the client
|
|
|
|
|
func (c *GeminiClient) StartChat(model Model, gem *Gem, metadata []string) *ChatSession {
|
|
|
|
|
return &ChatSession{client: c, metadata: normalizeMeta(metadata), model: model, gem: gem}
|
|
|
|
|
return &ChatSession{client: c, metadata: normalizeMeta(metadata), model: model, gem: gem, requestedModel: strings.ToLower(model.Name)}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// ChatSession holds conversation metadata
|
|
|
|
|
type ChatSession struct {
|
|
|
|
|
client *GeminiClient
|
|
|
|
|
metadata []string // cid, rid, rcid
|
|
|
|
|
lastOutput *ModelOutput
|
|
|
|
|
model Model
|
|
|
|
|
gem *Gem
|
|
|
|
|
client *GeminiClient
|
|
|
|
|
metadata []string // cid, rid, rcid
|
|
|
|
|
lastOutput *ModelOutput
|
|
|
|
|
model Model
|
|
|
|
|
gem *Gem
|
|
|
|
|
requestedModel string
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func (cs *ChatSession) String() string {
|
|
|
|
|
@@ -710,6 +731,10 @@ func normalizeMeta(v []string) []string {
|
|
|
|
|
|
|
|
|
|
func (cs *ChatSession) Metadata() []string { return cs.metadata }
|
|
|
|
|
func (cs *ChatSession) SetMetadata(v []string) { cs.metadata = normalizeMeta(v) }
|
|
|
|
|
func (cs *ChatSession) RequestedModel() string { return cs.requestedModel }
|
|
|
|
|
func (cs *ChatSession) SetRequestedModel(name string) {
|
|
|
|
|
cs.requestedModel = strings.ToLower(name)
|
|
|
|
|
}
|
|
|
|
|
func (cs *ChatSession) CID() string {
|
|
|
|
|
if len(cs.metadata) > 0 {
|
|
|
|
|
return cs.metadata[0]
|
|
|
|
|
|