diff options
-rw-r--r-- | bot.go | 8 | ||||
-rw-r--r-- | config/config.go | 1 | ||||
-rw-r--r-- | llm.go | 11 | ||||
-rw-r--r-- | main.go | 2 | ||||
-rw-r--r-- | tools.go | 2 | ||||
-rw-r--r-- | tui.go | 27 |
6 files changed, 40 insertions, 11 deletions
@@ -39,7 +39,7 @@ var ( chunkParser ChunkParser defaultLCPProps = map[string]float32{ "temperature": 0.8, - "dry_multiplier": 0.6, + "dry_multiplier": 0.0, "min_p": 0.05, "n_predict": -1.0, } @@ -108,6 +108,7 @@ func sendMsgToLLM(body io.Reader) { } // starts with -> data: line = line[6:] + logger.Info("debugging resp", "line", string(line)) content, stop, err := chunkParser.ParseChunk(line) if err != nil { logger.Error("error parsing response body", "error", err, "line", string(line), "url", cfg.CurrentAPI) @@ -185,6 +186,10 @@ func chatRound(userMsg, role string, tv *tview.TextView, regen bool) { fmt.Fprintf(tv, "(%d) ", len(chatBody.Messages)) fmt.Fprint(tv, roleToIcon(cfg.AssistantRole)) fmt.Fprint(tv, "\n") + if cfg.ThinkUse && !strings.Contains(cfg.CurrentAPI, "v1") { + // fmt.Fprint(tv, "<think>") + chunkChan <- "<think>" + } } respText := strings.Builder{} out: @@ -201,6 +206,7 @@ out: } } botRespMode = false + // how can previous messages be affected? chatBody.Messages = append(chatBody.Messages, models.RoleMsg{ Role: cfg.AssistantRole, Content: respText.String(), }) diff --git a/config/config.go b/config/config.go index ddb0d91..f26a82e 100644 --- a/config/config.go +++ b/config/config.go @@ -17,6 +17,7 @@ type Config struct { UserRole string `toml:"UserRole"` ToolRole string `toml:"ToolRole"` ToolUse bool `toml:"ToolUse"` + ThinkUse bool `toml:"ThinkUse"` AssistantRole string `toml:"AssistantRole"` SysDir string `toml:"SysDir"` ChunkLimit uint32 `toml:"ChunkLimit"` @@ -30,9 +30,6 @@ type OpenAIer struct { func (lcp LlamaCPPeer) FormMsg(msg, role string) (io.Reader, error) { if msg != "" { // otherwise let the bot continue - // if role == cfg.UserRole { - // msg = msg + cfg.AssistantRole + ":" - // } newMsg := models.RoleMsg{Role: role, Content: msg} chatBody.Messages = append(chatBody.Messages, newMsg) // if rag @@ -51,11 +48,17 @@ func (lcp LlamaCPPeer) FormMsg(msg, role string) (io.Reader, error) { messages[i] = m.ToPrompt() } prompt := strings.Join(messages, "\n") + // strings builder? if cfg.ToolUse && msg != "" { prompt += "\n" + cfg.ToolRole + ":\n" + toolSysMsg } botMsgStart := "\n" + cfg.AssistantRole + ":\n" - payload := models.NewLCPReq(prompt+botMsgStart, cfg, defaultLCPProps) + prompt += botMsgStart + // if cfg.ThinkUse && msg != "" && !cfg.ToolUse { + if cfg.ThinkUse && !cfg.ToolUse { + prompt += "<think>" + } + payload := models.NewLCPReq(prompt, cfg, defaultLCPProps) data, err := json.Marshal(payload) if err != nil { logger.Error("failed to form a msg", "error", err) @@ -12,7 +12,7 @@ var ( botRespMode = false editMode = false selectedIndex = int(-1) - indexLine = "F12 to show keys help | bot resp mode: %v (F6) | char: %s (ctrl+s) | chat: %s (F1) | RAGEnabled: %v (F11) | toolUseAdviced: %v (ctrl+k) | model: %s (ctrl+l)\nAPI_URL: %s (ctrl+v)" + indexLine = "F12 to show keys help | bot resp mode: %v (F6) | char: %s (ctrl+s) | chat: %s (F1) | RAGEnabled: %v (F11) | toolUseAdviced: %v (ctrl+k) | model: %s (ctrl+l)\nAPI_URL: %s (ctrl+v) | ThinkUse: %v (ctrl+p)" focusSwitcher = map[tview.Primitive]tview.Primitive{} ) @@ -12,7 +12,7 @@ var ( toolCallRE = regexp.MustCompile(`__tool_call__\s*([\s\S]*?)__tool_call__`) quotesRE = regexp.MustCompile(`(".*?")`) starRE = regexp.MustCompile(`(\*.*?\*)`) - thinkRE = regexp.MustCompile(`(<think>.*?</think>)`) + thinkRE = regexp.MustCompile(`(<think>\s*([\s\S]*?)</think>)`) codeBlockRE = regexp.MustCompile(`(?s)\x60{3}(?:.*?)\n(.*?)\n\s*\x60{3}\s*`) basicSysMsg = `Large Language Model that helps user with any of his requests.` toolSysMsg = `You can do functions call if needed. @@ -65,7 +65,7 @@ var ( [yellow]Ctrl+t[white]: remove thinking (<think>) and tool messages from context (delete from chat) [yellow]Ctrl+l[white]: update connected model name (llamacpp) [yellow]Ctrl+k[white]: switch tool use (recommend tool use to llm after user msg) -[yellow]Ctrl+i[white]: if chat agent is char.png will show the image; then any key to return +[yellow]Ctrl+j[white]: if chat agent is char.png will show the image; then any key to return Press Enter to go back ` @@ -97,6 +97,10 @@ func colorText() { var codeBlocks []string placeholder := "__CODE_BLOCK_%d__" counter := 0 + // thinking + var thinkBlocks []string + placeholderThink := "__THINK_BLOCK_%d__" + counterThink := 0 // Replace code blocks with placeholders and store their styled versions text = codeBlockRE.ReplaceAllStringFunc(text, func(match string) string { // Style the code block and store it @@ -107,19 +111,31 @@ func colorText() { counter++ return id }) + text = thinkRE.ReplaceAllStringFunc(text, func(match string) string { + // Style the code block and store it + styled := fmt.Sprintf("[red::i]%s[-:-:-]", match) + thinkBlocks = append(codeBlocks, styled) + // Generate a unique placeholder (e.g., "__CODE_BLOCK_0__") + id := fmt.Sprintf(placeholderThink, counterThink) + counter++ + return id + }) // Step 2: Apply other regex styles to the non-code parts text = quotesRE.ReplaceAllString(text, `[orange::-]$1[-:-:-]`) text = starRE.ReplaceAllString(text, `[turquoise::i]$1[-:-:-]`) - text = thinkRE.ReplaceAllString(text, `[turquoise::i]$1[-:-:-]`) + // text = thinkRE.ReplaceAllString(text, `[yellow::i]$1[-:-:-]`) // Step 3: Restore the styled code blocks from placeholders for i, cb := range codeBlocks { text = strings.Replace(text, fmt.Sprintf(placeholder, i), cb, 1) } + for i, tb := range thinkBlocks { + text = strings.Replace(text, fmt.Sprintf(placeholderThink, i), tb, 1) + } textView.SetText(text) } func updateStatusLine() { - position.SetText(fmt.Sprintf(indexLine, botRespMode, cfg.AssistantRole, activeChatName, cfg.RAGEnabled, cfg.ToolUse, currentModel, cfg.CurrentAPI)) + position.SetText(fmt.Sprintf(indexLine, botRespMode, cfg.AssistantRole, activeChatName, cfg.RAGEnabled, cfg.ToolUse, currentModel, cfg.CurrentAPI, cfg.ThinkUse)) } func initSysCards() ([]string, error) { @@ -167,6 +183,9 @@ func startNewChat() { func makePropsForm(props map[string]float32) *tview.Form { form := tview.NewForm(). AddTextView("Notes", "Props for llamacpp completion call", 40, 2, true, false). + AddCheckbox("Insert <think> (/completion only)", cfg.ThinkUse, func(checked bool) { + cfg.ThinkUse = checked + }). AddButton("Quit", func() { pages.RemovePage(propsPage) }) @@ -588,7 +607,7 @@ func init() { updateStatusLine() return nil } - if event.Key() == tcell.KeyCtrlI { + if event.Key() == tcell.KeyCtrlJ { // show image loadImage() pages.AddPage(imgPage, imgView, true, true) |