@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
at recaptime-dev/main 94 lines 2.6 kB view raw
1<?php 2 3final class PhabricatorDefaultRequestExceptionHandler 4 extends PhabricatorRequestExceptionHandler { 5 6 public function getRequestExceptionHandlerPriority() { 7 return 900000; 8 } 9 10 public function getRequestExceptionHandlerDescription() { 11 return pht('Handles all other exceptions.'); 12 } 13 14 public function canHandleRequestThrowable( 15 AphrontRequest $request, 16 $throwable) { 17 18 if (!$this->isPhabricatorSite($request)) { 19 return false; 20 } 21 22 return true; 23 } 24 25 public function handleRequestThrowable( 26 AphrontRequest $request, 27 $throwable) { 28 29 $viewer = $this->getViewer($request); 30 31 // Some types of uninteresting request exceptions don't get logged, usually 32 // because they are caused by the background radiation of bot traffic on 33 // the internet. These include requests with bad CSRF tokens and 34 // questionable "Host" headers. 35 $should_log = true; 36 if ($throwable instanceof AphrontMalformedRequestException) { 37 $should_log = !$throwable->getIsUnlogged(); 38 } 39 40 if ($should_log) { 41 phlog($throwable); 42 } 43 44 $class = get_class($throwable); 45 46 if (PhabricatorEnv::getEnvConfig('phabricator.developer-mode')) { 47 // Include last location in error message 48 $message = '"'.$throwable->getMessage().'" at '. 49 PhutilErrorHandler::adjustFilePath($throwable->getFile()). 50 ':'.$throwable->getLine(); 51 } else { 52 $message = $throwable->getMessage(); 53 } 54 55 if ($throwable instanceof AphrontSchemaQueryException) { 56 $message .= "\n\n".pht( 57 "NOTE: This usually indicates that the MySQL schema has not been ". 58 "properly upgraded. Run '%s' to ensure your schema is up to date.", 59 'bin/storage upgrade'); 60 } 61 62 if (PhabricatorEnv::getEnvConfig('phabricator.developer-mode')) { 63 $trace = id(new AphrontStackTraceView()) 64 ->setViewer($viewer) 65 ->setTrace($throwable->getTrace()); 66 } else { 67 $trace = null; 68 } 69 70 $content = phutil_tag( 71 'div', 72 array('class' => 'aphront-unhandled-exception'), 73 array( 74 phutil_tag('div', array('class' => 'exception-message'), $message), 75 $trace, 76 )); 77 78 $dialog = new AphrontDialogView(); 79 $dialog 80 ->setTitle(pht('Unhandled Exception ("%s")', $class)) 81 ->setClass('aphront-exception-dialog') 82 ->setViewer($viewer) 83 ->appendChild($content); 84 85 if ($request->isAjax()) { 86 $dialog->addCancelButton('/', pht('Close')); 87 } 88 89 return id(new AphrontDialogResponse()) 90 ->setDialog($dialog) 91 ->setHTTPResponseCode(500); 92 } 93 94}