-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathsentry.go
125 lines (99 loc) · 3 KB
/
sentry.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
// Copyright 2021-2022, the SS project owners. All rights reserved.
// Please see the OWNERS and LICENSE files for details.
package ss
import (
"log"
sentryclient "github.com/getsentry/sentry-go"
)
type sentry interface {
CaptureMessage(*LogMsg)
Recover(*LogMsg)
Flush()
}
func newSentry(
projectPackage string,
module string,
config Config,
) (sentry, error) {
if config.SS.Log.Sentry == "" {
return sentryDummy{}, nil
}
err := sentryclient.Init(
sentryclient.ClientOptions{
Dsn: config.SS.Log.Sentry,
AttachStacktrace: true,
Release: config.SS.Build.Version,
Environment: config.SS.Build.GetEnvironment(),
BeforeSend: func(
event *sentryclient.Event,
hint *sentryclient.EventHint,
) *sentryclient.Event {
event.Tags["module"] = module
event.Tags["package"] = projectPackage
event.Tags["build"] = config.SS.Build.ID
event.Tags["commit"] = config.SS.Build.Commit
event.Tags["builder"] = config.SS.Build.Builder
event.Tags["aws.region"] = config.SS.Service.AWS.Region
return event
},
})
if err != nil {
return nil, err
}
return sentryConnect{}, nil
}
////////////////////////////////////////////////////////////////////////////////
type sentryDummy struct{}
func (sentryDummy) CaptureMessage(*LogMsg) {}
func (sentryDummy) Recover(*LogMsg) {}
func (sentryDummy) Flush() {}
////////////////////////////////////////////////////////////////////////////////
type sentryConnect struct{}
func (s sentryConnect) CaptureMessage(message *LogMsg) {
if sentryclient.CaptureEvent(s.newEvent(message, false)) == nil {
log.Println("Failed to capture message by Sentry.")
}
}
func (s sentryConnect) Recover(message *LogMsg) {
event := s.newEvent(message, true)
if sentryclient.CaptureEvent(event) == nil {
log.Println(`Failed to recover panic by Sentry.`)
}
}
func (sentryConnect) Flush() {
if !sentryclient.Flush(S.Config().AWS.LambdaTimeout / 2) {
log.Println("Not all Sentry records were flushed, timeout was reached.")
}
}
func (s sentryConnect) newEvent(
source *LogMsg,
isCrash bool,
) *sentryclient.Event {
result := sentryclient.NewEvent()
switch source.GetLevel() {
case logLevelDebug:
result.Level = sentryclient.LevelDebug
case logLevelInfo:
result.Level = sentryclient.LevelInfo
case logLevelWarn:
result.Level = sentryclient.LevelWarning
case logLevelError:
result.Level = sentryclient.LevelError
default: // logLevelPanic also here
result.Level = sentryclient.LevelFatal
}
result.Threads = []sentryclient.Thread{{
Stacktrace: sentryclient.NewStacktrace(),
Crashed: isCrash,
Current: true,
}}
result.Extra = source.MarshalAttributesMap()
if user, has := result.Extra[logMsgNodeUser]; has {
result.User.ID = user.(UserID).String()
delete(result.Extra, logMsgNodeUser)
}
result.Message = source.GetMessage()
// Exception will be stored with Sentry record as "dumps".
return result
}
////////////////////////////////////////////////////////////////////////////////