Skip to content

Commit 1487e21

Browse files
committed
feat: support http proxy
1 parent e7dfe02 commit 1487e21

File tree

7 files changed

+64
-16
lines changed

7 files changed

+64
-16
lines changed

code/config.example.yaml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,4 +15,5 @@ CERT_FILE: cert.pem
1515
KEY_FILE: key.pem
1616
# openai 地址, 一般不需要修改, 除非你有自己的反向代理
1717
API_URL: https://api.openai.com
18-
18+
# 代理设置, 例如 "http://127.0.0.1:7890", ""代表不使用代理
19+
HTTP_PROXY: ""

code/initialization/config.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ type Config struct {
2222
CertFile string
2323
KeyFile string
2424
OpenaiApiUrl string
25+
HttpProxy string
2526
}
2627

2728
func LoadConfig(cfg string) *Config {
@@ -47,6 +48,7 @@ func LoadConfig(cfg string) *Config {
4748
CertFile: getViperStringValue("CERT_FILE", "cert.pem"),
4849
KeyFile: getViperStringValue("KEY_FILE", "key.pem"),
4950
OpenaiApiUrl: getViperStringValue("API_URL", "https://api.openai.com"),
51+
HttpProxy: getViperStringValue("HTTP_PROXY", ""),
5052
}
5153

5254
return config

code/main.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ func main() {
2626
pflag.Parse()
2727
config := initialization.LoadConfig(*cfg)
2828
initialization.LoadLarkClient(*config)
29-
gpt := services.NewChatGPT(config.OpenaiApiKeys, config.OpenaiApiUrl)
29+
gpt := services.NewChatGPT(*config)
3030
handlers.InitHandlers(gpt, *config)
3131

3232
eventHandler := dispatcher.NewEventDispatcher(

code/services/gpt3.go

Lines changed: 49 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import (
77
"fmt"
88
"io/ioutil"
99
"net/http"
10+
"net/url"
11+
"start-feishubot/initialization"
1012
"start-feishubot/services/loadbalancer"
1113
"strings"
1214
"time"
@@ -49,9 +51,10 @@ type ChatGPTRequestBody struct {
4951
PresencePenalty int `json:"presence_penalty"`
5052
}
5153
type ChatGPT struct {
52-
Lb *loadbalancer.LoadBalancer
53-
ApiKey []string
54-
ApiUrl string
54+
Lb *loadbalancer.LoadBalancer
55+
ApiKey []string
56+
ApiUrl string
57+
HttpProxy string
5558
}
5659

5760
type ImageGenerationRequestBody struct {
@@ -68,8 +71,9 @@ type ImageGenerationResponseBody struct {
6871
} `json:"data"`
6972
}
7073

71-
func (gpt ChatGPT) sendRequest(url, method string,
72-
requestBody interface{}, responseBody interface{}) error {
74+
func (gpt ChatGPT) doRequest(url, method string,
75+
requestBody interface{}, responseBody interface{},
76+
client *http.Client) error {
7377
api := gpt.Lb.GetAPI()
7478
if api == nil {
7579
return errors.New("no available API")
@@ -87,7 +91,7 @@ func (gpt ChatGPT) sendRequest(url, method string,
8791

8892
req.Header.Set("Content-Type", "application/json")
8993
req.Header.Set("Authorization", "Bearer "+api.Key)
90-
client := &http.Client{Timeout: 110 * time.Second}
94+
9195
response, err := client.Do(req)
9296
if err != nil {
9397
gpt.Lb.SetAvailability(api.Key, false)
@@ -114,6 +118,33 @@ func (gpt ChatGPT) sendRequest(url, method string,
114118
return nil
115119
}
116120

121+
func (gpt ChatGPT) sendRequest(link, method string,
122+
requestBody interface{}, responseBody interface{}) error {
123+
var err error
124+
client := &http.Client{Timeout: 110 * time.Second}
125+
if gpt.HttpProxy == "" {
126+
err = gpt.doRequest(link, method, requestBody, responseBody, client)
127+
} else {
128+
//fmt.Println("using proxy: " + gpt.HttpProxy)
129+
proxyUrl, err := url.Parse(gpt.HttpProxy)
130+
if err != nil {
131+
return err
132+
}
133+
134+
transport := &http.Transport{
135+
Proxy: http.ProxyURL(proxyUrl),
136+
}
137+
proxyClient := &http.Client{
138+
Transport: transport,
139+
Timeout: 110 * time.Second,
140+
}
141+
142+
err = gpt.doRequest(link, method, requestBody, responseBody, proxyClient)
143+
}
144+
145+
return err
146+
}
147+
117148
func (gpt ChatGPT) Completions(msg []Messages) (resp Messages, err error) {
118149
requestBody := ChatGPTRequestBody{
119150
Model: engine,
@@ -128,8 +159,11 @@ func (gpt ChatGPT) Completions(msg []Messages) (resp Messages, err error) {
128159
err = gpt.sendRequest(gpt.ApiUrl+"/v1/chat/completions", "POST",
129160
requestBody, gptResponseBody)
130161

131-
if err == nil {
162+
if err == nil && len(gptResponseBody.Choices) > 0 {
132163
resp = gptResponseBody.Choices[0].Message
164+
} else {
165+
resp = Messages{}
166+
err = errors.New("openai 请求失败")
133167
}
134168
return resp, err
135169
}
@@ -165,11 +199,15 @@ func (gpt ChatGPT) GenerateOneImage(prompt string, size string) (string, error)
165199
return b64s[0], nil
166200
}
167201

168-
func NewChatGPT(apiKeys []string, apiUrl string) *ChatGPT {
202+
func NewChatGPT(config initialization.Config) *ChatGPT {
203+
apiKeys := config.OpenaiApiKeys
204+
apiUrl := config.OpenaiApiUrl
205+
httpProxy := config.HttpProxy
169206
lb := loadbalancer.NewLoadBalancer(apiKeys)
170207
return &ChatGPT{
171-
Lb: lb,
172-
ApiKey: apiKeys,
173-
ApiUrl: apiUrl,
208+
Lb: lb,
209+
ApiKey: apiKeys,
210+
ApiUrl: apiUrl,
211+
HttpProxy: httpProxy,
174212
}
175213
}

code/services/gpt3_test.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ func TestCompletions(t *testing.T) {
1414
{Role: "user", Content: "翻译这段话: The assistant messages help store prior responses. They can also be written by a developer to help give examples of desired behavior."},
1515
}
1616

17-
gpt := NewChatGPT(config.OpenaiApiKeys, config.OpenaiApiUrl)
17+
gpt := NewChatGPT(*config)
1818

1919
resp, err := gpt.Completions(msgs)
2020
if err != nil {
@@ -27,7 +27,7 @@ func TestCompletions(t *testing.T) {
2727
func TestGenerateOneImage(t *testing.T) {
2828
config := initialization.LoadConfig("../config.yaml")
2929

30-
gpt := NewChatGPT(config.OpenaiApiKeys, config.OpenaiApiUrl)
30+
gpt := NewChatGPT(*config)
3131
prompt := "a red apple"
3232
size := "256x256"
3333

entrypoint.sh

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ USE_HTTPS=${USE_HTTPS:-""}
1717
CERT_FILE=${CERT_FILE:-""}
1818
KEY_FILE=${KEY_FILE:-""}
1919
API_URL=${API_URL:-""}
20+
HTTP_PROXY=${HTTP_PROXY:-""}
2021
CONFIG_PATH=${CONFIG_PATH:-"config.yaml"}
2122

2223

@@ -84,6 +85,10 @@ if [ "$API_URL" != "" ] ; then
8485
sed -i "17c API_URL: $API_URL" $CONFIG_PATH
8586
fi
8687

88+
if [ "$HTTP_PROXY" != "" ] ; then
89+
sed -i "19c HTTP_PROXY: $HTTP_PROXY" $CONFIG_PATH
90+
fi
91+
8792
echo -e "\033[32m[Success] Configuration file has been generated!\033[0m"
8893

8994
/dist/feishu_chatgpt

readme.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -207,7 +207,8 @@ docker run -d --name feishu-chatgpt -p 9000:9000 \
207207
--env APP_VERIFICATION_TOKEN=xxx \
208208
--env BOT_NAME=chatGpt \
209209
--env OPENAI_KEY="sk-xxx1,sk-xxx2,sk-xxx3" \
210-
--env API_URL=https://api.openai.com \
210+
--env API_URL="https://api.openai.com" \
211+
--env HTTP_PROXY="http://host.docker.internal:7890" \
211212
feishu-chatgpt:latest
212213
```
213214

@@ -226,6 +227,7 @@ docker run -d --restart=always --name feishu-chatgpt2 -p 9000:9000 -v /etc/local
226227
--env BOT_NAME=chatGpt \
227228
--env OPENAI_KEY="sk-xxx1,sk-xxx2,sk-xxx3" \
228229
--env API_URL=https://api.openai.com \
230+
--env HTTP_PROXY="" \
229231
dockerproxy.com/leizhenpeng/feishu-chatgpt:latest
230232
```
231233

0 commit comments

Comments
 (0)