raygun4go

package module
v1.3.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 7, 2023 License: MIT Imports: 13 Imported by: 4

README

Raygun4Go

GoDoc GoReportcard

Raygun4Go adds Raygun-based error handling to your Golang code. It catches all occuring errors, extracts as much information as possible, and sends the error to Raygun via our REST-API.

Getting Started

Installation
$ go get github.com/MindscapeHQ/raygun4go
Basic Usage

Include the package and then defer the HandleError-method as soon as possible, in a context as global as possible. In webservers, this will probably be your request handling method. In all other programs, it should be your main-method. It will automatically capture any panic and report it.

raygun, err := raygun4go.New("appName", "apiKey")
if err != nil {
  log.Println("Unable to create Raygun client:", err.Error())
}
defer raygun.HandleError()

Where appName is the name of your app and apiKey is your Raygun API key. If your program runs into a panic now (which you can easily test by adding panic("foo") after the call to defer), the handler will send the error to Raygun.

Manually sending errors

To send errors manually, you can use CreateError(message string), SendError(error error), or CreateErrorWithStackTrace(message string, st StackTrace).

  • CreateError creates an error with the given message and immediately reports it with the current execution stack trace.
  • SendError immediately reports the error with its stack trace if it's of type "github.com/go-errors/errors".Error. Otherwise, it uses the current execution stack trace.
  • CreateErrorWithStackTrace allows you to manually send an error with a custom stack trace.

Example of CreateError:

if err := raygun.CreateError("something bad happened"); err != nil {
    log.Printf("failed to report error to Raygun: %v\n", err)
}

Example of SendError:

err := something.Do()
if err := raygun.SendError(err); err != nil {
    log.Printf("failed to report error to Raygun: %v\n", err)
}

Example of CreateErrorWithStackTrace:

st := make(raygun4go.StackTrace, 0)
st.AddEntry(42, "main", "example.go", "exampleFunc")
if err := raygun.CreateErrorWithStackTrace("something bad happened", st); err != nil {
    log.Printf("failed to report error to Raygun: %v\n", err)
}

Options

The client returned by New has several chainable option-setting methods:

Method Description
Silent(bool) If set to true, this prevents the handler from sending the error to Raygun, printing it instead.
Request(*http.Request) Adds the responsible http.Request to the error.
Version(string) If your program has a version, you can add it here.
Tags([]string) Adds the given tags to the error. These can be used for filtering later.
CustomData(interface{}) Adds arbitrary custom data to you error. Will only reach Raygun if it works with json.Marshal().
User(string) Adds the name of the affected user to the error.
Custom grouping

By default, the Raygun service will group errors together based on stack trace content. If you have any cases where you want to control the error grouping yourself, then you can provide a custom-grouping-key callback function. Below is a simple example that returns a hard-coded grouping key, which would cause all errors to be grouped together:

raygun.CustomGroupingKeyFunction(func(error, raygun4go.PostData)string{return "customGroupingKey"})

The callback takes the original error, and the Raygun PostData payload structure that is about to be serialized and sent to Raygun. In your callback, you can check these values to help build your own grouping key logic based on different cases that you want to control. For any error you don't want to group yourself, return an empty string - Raygun will then use the default grouping.

Bugs and feature requests

Have a bug or a feature request? Please first check the list of issues.

If your problem or idea is not addressed yet, please open a new issue.

Documentation

Overview

Package raygun4go adds Raygun-based error handling to your golang code.

It basically adds an error-handler that recovers from all panics that might occur and sends information about that error to Raygun. The amount of data being sent is configurable.

Basic example:

raygun, err := raygun4go.New("appName", "apiKey")
if err != nil {
  log.Println("Unable to create Raygun client:", err.Error())
}
defer raygun.HandleError()

This will send the error message together with a stack trace to Raygun.

However, raygun4go really starts to shine if used in a webserver context. By calling

raygun.Request(*http.Request)

