Zend Database Adapter - Неисследованное исключение - трассировка стека показывает имя пользователя и пароль - PullRequest
3 голосов
/ 14 февраля 2012

Я использую Zend_Db_Adapter, в частности Zend_Db_Adapter_Pdo_Abstract.Я полагаю, что эта проблема распространяется и на другие адаптеры.Когда выбрасывается PDOException, это «неосторожно», и во многих случаях трассировка стека раскрывает имя пользователя и пароль.

Я проверил, что все следующие исключения PDO показывают учетные данные в трассировке стека:

  • SQLSTATE [HY000] [2005] Неизвестный хост сервера MySQL ... snip ...
  • SQLSTATE [HY000] [2013] Потеряно соединение сСервер MySQL в «пакете авторизации чтения»
  • SQLSTATE [08004] [1040] Слишком много соединений
  • SQLSTATE [28000] [1045] Доступ запрещен для пользователя ... snip ... (используя пароль: ДА)

Мои производственные сайты не показывают трассировки стека при наличии ошибок, и я все еще хочу видеть трассировки стека для этих ошибок в моих средах разработки, япросто не хочу, чтобы имена пользователей и пароли отображались в открытом виде.

Ответы [ 2 ]

3 голосов
/ 14 февраля 2012

Я бы решил это, не решая ... Позвольте мне объяснить:

В настоящее время нет способа отключить трассировки стека от необработанных исключений. PHP не позволяет вам сделать это.

Таким образом, вместо того, чтобы пытаться отключить его, я бы просто не позволил исключению остаться необработанным ... Я бы установил обработчик исключений , который бы затем регистрировал ответ -трекать информацию. Я бы не отображал это на экране. Я не проверю, в какой среде он находится. Я не проверю информацию запроса. Я просто записал бы его в файл и отобразил бы общую страницу 500 ошибок сервера.

Теперь в вашем обработчике вы можете выборочно показывать информацию о вызове, чтобы вы могли выбирать, регистрировать или нет информацию об аргументах:

set_exception_handler(function($exception) {
    $log = array(
        'message' => $exception->getMessage(),
        'trace' => array(),
    );
    foreach ($exception->getTrace() as $item) {
        $trace = isset($item['class']) ? $item['class'] . $item['type'] : '';
        $trace .= $item['function'] . '()';
        $log['trace'][] = $trace;
    }
    save_to_log($log);
});

Но я принимаю непонятное исключение как признак ошибки в вашем приложении. Вы должны найти их и исправить их. Если вы получаете их достаточно, чтобы беспокоиться о представлении аргументов на странице, то вам действительно нужно исправить тот факт, что в первую очередь существуют необъяснимые исключения ...

Редактировать Вот демонстрация того, что происходит:

class Foo {
    public function doSomething($user, $password) {
        throw new Exception('Something Went Wrong!');
    }
}

$f = new Foo();

$f->doSomething('user', 'passw');

на CodePad Результат:

<br />
<b>Fatal error</b>:  Uncaught exception 'Exception' with message 'Something Went Wrong!' in /code/MxH9Ls:4
Stack trace:
#0 /code/MxH9Ls(10): Foo-&gt;doSomething('user', 'passw')
#1 {main}
  thrown in <b>/code/MxH9Ls</b> on line <b>4</b><br />

Но, с обработчиком исключений (изменен для печати вместо журнала):

set_exception_handler(function($exception) {
    $log = array(
        'message' => $exception->getMessage(),
        'trace' => array(),
    );
    foreach ($exception->getTrace() as $item) {
        $trace = isset($item['class']) ? $item['class'] . $item['type'] : '';
        $trace .= $item['function'] . '()';
        $log['trace'][] = $trace;
    }
    echo $log['message'] . "\n";
    foreach ($log['trace'] as $trace) {
        echo " - $trace\n";
    }
});

class Foo {
    public function doSomething($user, $password) {
        throw new Exception('Something Went Wrong!');
    }
}

$f = new Foo();

$f->doSomething('user', 'passw');

На CodePad производит:

Something Went Wrong!
 - Foo->doSomething()
1 голос
/ 14 февраля 2012

Есть две вещи, которые вы можете попробовать, первое и, вероятно, лучшее решение - перехватить исключения и передать их в пользовательский класс исключений.Класс также будет принимать экземпляр адаптера, например:

Непроверенный пример

class myPDOException extends Exception
{
     public function __construct($message = '', $code = 0, Exception $previous = null, Zend_Db_Adapter_Abstract $adapter) {
        $config = $adapter->getConfig();
        $message = str_replace(array($config['username'], $config['password']), array('--user--', '--pass--'));
        parent::__construct($message, $code, $previous);
     }         
}

Другой вариант - использовать set_exception_handler после регистрации вваш загрузчик, если env разрабатывается, тогда вы можете сделать следующее:

function exception_handler($exception) {
    if ($exception instanceof PDOException) {
        //load your configuration
        //replace the user pass in the message
        //rethrow the exceptio with the updated message
    }
}

set_exception_handler('exception_handler');

Способ обработки непредвиденных исключений состоит в том, чтобы сохранить их в очереди, которая затем отправляет мне по электронной почте всю необходимую информацию, и мы можем исправитьпричина исключения.

Надеюсь, что поможет

Jay

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...