Installation

Raygun4PHP provider

A library you can easily add to your PHP-based website, which then allows you to transmit all errors and exceptions to your Raygun Crash Reporting dashboard. Installation is painless, and configuring your site to start real time error monitoring and crash reporting takes only 5 minutes.

Raygun4PHP is designed to send both classical PHP errors, as well as PHP5 exception objects by providing Send() functions. You can add a set of tags (as an array of strings) to identify a certain errors, add custom user data, and custom how errors are grouped.

Installation

With Composer

Composer is a package management tool for PHP which automatically fetches dependencies and also supports autoloading - this is a low-impact way to get Raygun4PHP into your site.

  • If you use a *nix environment, follow the instructions to install Composer. Windows users can run this installer to automatically add it to the path etc.
  • Inside your project’s root directory create a composer.json file, containing:
{
    "require": {
        "mindscape/raygun4php": "1.*"
    }
}
  • From your shell run php composer.phar install (*nix) or composer install (Windows). This will download Raygun4Php and create the appropriate autoload data.
  • Then in a PHP file just add this, and the library will be ready for use:
require_once 'vendor/autoload.php'

Manually with Git

Clone the Raygun4PHP repository and copy the folder src/Raygun4php into an appropriate subdirectory in your project, such as /vendor/Raygun4php. Then add the following require definitions for RaygunClient.php inside the file you want to make a call to Send().

Usage

You can send both PHP errors and object-oriented exceptions to Raygun. An easy way to accomplish this is to create a file containing exception and error handlers which make calls to the appropriate Raygun4php functions. As above, import Raygun4php - if you’re using Composer, just add require_once ‘vendor/autoload.php’, or if not manually import RaygunClient.php. Then, create handlers that look like this:

<?php
namespace
{
    // paste your 'requires' statement

    $client = new \Raygun4php\RaygunClient("apikey for your application");

    function error_handler($errno, $errstr, $errfile, $errline ) {
        global $client;
        $client->SendError($errno, $errstr, $errfile, $errline);
    }

    function exception_handler($exception)
    {
        global $client;
        $client->SendException($exception);
    }

    function fatal_error()
    {
        global $client;
        $last_error = error_get_last();

        if (!is_null($last_error)) {
            $errno = $last_error['type'];
            $errstr = $last_error['message'];
            $errfile = $last_error['file'];
            $errline = $last_error['line'];
            $client->SendError($errno, $errstr, $errfile, $errline);
        }
    }
    set_exception_handler('exception_handler');
    set_error_handler("error_handler");
    register_shutdown_function("fatal_error");
}

Note that if you are placing in inside a file with a namespace of your choosing, the above code should be declared to be within the global namespace (thus the namespace { } is required). You will also need whichever requires statement as above (autoload or manual) before the $client instantiation. Copy your application’s API key from the Raygun Crash Reporting dashboard, and place it in the constructor call as above (do not include the curly brackets). If the handlers reside in their own file, just import it in every file where you’d like exceptions and errors to be sent, and they will be delivered to Raygun Crash Reporting.

Manually sending exceptions

You can manually send exceptions at any time with the stack trace like this:

<?php
require_once "vendor/autoload.php"; // if using Composer

$client = new \Raygun4php\RaygunClient("apikey");
try {
  throw new Exception("Your message");
} catch (Exception $e) {
  $client->SendException($e);
}

Async vs Sync Sending

For supported platforms (*nix, OS X, some Windows) the PHP provider has fully asynchronous, non-blocking sending logic. This ensures the user receives the requested page without having to wait for the server to send its error message to Raygun.

Asynchronous

POSTs the message and returns to your script immediately without waiting for the response from the Raygun API.

Linux/OS X platforms defaults to using this method.

<?php
$useAsyncSending = true;
$client = new \Raygun4php\RaygunClient("apiKey", $useAsyncSending);

Synchronous

POSTs the message, blocks and receives the HTTP response from the Raygun API. This uses a socket connection which is still reasonably fast. This also allows the use of the debug mode to receive the HTTP response code; see below.

Windows defaults to using this method due to limitations of arguments passed to CLI cURL.

<?php
$useAsyncSending = false;
$client = new \Raygun4php\RaygunClient("apiKey", $useAsyncSending);

HTTP Proxy

You can make Raygun4PHP post through an HTTP proxy of your choice like this:

<?php
$client->setProxy('http://myproxy:3128');

Debug mode (Since 1.3)

A debug mode in which the HTTP response code can be returned after a POST attempt which can be useful when initially adding Raygun. This is accessed by passing in true as the third parameter in the client constructor:

<?php
$client = new \Raygun4php\RaygunClient("apiKey", false, $debugMode);
echo $client->SendException(new Exception('Error')); // Response code will be displayed