you can set a request to be analyzed in case of an error. If an error occurs, this will send the request details to Raygun, including

  • hostname
  • url
  • http method
  • ip adress
  • url parameters
  • POSTed form fields
  • headers
  • cookies

giving you a lot more leverage on your errors than the plain error message could provide you with.

Chainable configuration methods are available (see below) to set the affected version, user, tags or custom data.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Current

func Current(stack stackTrace)

Current loads the current stacktrace into a given stack

func LoadGoErrorStack added in v1.1.1

func LoadGoErrorStack(frames []goerrors.StackFrame, stack stackTrace)

LoadGoErrorStack loads the strack trace (given as frames) into the given stack.

func Parse

func Parse(trace []byte, stack stackTrace)

Parse loads the stack trace (given as trace) into the given stack. See Current() on how to obtain a stack trace.

Types

type Client

type Client struct {
	// contains filtered or unexported fields
}

Client is the struct holding your Raygun configuration and context information that is needed if an error occurs.

func New

func New(appName, apiKey string) (c *Client, err error)

New creates and returns a Client, needing an appName and an apiKey. It also creates a unique identifier for your program.

func (*Client) Asynchronous

func (c *Client) Asynchronous(a bool) *Client

Sets whether or not this client submits reports to Raygun asynchronously. The default is false.

func (*Client) Clone

func (c *Client) Clone() *Client

func (*Client) CreateError

func (c *Client) CreateError(message string) error

Manually send a new error with the given message to Raygun. This will use the current execution stacktrace.

func (*Client) CreateErrorWithStackTrace added in v1.3.0

func (c *Client) CreateErrorWithStackTrace(message string, st StackTrace) error

Manually send an error to Raygun with a custom message and a custom stacktrace. This can be useful when the default system stack trace is not relevant or sufficient.

The message parameter is the error message to be reported. The st parameter is a custom StackTrace to be associated with the error.

To construct a StackTrace, use the AddEntry method of the StackTrace type. For example:

st := make(raygun4go.StackTrace, 0)
st.AddEntry(42, "main", "example.go", "exampleFunc")

func (*Client) CustomData

func (c *Client) CustomData(data interface{}) *Client

CustomData is a chainable option-setting method to add arbitrary custom data to the context. Note that the given type (or at least parts of it) must implement the Marshaler-interface for this to work.

func (*Client) CustomGroupingKeyFunction

func (c *Client) CustomGroupingKeyFunction(getCustomGroupingKey func(error, PostData) string) *Client

CustomGroupingKeyFunction is a chainable option-setting method to provide a callback function that returns a custom grouping key. This function is passed the original error and Raygun payload just before it is serialized and sent to Raygun. This lets you control how errors are grouped in your Raygun account. Returning null will result in Raygun grouping the errors for you. This allows you to pick and choose which errors you want to control the grouping for.

func (*Client) HandleError

func (c *Client) HandleError() error

HandleError sets up the error handling code. It needs to be called with

defer c.HandleError()

to handle all panics inside the calling function and all calls made from it. Be sure to call this in your main function or (if it is webserver) in your request handler as soon as possible.

func (*Client) LogToStdOut

func (c *Client) LogToStdOut(l bool) *Client

LogToStdOut sets the logToStdOut-property on the Client. If true, errors will be printed to std out as they are submitted to raygun. This will also log any errors that occur when submiting to raygun to std out

func (*Client) Request

func (c *Client) Request(r *http.Request) *Client

Request is a chainable option-setting method to add a request to the context.

func (*Client) SendError

func (c *Client) SendError(error error) error

Manually send the given error to Raygun. If the given error is a "github.com/go-errors/errors".Error, then its stacktrace will be used in the Raygun report. For other errors, the current execution stacktrace is used in the Raygun report.

func (*Client) Silent

func (c *Client) Silent(s bool) *Client

Silent sets the silent-property on the Client. If true, errors will not be sent to Raygun but printed instead.

func (*Client) Submit added in v1.1.0

