Merge pull request #183 from evalphobia/feature/sentry-http-request

Added special field for *http.Request to Sentry hook
This commit is contained in:
Simon Eskildsen 2015-05-22 10:03:26 -04:00
commit 092eda23b5
3 changed files with 30 additions and 6 deletions

View File

@ -34,12 +34,13 @@ func main() {
## Special fields ## Special fields
Some logrus fields have a special meaning in this hook, Some logrus fields have a special meaning in this hook,
these are server_name and logger. these are `server_name`, `logger` and `http_request`.
When logs are sent to sentry these fields are treated differently. When logs are sent to sentry these fields are treated differently.
- server_name (also known as hostname) is the name of the server which - `server_name` (also known as hostname) is the name of the server which
is logging the event (hostname.example.com) is logging the event (hostname.example.com)
- logger is the part of the application which is logging the event. - `logger` is the part of the application which is logging the event.
In go this usually means setting it to the name of the package. In go this usually means setting it to the name of the package.
- `http_request` is the in-coming request(*http.Request). The detailed request data are sent to Sentry.
## Timeout ## Timeout

View File

@ -3,6 +3,7 @@ package logrus_sentry
import ( import (
"fmt" "fmt"
"time" "time"
"net/http"
"github.com/Sirupsen/logrus" "github.com/Sirupsen/logrus"
"github.com/getsentry/raven-go" "github.com/getsentry/raven-go"
@ -36,6 +37,22 @@ func getAndDel(d logrus.Fields, key string) (string, bool) {
return val, true return val, true
} }
func getAndDelRequest(d logrus.Fields, key string) (*http.Request, bool) {
var (
ok bool
v interface{}
req *http.Request
)
if v, ok = d[key]; !ok {
return nil, false
}
if req, ok = v.(*http.Request); !ok || req == nil {
return nil, false
}
delete(d, key)
return req, true
}
// SentryHook delivers logs to a sentry server. // SentryHook delivers logs to a sentry server.
type SentryHook struct { type SentryHook struct {
// Timeout sets the time to wait for a delivery error from the sentry server. // Timeout sets the time to wait for a delivery error from the sentry server.
@ -61,7 +78,7 @@ func NewSentryHook(DSN string, levels []logrus.Level) (*SentryHook, error) {
// Called when an event should be sent to sentry // Called when an event should be sent to sentry
// Special fields that sentry uses to give more information to the server // Special fields that sentry uses to give more information to the server
// are extracted from entry.Data (if they are found) // are extracted from entry.Data (if they are found)
// These fields are: logger and server_name // These fields are: logger, server_name and http_request
func (hook *SentryHook) Fire(entry *logrus.Entry) error { func (hook *SentryHook) Fire(entry *logrus.Entry) error {
packet := &raven.Packet{ packet := &raven.Packet{
Message: entry.Message, Message: entry.Message,
@ -78,6 +95,9 @@ func (hook *SentryHook) Fire(entry *logrus.Entry) error {
if serverName, ok := getAndDel(d, "server_name"); ok { if serverName, ok := getAndDel(d, "server_name"); ok {
packet.ServerName = serverName packet.ServerName = serverName
} }
if req, ok := getAndDelRequest(d, "http_request"); ok {
packet.Interfaces = append(packet.Interfaces, raven.NewHttp(req))
}
packet.Extra = map[string]interface{}(d) packet.Extra = map[string]interface{}(d)
_, errCh := hook.client.Capture(packet, nil) _, errCh := hook.client.Capture(packet, nil)

View File

@ -61,9 +61,12 @@ func TestSpecialFields(t *testing.T) {
t.Fatal(err.Error()) t.Fatal(err.Error())
} }
logger.Hooks.Add(hook) logger.Hooks.Add(hook)
req, _ := http.NewRequest("GET", "url", nil)
logger.WithFields(logrus.Fields{ logger.WithFields(logrus.Fields{
"server_name": server_name, "server_name": server_name,
"logger": logger_name, "logger": logger_name,
"http_request": req,
}).Error(message) }).Error(message)
packet := <-pch packet := <-pch