Files
Cursor AgentandHoshinoAya c8ba5f6516 fix: 改进 notifier 包的错误处理和连接复用
- notifier.go: Send 使用 errors.Join 收集所有通道的错误,不再丢弃中间错误
- bark.go/gotify.go/webhook.go: 响应体在关闭前先 drain,确保 HTTP 连接可复用

Co-authored-by: HoshinoAya <HoshinoDesu@users.noreply.github.com>
2026-03-06 06:39:00 +00:00

76 lines
1.5 KiB
Go

package notifier
import (
"bytes"
"encoding/json"
"fmt"
"io"
"net/http"
"github.com/CyberPigeon/internal/config"
)
// GotifyChannel Gotify 通道
type GotifyChannel struct {
cfg config.ChannelConfig
client *http.Client
}
// NewGotifyChannel 创建 Gotify 通道
func NewGotifyChannel(cfg config.ChannelConfig) (*GotifyChannel, error) {
if cfg.Endpoint == "" || cfg.Token == "" {
return nil, fmt.Errorf("Gotify 配置不完整")
}
if cfg.Priority == 0 {
cfg.Priority = 5
}
return &GotifyChannel{cfg: cfg, client: newHTTPClient(cfg)}, nil
}
// Type 返回通道类型
func (g *GotifyChannel) Type() string {
return "gotify"
}
// Send 发送 Gotify 通知
func (g *GotifyChannel) Send(msg Message) error {
url := fmt.Sprintf("%s/message", g.cfg.Endpoint)
title := msg.From
if title == "" {
title = "未知号码"
}
payload := map[string]interface{}{
"title": title,
"message": msg.String(),
"priority": g.cfg.Priority,
}
data, err := json.Marshal(payload)
if err != nil {
return err
}
req, err := http.NewRequest(http.MethodPost, url, bytes.NewReader(data))
if err != nil {
return err
}
req.Header.Set("Content-Type", "application/json")
req.Header.Set("X-Gotify-Key", g.cfg.Token)
resp, err := g.client.Do(req)
if err != nil {
return err
}
defer func() {
io.Copy(io.Discard, resp.Body)
resp.Body.Close()
}()
if resp.StatusCode != http.StatusOK {
return fmt.Errorf("Gotify 返回错误状态: %d", resp.StatusCode)
}
return nil
}