func (c *Client) Submit(post PostData) error

Submit takes care of actually sending the error to Raygun unless the silent option is set.

func (*Client) Tags

func (c *Client) Tags(tags []string) *Client

Tags is a chainable option-setting method to add tags to the context. You can use tags to filter errors in Raygun.

func (*Client) User

func (c *Client) User(u string) *Client

User is a chainable option-setting method to add an affected Username to the context.

func (*Client) Version

func (c *Client) Version(v string) *Client

Version is a chainable option-setting method to add a version to the context.

type ClientData

type ClientData struct {
	Name      string `json:"name"`
	Version   string `json:"version"`
	ClientURL string `json:"clientUrl"`
}

clientData is the struct holding information on this client.

type Context

type Context struct {
	Identifier string `json:"identifier"`
}

context holds information on the program context.

type DetailsData

type DetailsData struct {
	MachineName    string         `json:"machineName"`    // the machine's hostname
	Version        string         `json:"version"`        // the version from context
	Error          ErrorData      `json:"error"`          // everything we know about the error itself
	Tags           []string       `json:"tags"`           // the tags from context
	UserCustomData UserCustomData `json:"userCustomData"` // the custom data from the context
	Request        RequestData    `json:"request"`        // the request from the context
	User           User           `json:"user"`           // the user from the context
	Context        Context        `json:"context"`        // the identifier from the context
	Client         ClientData     `json:"client"`         // information on this client
	GroupingKey    *string        `json:"groupingKey"`    // a custom key that Raygun will use for grouping errors
}

detailsData is the container holding all information regarding the more detailed circumstances the error occured in.

type ErrorData

type ErrorData struct {
	Message    string     `json:"message"`    // the actual message the error produced
	StackTrace StackTrace `json:"stackTrace"` // the error's stack trace
}

errorData is the struct holding all technical information on the error.

type PostData

type PostData struct {
	OccuredOn string      `json:"occurredOn"` // the time the error occured on, format 2006-01-02T15:04:05Z
	Details   DetailsData `json:"details"`    // all the details needed by the API
}

postData is the outmost element of the Raygun-REST-API

type RequestData

type RequestData struct {
	HostName    string            `json:"hostName"`
	URL         string            `json:"url"`
	HTTPMethod  string            `json:"httpMethod"`
	IPAddress   string            `json:"ipAddress"`
	QueryString map[string]string `json:"queryString"` // key-value-pairs from the URI parameters
	Form        map[string]string `json:"form"`        // key-value-pairs from a given form (POST)
	Headers     map[string]string `json:"headers"`     // key-value-pairs from the header
}

requestData holds all information on the request from the context

type StackTrace

type StackTrace []StackTraceElement

StackTrace represents a series of stack trace elements, each detailing a level of the call stack. Users can manually build a StackTrace by appending StackTraceElement instances to it.

func (*StackTrace) AddEntry

func (s *StackTrace) AddEntry(lineNumber int, packageName, fileName, methodName string)

AddEntry appends a new entry to the StackTrace. This method is primarily used by internal parsing functions but can also be used to manually construct a StackTrace.

  • lineNumber: The line number where the call occurred.
  • packageName: The package that contains the file of the call.
  • fileName: The file where the call occurred.
  • methodName: The method or function name where the call occurred.

type StackTraceElement

type StackTraceElement struct {
	LineNumber  int    `json:"lineNumber"`
	PackageName string `json:"className"`
	FileName    string `json:"fileName"`
	MethodName  string `json:"methodName"`
}

stackTraceElement is one element of the error's stack trace. It is filled by stack2struct.

type User

type User struct {
	Identifier string `json:"identifier"`
}

user holds information on the affected user.

type UserCustomData

type UserCustomData interface{}

UserCustomData is the interface that needs to be implemented by the custom data to be sent with the error. Being 'interface{}' suggests that it could be anything, but the data itself or contained data should respond to json.Marshal() for the data to be transmitted.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL