eesyphp/src/SentryIntegration.php

114 lines
3.4 KiB
PHP
Raw Normal View History

2023-01-29 18:17:50 +01:00
<?php
namespace EesyPHP;
use Throwable;
use Exception;
class SentryIntegration {
/**
* Sentry DSN
* @var string|null
*/
protected static $dsn = null;
/**
* Types of PHP error to log in Sentry
* @see https://www.php.net/manual/fr/errorfunc.constants.php
* @var array<int>
*/
protected static array $php_error_types = array(
E_ERROR, E_PARSE, E_CORE_ERROR, E_COMPILE_ERROR, E_USER_ERROR,
E_RECOVERABLE_ERROR,E_DEPRECATED,
);
/**
* Initialization
* @param string|null $dsn Sentry DSN
* @param float|null $traces_sample_rate Sentry traces sample rate
* (optional, default: 0.2)
* @param array<int>|null $php_error_types Types of PHP error to log in Sentry
* (optional, default: see self::$php_error_types)
* @return void
*/
public static function init($dsn=null, $traces_sample_rate=null,
$php_error_types=null) {
// Init Sentry (if its DSN is configured)
if (!$dsn) return;
\Sentry\init([
'dsn' => $dsn,
'traces_sample_rate' => (
$traces_sample_rate?
$traces_sample_rate:0.2
),
]);
\Sentry\configureScope(function (\Sentry\State\Scope $scope): void {
global $auth_user;
$scope->setUser([
'id' => isset($auth_user) && $auth_user?$auth_user['uid']:null,
'email' => isset($auth_user) && $auth_user?$auth_user['mail']:null,
'segment' => isset($auth_user) && $auth_user?$auth_user['type']:null,
'ip_address' => $_SERVER['REMOTE_ADDR'],
]);
});
if (is_array($php_error_types))
self :: $php_error_types = $php_error_types;
set_error_handler(
array('EesyPHP\\SentryIntegration', 'on_php_error'),
E_ALL
);
}
/**
* Log an exception or a message in Sentry
* @param string|Throwable $message
* @param array $extra_args Extra arguments to use to compute message using sprintf
* @return void
*/
public static function log($message, ...$extra_args) {
if (!self :: $dsn) {
Log :: trace('Sentry DSN not configured, do not log this error');
return;
}
if (is_string($message)) {
// Extra arguments passed, format message using sprintf
if ($extra_args) {
$message = call_user_func_array(
'sprintf',
array_merge(array($message), $extra_args)
);
}
Log :: debug('Error logged in Sentry');
\Sentry\captureMessage($message);
}
elseif ($message instanceof Exception) {
Log :: debug('Exception logged in Sentry');
\Sentry\captureException($message);
}
}
/**
* Log a PHP error in Sentry
* Note: method design to be used as callable by set_error_handler()
* @param int $errno The error number
* @param string $errstr The error message
* @param string $errfile The filename that the error was raised in
* @param int $errline The line number where the error was raised
* @return false Return false to let the normal error handler continues.
*/
public static function on_php_error($errno, $errstr, $errfile, $errline) {
if (in_array($errno, self :: $php_error_types))
self :: log(
"A PHP error occured : [%s] %s\nFile : %s (line : %d)",
Log :: errno2type($errno), $errstr, $errfile, $errline
);
return false;
}
}
# vim: tabstop=2 shiftwidth=2 softtabstop=2 expandtab