Skip to content

Commit

Permalink
add auto generate title, closes #134
Browse files Browse the repository at this point in the history
  • Loading branch information
juzeon committed Dec 14, 2023
1 parent 76f986c commit 9341a84
Show file tree
Hide file tree
Showing 6 changed files with 147 additions and 6 deletions.
84 changes: 79 additions & 5 deletions app_chatbot.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package main

import (
"bytes"
"context"
"encoding/json"
"errors"
Expand Down Expand Up @@ -213,15 +214,11 @@ func (a *App) askOpenAI(options AskOptions) {
return
}
slog.Info("Ask OpenAI with backend: ", "data", backend)
hClient, err := util.MakeHTTPClient(a.settings.config.Proxy, 0)
client, err := util.CreateOpenAIClient(a.settings.config.Proxy, backend.OpenaiKey, backend.OpenaiEndpoint)
if err != nil {
handleErr(err)
return
}
config := openai.DefaultConfig(backend.OpenaiKey)
config.BaseURL = backend.OpenaiEndpoint
config.HTTPClient = hClient
client := openai.NewClientWithConfig(config)
messages := util.GetOpenAIChatMessages(options.ChatContext)
slog.Info("Get chat messages", "messages", messages)
messages = append(messages, openai.ChatCompletionMessage{
Expand Down Expand Up @@ -277,3 +274,80 @@ func (a *App) AskAI(options AskOptions) {
a.askOpenAI(options)
}
}

type ConciseAnswerReq struct {
Prompt string `json:"prompt"`
Context string `json:"context"`
Backend string `json:"backend"`
}

func (a *App) GetConciseAnswer(req ConciseAnswerReq) (string, error) {
if req.Backend == "Sydney" {
cookies, err := util.ReadCookiesFile()
if err != nil {
return "", err
}
syd := sydney.NewSydney(sydney.Options{
Debug: false,
Cookies: cookies,
Proxy: a.settings.config.Proxy,
WssDomain: a.settings.config.WssDomain,
CreateConversationURL: a.settings.config.CreateConversationURL,
NoSearch: true,
GPT4Turbo: true,
})
if err != nil {
return "", err
}
conversation, err := syd.CreateConversation()
if err != nil {
return "", err
}
ch := syd.AskStream(sydney.AskStreamOptions{
StopCtx: context.Background(),
Conversation: conversation,
Prompt: req.Prompt,
WebpageContext: req.Context,
})
var result bytes.Buffer
for msg := range ch {
if msg.Type == sydney.MessageTypeError {
return "", msg.Error
}
if msg.Type != sydney.MessageTypeMessageText {
continue
}
result.WriteString(msg.Text)
}
return result.String(), nil
}
// openai backends
backend, ok := lo.Find(a.settings.config.OpenAIBackends, func(item OpenAIBackend) bool {
return item.Name == req.Backend
})
if !ok {
return "", errors.New("openai backend not found: " + req.Backend)
}
client, err := util.CreateOpenAIClient(a.settings.config.Proxy, backend.OpenaiKey, backend.OpenaiEndpoint)
if err != nil {
return "", err
}
messages := lo.Ternary(req.Context == "", []openai.ChatCompletionMessage{
{Role: "user", Content: req.Prompt},
}, []openai.ChatCompletionMessage{
{Role: "system", Content: req.Context},
{Role: "user", Content: req.Prompt},
})
resp, err := client.CreateChatCompletion(context.Background(), openai.ChatCompletionRequest{
Model: backend.OpenaiShortModel,
Messages: messages,
Temperature: 1,
})
if err != nil {
return "", err
}
if len(resp.Choices) == 0 {
return "", errors.New("openai len(choices) == 0")
}
return resp.Choices[0].Message.Content, nil
}
37 changes: 36 additions & 1 deletion frontend/src/pages/IndexPage.vue
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import {computed, onMounted, onUnmounted, ref, watch} from "vue"
import {main, sydney} from "../../wailsjs/go/models"
import {EventsEmit, EventsOff, EventsOn} from "../../wailsjs/runtime"
import {generateRandomName, shadeColor, swal} from "../helper"
import {AskAI, CountToken, GenerateImage} from "../../wailsjs/go/main/App"
import {AskAI, CountToken, GenerateImage, GetConciseAnswer} from "../../wailsjs/go/main/App"
import {AskTypeOpenAI, AskTypeSydney} from "../constants"
import Scaffold from "../components/Scaffold.vue"
import {useSettings} from "../composables"
Expand All @@ -23,6 +23,7 @@ import ChatFinishResult = main.ChatFinishResult
import UploadSydneyImageResult = main.UploadSydneyImageResult
import GenerativeImage = sydney.GenerativeImage
import GenerateImageResult = sydney.GenerateImageResult
import ConciseAnswerReq = main.ConciseAnswerReq
let theme = useTheme()
let navDrawer = ref(true)
Expand Down Expand Up @@ -105,6 +106,7 @@ let askEventMap = {
uploadedImage.value = undefined
}
lockScroll.value = false
generateTitle()
} else {
console.log('error type: ' + result.err_type)
console.log('error message: ' + result.err_msg)
Expand Down Expand Up @@ -326,6 +328,39 @@ let additionalOptionPreview = computed(() => {
'; No Search: ' + currentWorkspace.value.no_search +
'; GPT-4-Turbo: ' + currentWorkspace.value.gpt_4_turbo
})
function generateTitle() {
let workspace = currentWorkspace.value
if (!/^Chat \w+_\w+$/m.test(workspace.title)) {
return
}
let systemPrompt = '# Role: Title Generator\n' +
'## Rules:\n' +
'- Write an extremely concise subtitle for the text provided wrapped with <x-text> tag ' +
'with no more than a few words.\n' +
'- All words should be capitalized.\n' +
'- Exclude punctuation.\n' +
'- Write just the title and nothing else. No introduction to yourself. No explanation. Just the title.\n'
let req: ConciseAnswerReq
if (workspace.backend === 'Sydney') {
req = {
backend: workspace.backend,
context: '<x-text>\n' + workspace.context + '\n</x-text>',
prompt: systemPrompt,
}
} else {
req = {
backend: workspace.backend,
context: systemPrompt,
prompt: '<x-text>\n' + workspace.context + '\n</x-text>',
}
}
GetConciseAnswer(req).then(title => {
workspace.title = title
}).catch(err => {
console.log(err)
})
}
</script>

<template>
Expand Down
2 changes: 2 additions & 0 deletions frontend/wailsjs/go/main/App.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ export function FetchWebpage(arg1:string):Promise<main.FetchWebpageResult>;

export function GenerateImage(arg1:sydney.GenerativeImage):Promise<sydney.GenerateImageResult>;

export function GetConciseAnswer(arg1:main.ConciseAnswerReq):Promise<string>;

export function GetUser():Promise<string>;

export function SaveRemoteJPEGImage(arg1:string):Promise<void>;
Expand Down
4 changes: 4 additions & 0 deletions frontend/wailsjs/go/main/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@ export function GenerateImage(arg1) {
return window['go']['main']['App']['GenerateImage'](arg1);
}

export function GetConciseAnswer(arg1) {
return window['go']['main']['App']['GetConciseAnswer'](arg1);
}

export function GetUser() {
return window['go']['main']['App']['GetUser']();
}
Expand Down
16 changes: 16 additions & 0 deletions frontend/wailsjs/go/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,22 @@ export namespace main {
this.release_note = source["release_note"];
}
}
export class ConciseAnswerReq {
prompt: string;
context: string;
backend: string;

static createFrom(source: any = {}) {
return new ConciseAnswerReq(source);
}

constructor(source: any = {}) {
if ('string' === typeof source) source = JSON.parse(source);
this.prompt = source["prompt"];
this.context = source["context"];
this.backend = source["backend"];
}
}
export class OpenAIBackend {
name: string;
openai_key: string;
Expand Down
10 changes: 10 additions & 0 deletions util/chat.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,3 +55,13 @@ func GetChatMessage(chatContext string) []ChatMessage {
}
return result
}
func CreateOpenAIClient(proxy string, key string, endpoint string) (*openai.Client, error) {
hClient, err := MakeHTTPClient(proxy, 0)
if err != nil {
return nil, err
}
config := openai.DefaultConfig(key)
config.BaseURL = endpoint
config.HTTPClient = hClient
return openai.NewClientWithConfig(config), nil
}

0 comments on commit 9341a84

Please sign in to comment.