Note: This is only avaliable when using the Synchronous sending method

Response codes

  • 202: Message received by Raygun API correctly
  • 403: Invalid API key. API keys can be found in your Raygun Application Settings
  • 400: Bad message. This may indicate an invalid payload - please contact us if you continue to see this.

Version numbers

You can transmit the version number of your PHP project along with the message by calling SetVersion() on your RaygunClient after it is instantiated - this is optional but recommended as the version number is considered to be first-class data for a message.

Adding Tags

Tags can be added to error data to provide extra information and to help filtering errors within Raygun. They are provided as an array of strings or numbers passed as the 5th argument to the SendError function and as the 2nd argument to the SendException function.

The declaration of the exception and error handlers using tags could look something like this:

<?php
$tags = array("testing-enviroment", "machine-4");

function error_handler($errno, $errstr, $errfile, $errline) {
    global $client, $tags;
    $client->SendError($errno, $errstr, $errfile, $errline, $tags);
}

function exception_handler($exception) {
    global $client, $tags;
    $client->SendException($exception, $tags);
}
function fatal_error()
{
    global $client;
    $last_error = error_get_last();

    if (!is_null($last_error)) {
        $errno = $last_error['type'];
        $errstr = $last_error['message'];
        $errfile = $last_error['file'];
        $errline = $last_error['line'];
        $client->SendError($errno, $errstr, $errfile, $errline, $tags);
    }
}

Custom grouping (Since 1.7)

Error instances are grouped automatically using the Raygun4PHP hasher logic. You can override this by passing a callback and manually group instances together by passing the same key for the errors/exceptions. The callback’s signature can take in the error payload, stack trace and then return a string which functions as the key before mentioned.

<?php
$client->SetGroupingKey(function($payload, $stackTrace) {
  // Inspect the above parameters and return a hash from the properties
  return $payload->Details->Error->Message; // Naive message-based grouping only
});

If the callback doesn’t return a string, the error will be grouped automatically.

User tracking

Users are tracked automatically by setting a random UUID, stored as a cookie. You can provide your own details about the user by passing a string (either username or email address) when calling the SetUser($user) method. That information will then be visible in the dashboard.

If the user logs in or out, be sure to call it again passing in the new user (or just call $client->SetUser() to assign a new random identifier).

<?php
$client->SetUser($user);

This feature can be used in CLI mode by calling SetUser(string) at the start of your session.

Additional Data (Since 1.5)

Extra information can be passed, used to provide an affected user count and reports.

<?php
$client->SetUser($user, $firstName, $fullName, $email, $isAnonymous, $uuid);

In this case $user should be a unique identifier used to identify your users. If you set this to their email address, be sure to also set the $email parameter too.

Sensitive data filtering

Some error data will be too sensitive to transmit to an external service, such as credit card details or passwords. Since this data is very application specific, Raygun doesn’t filter out anything by default. You can configure to either replace or otherwise transform specific values based on their keys. These transformations apply to form data ($_POST), custom user data, HTTP headers, and environment data ($_SERVER). It does not filter the URL or its $_GET parameters, or custom message strings. Since Raygun doesn’t log method arguments in stack traces, those don’t need filtering. All key comparisons are case insensitive.

<?php
$client = new \Raygun4php\RaygunClient("apiKey");
$client->setFilterParams(array(
    'password' => true,
    'creditcardnumber' => true,
    'ccv' => true,
    'php_auth_pw' => true, // filters basic auth from $_SERVER
));
// Example input: array('Username' => 'myuser','Password' => 'secret')
// Example output: array('Username' => 'myuser','Password' => '[filtered]')

You can also define keys as regular expressions:

<?php
$client = new \Raygun4php\RaygunClient("apiKey");
$client->setFilterParams(array(
    '/^credit/i' => true,
));
// Example input: array('CreditCardNumber' => '4111111111111111','CreditCardCcv' => '123')
// Example output: array('CreditCardNumber' => '[filtered]','CreditCardCcv' => '[filtered]')

In case you want to retain some hints on the data rather than removing it completely, you can also apply custom transformations through PHP’s anonymous functions. The following example truncates all keys starting with “address”.

<?php
$client = new \Raygun4php\RaygunClient("apiKey");
$client->setFilterParams(array(
    'Email' => function($key, $val) {return substr($val, 0, 5) . '...';}
));
// Example input: array('Email' => 'test@test.com')
// Example output: array('Email' => 'test@...')

Note that when any filters are defined, the Raygun error will no longer contain the raw HTTP data, since there’s no effective way to filter it.

The provider is open source and available at the Raygun4PHP repository.