Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/phabricator
Path: blob/master/src/aphront/response/AphrontUnhandledExceptionResponse.php
12241 views
1
<?php
2
3
final class AphrontUnhandledExceptionResponse
4
extends AphrontStandaloneHTMLResponse {
5
6
private $exception;
7
private $showStackTraces;
8
9
public function setShowStackTraces($show_stack_traces) {
10
$this->showStackTraces = $show_stack_traces;
11
return $this;
12
}
13
14
public function getShowStackTraces() {
15
return $this->showStackTraces;
16
}
17
18
public function setException($exception) {
19
// NOTE: We accept an Exception or a Throwable.
20
21
// Log the exception unless it's specifically a silent malformed request
22
// exception.
23
24
$should_log = true;
25
if ($exception instanceof AphrontMalformedRequestException) {
26
if ($exception->getIsUnlogged()) {
27
$should_log = false;
28
}
29
}
30
31
if ($should_log) {
32
phlog($exception);
33
}
34
35
$this->exception = $exception;
36
return $this;
37
}
38
39
public function getHTTPResponseCode() {
40
return 500;
41
}
42
43
protected function getResources() {
44
return array(
45
'css/application/config/config-template.css',
46
'css/application/config/unhandled-exception.css',
47
);
48
}
49
50
protected function getResponseTitle() {
51
$ex = $this->exception;
52
53
if ($ex instanceof AphrontMalformedRequestException) {
54
return $ex->getTitle();
55
} else {
56
return pht('Unhandled Exception');
57
}
58
}
59
60
protected function getResponseBodyClass() {
61
return 'unhandled-exception';
62
}
63
64
private function getExceptionList() {
65
return $this->expandException($this->exception);
66
}
67
68
private function expandException($root) {
69
if ($root instanceof PhutilAggregateException) {
70
$list = array();
71
72
$list[] = $root;
73
74
foreach ($root->getExceptions() as $ex) {
75
foreach ($this->expandException($ex) as $child) {
76
$list[] = $child;
77
}
78
}
79
80
return $list;
81
}
82
83
return array($root);
84
}
85
86
protected function getResponseBody() {
87
$body = array();
88
89
foreach ($this->getExceptionList() as $ex) {
90
$body[] = $this->newHTMLMessage($ex);
91
}
92
93
return $body;
94
}
95
96
private function newHTMLMessage($ex) {
97
if ($ex instanceof AphrontMalformedRequestException) {
98
$title = $ex->getTitle();
99
} else {
100
$title = get_class($ex);
101
}
102
103
$body = $ex->getMessage();
104
$body = phutil_escape_html_newlines($body);
105
106
$classes = array();
107
$classes[] = 'unhandled-exception-detail';
108
109
$stack = null;
110
if ($this->getShowStackTraces()) {
111
try {
112
$stack = id(new AphrontStackTraceView())
113
->setTrace($ex->getTrace());
114
115
$stack = hsprintf('%s', $stack);
116
117
$stack = phutil_tag(
118
'div',
119
array(
120
'class' => 'unhandled-exception-stack',
121
),
122
$stack);
123
124
$classes[] = 'unhandled-exception-with-stack';
125
} catch (Exception $trace_exception) {
126
$stack = null;
127
} catch (Throwable $trace_exception) {
128
$stack = null;
129
}
130
}
131
132
return phutil_tag(
133
'div',
134
array(
135
'class' => implode(' ', $classes),
136
),
137
array(
138
phutil_tag(
139
'h1',
140
array(
141
'class' => 'unhandled-exception-title',
142
),
143
$title),
144
phutil_tag(
145
'div',
146
array(
147
'class' => 'unhandled-exception-body',
148
),
149
$body),
150
$stack,
151
));
152
}
153
154
protected function buildPlainTextResponseString() {
155
$messages = array();
156
157
foreach ($this->getExceptionList() as $exception) {
158
$messages[] = $this->newPlainTextMessage($exception);
159
}
160
161
return implode("\n\n", $messages);
162
}
163
164
private function newPlainTextMessage($exception) {
165
return pht(
166
'%s: %s',
167
get_class($exception),
168
$exception->getMessage());
169
}
170
171
}
172
173