I’m using chatgpt from kakoune like this, I wrote this little program:
package main
import (
"bufio"
"context"
"fmt"
"io"
"log"
"os"
"strconv"
openai "github.com/sashabaranov/go-openai"
)
func main() {
client := openai.NewClient(os.Getenv("OPENAI_API_KEY"))
rawMessageCap := os.Getenv("MESSAGE_CAP")
if rawMessageCap == "" {
rawMessageCap = "50"
}
messageCap, err := strconv.Atoi(rawMessageCap)
if err != nil {
log.Fatal("Failed to parse message cap:", err)
}
req := openai.ChatCompletionRequest{
Stream: true,
Model: openai.GPT3Dot5Turbo,
Messages: []openai.ChatCompletionMessage{
{
Role: openai.ChatMessageRoleSystem,
Content: "you are a helpful chatbot",
},
},
}
infifo := os.Args[1]
outfifo := os.Args[2]
inputFile, err := os.OpenFile(infifo, os.O_RDWR, os.ModeNamedPipe)
if err != nil {
log.Fatal("Failed to open input FIFO:", err)
}
defer inputFile.Close()
outputFile, err := os.OpenFile(outfifo, os.O_RDWR, os.ModeNamedPipe)
if err != nil {
log.Fatal("Failed to open output FIFO:", err)
}
defer outputFile.Close()
s := bufio.NewScanner(inputFile)
for s.Scan() {
req.Messages = append(req.Messages, openai.ChatCompletionMessage{
Role: openai.ChatMessageRoleUser,
Content: s.Text(),
})
stream, err := client.CreateChatCompletionStream(context.Background(), req)
if err != nil {
fmt.Printf("ChatCompletion error: %v\n", err)
continue
}
msg := openai.ChatCompletionMessage{Role: openai.ChatMessageRoleAssistant}
BUFFERING:
for {
resp, err := stream.Recv()
if err != nil {
if err == io.EOF {
outputFile.WriteString("\n")
break BUFFERING
}
fmt.Printf("ChatCompletion error: %v\n", err)
}
outputFile.WriteString(fmt.Sprintf("%s", resp.Choices[0].Delta.Content))
msg.Content = msg.Content + resp.Choices[0].Delta.Content
}
req.Messages = append(req.Messages, msg)
ran := len(req.Messages) - messageCap
if ran < 0 {
ran = 0
}
req.Messages = req.Messages[ran:]
}
}
and added this to my kakrc:
define-command opengpt %{
eval -try-client tools %{
edit -fifo ~/chatout chat
}
}
define-command gpt -override -params 0.. %{
evaluate-commands %sh{
if [ $(($(printf %s "${kak_selection}" | wc -m))) -gt 1 ]; then
echo "$@ " "$(printf '%s' "${kak_selection}" | tr '\n' ' ')" > ~/chatin
else
echo "$@" > ~/chatin
fi
}
eval -try-client tools %{
buffer chat
}
}
map global user i ": gpt "
I run the program like this
OPENAI_API_KEY=XXX <path_to_program> ~/chatin ~/chatout
chatin and chatout are some fifos that live in my home dir and thats it, a little hardcoded but this allows me to have actual conversations, and easily pass the content of my selection as additional input