Add BugSnag to your net/http applications.
This library supports Go 1.11 and above. To integrate with older versions of Go, check out our legacy integration.
New to BugSnag? Create an account
Looking for performance monitoring? See our performance guide
Download the packages via go get
:
go get github.com/bugsnag/bugsnag-go/v2
go install github.com/bugsnag/panic-monitor
The latest available version of bugsnag-go
is v2.5.1
.
For a golang app based on net/http, integrating BugSnag takes two steps. You should also use these instructions if you’re using the gorilla toolkit, or the pat muxer.
Configure bugsnag at the start of your main()
function:
import "github.com/bugsnag/bugsnag-go/v2"
func main() {
bugsnag.Configure(bugsnag.Configuration{
APIKey: "YOUR API KEY HERE",
ReleaseStage: "production",
// The import paths for the Go packages containing your source files
ProjectPackages: []string{"main", "github.com/org/myapp"},
// more configuration options
})
// rest of your program.
}
You can find your API key in Project Settings from your BugSnag dashboard.
Initializing BugSnag in a location other than the start of your application may have unintended side effects due to the monitoring behavior of Configuration.PanicHandler
, which wraps and monitors the application process. See the configuration documentation for more details.
Then wrap your server in a bugsnag.Handler.
// a. If you're using the builtin http mux, you can just pass
// bugsnag.Handler(nil) to http.ListenAndServer
http.ListenAndServe(":8080", bugsnag.Handler(nil))
// b. If you're creating a server manually yourself, you can set
// its handlers the same way
srv := http.Server{
Handler: bugsnag.Handler(nil)
}
// c. If you're not using the builtin http mux, wrap your own handler
// (though make sure that it doesn't already catch panics)
http.ListenAndServe(":8080", bugsnag.Handler(handler))
context.Context
to manage HTTP session dataWe strongly recommend passing in context.Context to appropriate BugSnag calls.
Passing the context.Context from *http.Request
objects will automatically attach HTTP request data to your error reports, as well as session data that helps BugSnag track the stability of your application.
For more information around how to use context.Context
with BugSnag, see the context reference here.
Context can be retrieved from an HTTP request or created if outside a request (see session tracking for more details on sessions)
// Get context from an HTTP request
ctx = request.Context()
// or from manually starting a session outside a http request
ctx = bugsnag.StartSession(context.Background())
Unhandled panics are reported using panic-monitor, which is a program launcher that automatically reports any panics which occur in your program.
After completing installation and basic configuration, set the BUGSNAG_API_KEY
environment variable to the API key for your project and launch the monitor with your program and its arguments.
BUGSNAG_API_KEY="YOUR API KEY HERE" panic-monitor ./my-app --my-app-flag
Unhandled panics will be automatically reported and error data will begin to appear in your project’s dashboard.
If the panic-monitor launcher system cannot be used in your deployment environment, bugsnag-go
will instead attempt to detect panics in process with the following caveats:
bugsnag.Configure()
must be called at the start of your application’s main()
function, to avoid unintended side effects like re-calling any code prior to bugsnag.Configure()
when the application is forked.OnBeforeNotify
callbacks must be registered prior to calling Configure()
or will have no effect on events created from unrecovered panics. Panic handling in bugsnag-go forks the process when Configure()
is first called, so any callbacks added after that point will not be present in the monitoring process.See Configuration.PanicHandler
to disable reporting panics in-process.
Unhandled panics will terminate the app process, and when deployed with Docker as the main command, may not allow enough time to send the final panic event to BugSnag. Go apps deployed with Docker as PID 1 should use a launcher which will wait for a few seconds prior to allowing the container to terminate.
A bash script which launches and waits on an app named my-go-app
, terminating if requested by the operating system and waits after the app terminates to send a pending request. This script is intended to be run as the CMD
of a Dockerfile.
#!/usr/bin/env bash
# Forward signals to the app process so it terminates if
# requested by the system
_forward_signal() {
sig="$1"
kill -$sig "$app_pid" 2>/dev/null
wait $app_pid
}
_trap_signals() {
for sig in "$@"; do
trap "_forward_signal $sig" "$sig"
done
}
# Wait to allow potential unhandled panic requests to complete
_at_exit() {
sleep 3
}
_trap_signals INT TERM
trap _at_exit EXIT
./my-go-app &
# Wait until the app process terminates (ensuring signals
# can be captured)
app_pid=$!
wait $app_pid
Since goroutines are generally non-blocking, panics captured on a goroutine may crash the application before having the opportunity to be delivered to BugSnag unless intentionally handled.
Use bugsnag.AutoNotify()
to notify bugsnag of a panic while letting the program continue to panic. This
is useful if you’re using a framework that already has some handling of panics
and you are retrofitting BugSnag support.
go func(ctx context.Context) {
defer bugsnag.AutoNotify(ctx)
// ...
}(ctx)
To avoid a panic in a goroutine from crashing your entire app, you can use
bugsnag.Recover()
to stop a panic from unwinding the stack any further. When Recover()
is hit,
it will send any current panic to BugSnag and then stop panicking. This is
most useful at the start of a goroutine:
go func(ctx context.Context) {
defer bugsnag.Recover(ctx)
// ...
}(ctx)
Sometimes it is useful to manually notify BugSnag of a problem. To do
this, call
bugsnag.Notify()
if err != nil {
bugsnag.Notify(err, ctx)
}
When reporting handled errors, it’s often helpful to send us custom diagnostic data or to adjust the severity of particular errors. For more information, see the reporting handled errors reference.
Most functions in the BugSnag API, including bugsnag.Notify()
,
bugsnag.Recover()
, bugsnag.AutoNotify()
, and bugsnag.Handler()
let you
attach data to the notifications that they send. To do this you pass in
rawData
, which can be any of the supported types listed here.
Custom metaData appears as tabs on error reports on your BugSnag dashboard. You
can set it by passing a
bugsnag.MetaData
object as rawData.
bugsnag.Notify(err, ctx,
bugsnag.MetaData{
"Account": {
"Name": Account.Name,
"Paying": Account.Plan.Premium,
},
})
For more information, see the reporting handled errors reference.
See this reference to learn more about the ctx
argument and the advantages of using it.
User data is searchable, and the Id
powers the count of users affected. You
can set which user an error affects by passing a
bugsnag.User
object
as rawData.
bugsnag.Notify(err, ctx,
bugsnag.User{Id: "1234", Name: "Conrad", Email: "me@example.com"})
For more information, see the reporting handled errors reference.
See this reference to learn more about the ctx
argument and the advantages of using it.
BugSnag tracks the number of “sessions” that happen within your application. This allows you to compare stability scores between releases and helps you to understand the quality of your releases.
Sessions are captured and reported by default. This behavior can be disabled using the AutoCaptureSessions
configuration option.
Configure your app version to see the release that each error was introduced in.
bugsnag.Configure(bugsnag.Configuration{
AppVersion: "1.2.3",
})
Then set up a build tool integration to enable linking to code in your source control provider from the releases dashboard, timeline annotations, and stack traces.
bugsnag-go
, the library powering this integration, on GitHub