Elgg  Version 3.0
ExceptionHandler.php
Go to the documentation of this file.
1 <?php
2 
3 namespace Elgg\Application;
4 
7 use Elgg\Loggable;
8 use Exception;
13 
20 
21  use Loggable;
22 
39  public function __invoke($exception) {
40  $exception->timestamp = time();
41  $exception->uncaught = true;
42 
43  $this->log(LogLevel::CRITICAL, $exception);
44 
45  // Wipe any existing output buffer
46  ob_end_clean();
47 
48  $request = Request::createFromGlobals();
49  $headers = [
50  'Cache-Control' => 'no-cache, must-revalidate',
51  'Expires' => 'Fri, 05 Feb 1982 00:00:00 -0500',
52  ];
53 
54  if ($exception instanceof \InstallationException) {
55  $response = RedirectResponse::create('/install.php', 307, $headers);
56  $response->prepare($request);
57 
58  $response->send();
59 
60  return;
61  }
62 
64 
65  if (!$app || !$app->_services) {
66  $msg = "Exception loading Elgg core. Check log at time {$exception->timestamp}";
67  $response = Response::create($msg, 500, $headers);
68  $response->prepare($request);
69 
70  $response->send();
71 
72  return;
73  }
74 
75  $services = $app->_services;
76 
77  try {
78  // allow custom scripts to trigger on exception
79  // value in settings.php should be a system path to a file to include
80  $exception_include = $services->config->exception_include;
81 
82  if ($exception_include && is_file($exception_include)) {
83  ob_start();
84 
85  // don't isolate, these scripts may use the local $exception var.
86  include $exception_include;
87 
88  $exception_output = ob_get_clean();
89 
90  // if content is returned from the custom handler we will output
91  // that instead of our default failsafe view
92  if (!empty($exception_output)) {
93  $response = Response::create($exception_output, 500, $headers);
94  $response->prepare($request);
95 
96  $response->send();
97 
98  return;
99  }
100  }
101 
102  if (Application::isCli()) {
103  // An error has already been logged
104  return;
105  }
106 
107  if ($services->request->isXmlHttpRequest()) {
108  $services->views->setViewtype('json');
109  $response = new JsonResponse(null, 500, $headers);
110  } else {
111  $services->views->setViewtype('failsafe');
112  $response = new Response('', 500, $headers);
113  }
114 
115  $body = elgg_view("messages/exceptions/exception", [
116  'object' => $exception,
117  'ts' => $exception->timestamp,
118  ]);
119 
120  $response->prepare($services->request);
121  $response->setContent(elgg_view_page(elgg_echo('exception:title'), $body));
122  $response->send();
123  } catch (Exception $e) {
124  $timestamp = time();
125 
126  $e->timestamp = $timestamp;
127 
128  $this->log(LogLevel::CRITICAL, $e);
129 
130  $msg = "Fatal error in exception handler. Check log for Exception at time $timestamp";
131 
132  $response = new Response($msg, 500, $headers);
133  $response->prepare($request);
134  $response->send();
135  }
136  }
137 }
Handler for uncaught exceptions.
static $_instance
Reference to the loaded Application.
Definition: Application.php:75
$request
Page handler for autocomplete endpoint.
Definition: livesearch.php:9
trait Loggable
Enables adding a logger.
Definition: Loggable.php:12
$timestamp
Definition: date.php:33
elgg_echo($message_key, array $args=[], $language="")
Given a message key, returns an appropriately translated full-text string.
Definition: languages.php:21
elgg_view_page($title, $body, $page_shell= 'default', $vars=[])
Assembles and outputs a full page.
Definition: views.php:360
$exception
static isCli()
Is application running in CLI.
$body
Definition: useradd.php:60
log($level, $message, array $context=[])
Log a message.
Definition: Loggable.php:55
__invoke($exception)
Intercepts, logs, and displays uncaught exceptions.
elgg_view($view, $vars=[], $viewtype= '')
Return a parsed view.
Definition: views.php:246