package telegram import ( "context" "fmt" "log/slog" "strconv" tele "gopkg.in/telebot.v3" ) // Notifier 告警通知器 type Notifier struct { bot *tele.Bot chatID string } // NewNotifier 创建通知器 func NewNotifier(bot *tele.Bot, chatID string) *Notifier { return &Notifier{ bot: bot, chatID: chatID, } } // SendAlert 发送告警 func (n *Notifier) SendAlert(ctx context.Context, alive, dead, total int, alivePercent float64) { if n.chatID == "" { slog.Warn("notify_chat_id not configured, skipping alert") return } chatID, err := strconv.ParseInt(n.chatID, 10, 64) if err != nil { slog.Error("invalid chat_id", "chat_id", n.chatID, "error", err) return } msg := fmt.Sprintf(`🚨 *代理池告警* 存活率低于阈值! *统计:* • 存活: %d (%.1f%%) • 死亡: %d • 总数: %d 请及时补充代理或检查网络状况。`, alive, alivePercent, dead, total) chat, err := n.bot.ChatByID(chatID) if err != nil { slog.Error("failed to get chat", "chat_id", n.chatID, "error", err) return } _, err = n.bot.Send(chat, msg, &tele.SendOptions{ParseMode: tele.ModeMarkdown}) if err != nil { slog.Error("failed to send alert", "error", err) return } slog.Info("alert sent", "chat_id", n.chatID, "alive_percent", alivePercent) } // SendMessage 发送普通消息 func (n *Notifier) SendMessage(ctx context.Context, message string) error { if n.chatID == "" { return nil } chatID, err := strconv.ParseInt(n.chatID, 10, 64) if err != nil { return err } chat, err := n.bot.ChatByID(chatID) if err != nil { return err } _, err = n.bot.Send(chat, message, &tele.SendOptions{ParseMode: tele.ModeMarkdown}) return err }