-
Notifications
You must be signed in to change notification settings - Fork 0
/
logger.go
145 lines (117 loc) · 3.51 KB
/
logger.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
// Go Telegram logger
package gtl
import (
"encoding/json"
"errors"
"fmt"
"reflect"
"time"
"github.com/cheatsnake/gtl/internal/telegram"
)
// Logger is used to send log messages or notifications via Telegram.
type Logger struct {
botAPI telegram.BotAPI
Options Options
}
// New creates and initializes a new Logger instance.
//
// This function is used to set up a Logger that integrates with a Telegram bot.
// It requires a Telegram bot token for authentication and an Options struct
// to configure the logger's behavior.
func New(botToken string, opts Options) (*Logger, error) {
if botToken == "" {
return nil, errors.New(botTokenRequiredErr)
}
if opts.ChatID == "" {
return nil, errors.New(chatIdRequiredErr)
}
return &Logger{
botAPI: telegram.NewBot(botToken),
Options: opts,
}, nil
}
// Log information message
func (l *Logger) Info(data any, opts ...Options) (*telegram.Response, error) {
resp, err := l.sendLog(data, infoEmoji+" "+infoTitle, opts)
return resp, err
}
// Log success message
func (l *Logger) Ok(data any, opts ...Options) (*telegram.Response, error) {
resp, err := l.sendLog(data, successEmoji+" "+successTitle, opts)
return resp, err
}
// Log warning message
func (l *Logger) Warn(data any, opts ...Options) (*telegram.Response, error) {
resp, err := l.sendLog(data, warningEmoji+" "+warningTitle, opts)
return resp, err
}
// Log error message
func (l *Logger) Err(data any, opts ...Options) (*telegram.Response, error) {
resp, err := l.sendLog(data, errorEmoji+" "+errorTitle, opts)
return resp, err
}
// Log raw message without any prefix
func (l *Logger) Raw(data any, opts ...Options) (*telegram.Response, error) {
resp, err := l.sendLog(data, "", opts)
return resp, err
}
func (l *Logger) sendLog(data any, prefix string, overOpts []Options) (*telegram.Response, error) {
opts := l.Options
// Override global options
if len(overOpts) > 0 {
// Exclude overrides for ChatID and ThreadID if they are not passed in
if overOpts[0].ChatID != "" {
opts.ChatID = overOpts[0].ChatID
}
if overOpts[0].ThreadID != 0 {
opts.ThreadID = overOpts[0].ThreadID
}
opts.CodeExtension = overOpts[0].CodeExtension
opts.DisableNotification = overOpts[0].DisableNotification
opts.ParseMode = overOpts[0].ParseMode
opts.TimeMetadata = overOpts[0].TimeMetadata
opts.WrapAsCode = overOpts[0].WrapAsCode
}
text := prepareLog(data, prefix, opts.ParseMode, opts.CodeExtension, opts.WrapAsCode, opts.TimeMetadata)
resp, err := l.botAPI.SendMessage(
text,
opts.ChatID,
opts.ThreadID,
opts.ParseMode,
opts.DisableNotification,
)
return resp, err
}
func prepareLog(data any, prefix, parseMode, codeExtension string, wrapAsCode, timeMetadata bool) string {
text := tryConvertToJSON(data)
if parseMode == telegram.Md2ParseMode {
text = telegram.FormatForMarkdownV2(text)
}
if wrapAsCode {
text = telegram.FormatAsCode(text, parseMode, codeExtension)
}
if len(prefix) > 0 {
boldPrefix := telegram.FormatAsBold(prefix, parseMode)
text = fmt.Sprintf("%s\n\n%s", boldPrefix, text)
}
if timeMetadata {
datetime := time.Now().Format(datetimeFormat)
if parseMode == telegram.Md2ParseMode {
datetime = telegram.FormatForMarkdownV2(datetime)
}
text = fmt.Sprintf("%s\n\n%s", text, datetime)
}
return text
}
func tryConvertToJSON(value any) string {
if value == nil {
return ""
}
if reflect.TypeOf(value).Kind() == reflect.Struct {
json, err := json.MarshalIndent(value, "", " ")
if err == nil {
return string(json)
}
}
return fmt.Sprintf("%v", value)
}