mirror of
https://github.com/nikoksr/notify.git
synced 2025-02-05 13:05:16 +02:00
113 lines
3.0 KiB
Go
113 lines
3.0 KiB
Go
package lark
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"net/http"
|
|
"time"
|
|
|
|
"github.com/go-lark/lark"
|
|
|
|
"github.com/nikoksr/notify"
|
|
)
|
|
|
|
// CustomAppService is a Lark notify service using a Lark custom app.
|
|
type CustomAppService struct {
|
|
receiveIDs []*ReceiverID
|
|
cli sendToer
|
|
}
|
|
|
|
// Compile time check that larkCustomAppService implements notify.Notifer.
|
|
var _ notify.Notifier = &CustomAppService{}
|
|
|
|
// NewCustomAppService returns a new instance of a Lark notify service using a
|
|
// Lark custom app.
|
|
func NewCustomAppService(appID, appSecret string) *CustomAppService {
|
|
bot := lark.NewChatBot(appID, appSecret)
|
|
|
|
// We need to set the bot to use Lark's open.larksuite.com domain instead of
|
|
// the default open.feishu.cn domain.
|
|
bot.SetDomain(lark.DomainLark)
|
|
|
|
// Let the bot use a HTTP client with a longer timeout than the default 5
|
|
// seconds.
|
|
bot.SetClient(&http.Client{
|
|
Timeout: 8 * time.Second,
|
|
})
|
|
|
|
_ = bot.StartHeartbeat()
|
|
|
|
return &CustomAppService{
|
|
receiveIDs: make([]*ReceiverID, 0),
|
|
cli: &larkClientGoLarkChatBot{
|
|
bot: bot,
|
|
},
|
|
}
|
|
}
|
|
|
|
// AddReceivers adds recipients to future notifications. There are five different
|
|
// types of receiver IDs available in Lark and they must be specified here. For
|
|
// example:
|
|
//
|
|
// larkService.AddReceivers(
|
|
// lark.OpenID("ou_c99c5f35d542efc7ee492afe11af19ef"),
|
|
// lark.UserID("8335aga2"),
|
|
// lark.UnionID("on_cad4860e7af114fb4ff6c5d496d1dd76"),
|
|
// lark.Email("xyz@example.com"),
|
|
// lark.ChatID("oc_a0553eda9014c201e6969b478895c230"),
|
|
// )
|
|
func (c *CustomAppService) AddReceivers(ids ...*ReceiverID) {
|
|
c.receiveIDs = append(c.receiveIDs, ids...)
|
|
}
|
|
|
|
// Send takes a message subject and a message body and sends them to all
|
|
// previously registered recipient IDs.
|
|
func (c *CustomAppService) Send(ctx context.Context, subject, message string) error {
|
|
for _, id := range c.receiveIDs {
|
|
select {
|
|
case <-ctx.Done():
|
|
return ctx.Err()
|
|
default:
|
|
if err := c.cli.SendTo(subject, message, id.id, string(id.typ)); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// larkClientGoLarkChatBot is a wrapper around go-lark/lark's Bot, to be used
|
|
// for sending messages with custom apps.
|
|
type larkClientGoLarkChatBot struct {
|
|
bot *lark.Bot
|
|
}
|
|
|
|
// SendTo implements the sendToer interface using a go-lark/lark chat bot.
|
|
func (l *larkClientGoLarkChatBot) SendTo(subject, message, receiverID, idType string) error {
|
|
content := lark.NewPostBuilder().
|
|
Title(subject).
|
|
TextTag(message, 1, false).
|
|
Render()
|
|
msg := lark.NewMsgBuffer(lark.MsgPost).Post(content)
|
|
switch receiverIDType(idType) {
|
|
case openID:
|
|
msg.BindOpenID(receiverID)
|
|
case userID:
|
|
msg.BindUserID(receiverID)
|
|
case unionID:
|
|
msg.BindUnionID(receiverID)
|
|
case email:
|
|
msg.BindEmail(receiverID)
|
|
case chatID:
|
|
msg.BindChatID(receiverID)
|
|
}
|
|
res, err := l.bot.PostMessage(msg.Build())
|
|
if err != nil {
|
|
return fmt.Errorf("failed to send message: %w", err)
|
|
}
|
|
if res.Code != 0 {
|
|
return fmt.Errorf("send failed with error code %d, please see https://open.larksuite.com/document/ukTMukTMukTM/ugjM14COyUjL4ITN for details", res.Code)
|
|
}
|
|
return nil
|
|
}
|