These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more
| 1 | <?php |
||
| 2 | /** |
||
| 3 | * @file |
||
| 4 | * Administrative page callbacks for the Database Logging module. |
||
| 5 | */ |
||
| 6 | |||
| 7 | use Drupal\Core\Logger\RfcLogLevel; |
||
| 8 | |||
| 9 | /** |
||
| 10 | * Display watchdogs entry details in MongoDB. |
||
| 11 | * |
||
| 12 | * @param array $dblog |
||
| 13 | */ |
||
| 14 | function mongodb_watchdog_event($dblog) { |
||
| 15 | $severity = watchdog_severity_levels(); |
||
| 16 | $rows = array( |
||
| 17 | array( |
||
| 18 | array('data' => t('Type'), 'header' => TRUE), |
||
| 19 | t($dblog['type']), |
||
| 20 | ), |
||
| 21 | array( |
||
| 22 | array('data' => t('Severity'), 'header' => TRUE), |
||
| 23 | $severity[$dblog['severity']], |
||
| 24 | ), |
||
| 25 | array( |
||
| 26 | array('data' => t('Function'), 'header' => TRUE), |
||
| 27 | isset($dblog['function']) ? $dblog['function'] : '', |
||
| 28 | ), |
||
| 29 | array( |
||
| 30 | array('data' => t('File'), 'header' => TRUE), |
||
| 31 | isset($dblog['file']) ? $dblog['file'] : '', |
||
| 32 | ), |
||
| 33 | array( |
||
| 34 | array('data' => t('Line'), 'header' => TRUE), |
||
| 35 | isset($dblog['line']) ? $dblog['line'] : '', |
||
| 36 | ), |
||
| 37 | array( |
||
| 38 | array('data' => t('Count'), 'header' => TRUE), |
||
| 39 | isset($dblog['count']) ? $dblog['count'] : '', |
||
| 40 | ), |
||
| 41 | ); |
||
| 42 | $build['reports'] = array( |
||
| 43 | '#type' => 'markup', |
||
| 44 | '#markup' => l(t('Return to log report'), 'admin/reports/mongodb'), |
||
| 45 | ); |
||
| 46 | $build['mongodb_watchdog_event_table']['header'] = array( |
||
| 47 | '#theme' => 'table', |
||
| 48 | '#rows' => $rows, |
||
| 49 | '#attributes' => array('class' => array('dblog-event')), |
||
| 50 | ); |
||
| 51 | // @todo: the count is unreliable, so just get the actual number of entries. |
||
| 52 | //$total = min($dblog['count'], variable_get('mongodb_watchdog_items', 10000)); |
||
| 53 | $collection = mongodb_collection(variable_get('mongodb_watchdog', 'watchdog')); |
||
| 54 | $collection = $collection->db->selectCollection('watchdog_event_' . $dblog['_id']); |
||
| 55 | $total = $collection->count(); |
||
| 56 | $limit = 20; |
||
| 57 | $pagenumber = mongodb_watchdog_pager_init(0, $limit, $total); |
||
| 58 | $result = $collection |
||
| 59 | ->find() |
||
| 60 | ->skip($pagenumber * $limit) |
||
| 61 | ->limit($limit) |
||
| 62 | ->sort(array('$natural' => -1)); |
||
| 63 | $severity = watchdog_severity_levels(); |
||
| 64 | $rows = array(); |
||
| 65 | $header = array( |
||
| 66 | array('data' => t('Date'), 'header' => TRUE), |
||
| 67 | array('data' => t('User'), 'header' => TRUE), |
||
| 68 | array('data' => t('Location'), 'header' => TRUE), |
||
| 69 | array('data' => t('Referrer'), 'header' => TRUE), |
||
| 70 | array('data' => t('Hostname'), 'header' => TRUE), |
||
| 71 | array('data' => t('Message'), 'header' => TRUE), |
||
| 72 | array('data' => t('Operations'), 'header' => TRUE), |
||
| 73 | ); |
||
| 74 | foreach ($result as $event) { |
||
| 75 | if (isset($event['wd-user'])) { |
||
| 76 | $account = $event['wd-user']; |
||
| 77 | unset($event['wd-user']); |
||
| 78 | $ip = $dblog['ip']; |
||
| 79 | $request_uri = $dblog['request_uri']; |
||
| 80 | $referer = $dblog['referer']; |
||
| 81 | $link = $dblog['link']; |
||
| 82 | $dblog['variables'] = $event; |
||
| 83 | } |
||
| 84 | else { |
||
| 85 | $account = $event['user']; |
||
| 86 | $ip = $event['ip']; |
||
| 87 | $request_uri = $event['request_uri']; |
||
| 88 | $referer = $event['referer']; |
||
| 89 | $link = $event['link']; |
||
| 90 | $dblog['variables'] = $event['variables']; |
||
| 91 | } |
||
| 92 | $rows[] = array( |
||
| 93 | format_date($event['timestamp'], 'short'), |
||
| 94 | l($account['name'], 'user/' . $account['uid']), |
||
| 95 | $request_uri ? l(truncate_utf8(basename(($request_uri)), 20), $request_uri) : '', |
||
| 96 | $referer ? l(truncate_utf8(basename(($referer)), 20), $referer) : '', |
||
| 97 | check_plain($ip), |
||
| 98 | _mongodb_watchdog_format_message($dblog), |
||
| 99 | $link, |
||
| 100 | ); |
||
| 101 | } |
||
| 102 | $build['mongodb_watchdog_event_table']['messages'] = array( |
||
| 103 | '#theme' => 'table', |
||
| 104 | '#header' => $header, |
||
| 105 | '#rows' => $rows, |
||
| 106 | ); |
||
| 107 | if ($total > $limit) { |
||
| 108 | $build['mongodb_watchdog_event_table']['pager'] = array( |
||
| 109 | '#theme' => 'pager', |
||
| 110 | ); |
||
| 111 | |||
| 112 | } |
||
| 113 | return $build; |
||
| 114 | } |
||
| 115 | |||
| 116 | /** |
||
| 117 | * Initialize the global pager variables for use in a mongodb_watchdog event list. |
||
| 118 | * |
||
| 119 | * @param int $element |
||
| 120 | * @param int $limit |
||
| 121 | * @param int $total |
||
| 122 | * |
||
| 123 | * @return int |
||
| 124 | */ |
||
| 125 | function mongodb_watchdog_pager_init($element, $limit, $total) { |
||
| 126 | global $pager_page_array, $pager_total, $pager_total_items; |
||
| 127 | |||
| 128 | // Initialize pager, see pager.inc. |
||
| 129 | $page = isset($_GET['page']) ? $_GET['page'] : ''; |
||
| 130 | $pager_page_array = explode(',', $page); |
||
| 131 | if (!isset($pager_page_array[$element])) { |
||
| 132 | $pager_page_array[$element] = 0; |
||
| 133 | } |
||
| 134 | $pager_total_items[$element] = $total; |
||
| 135 | $pager_total[$element] = ceil($pager_total_items[$element] / $limit); |
||
| 136 | $pager_page_array[$element] = max(0, min((int) $pager_page_array[$element], ((int) $pager_total[$element]) - 1)); |
||
| 137 | return isset($pager_page_array[$element]) ? $pager_page_array[$element] : 0; |
||
| 138 | } |
||
| 139 | |||
| 140 | /** |
||
| 141 | * Formats a log message for display. |
||
| 142 | * |
||
| 143 | * @param $dblog |
||
| 144 | * An object with at least the message and variables properties |
||
| 145 | * |
||
| 146 | * @return string |
||
| 147 | */ |
||
| 148 | function _mongodb_watchdog_format_message($dblog) { |
||
| 149 | // Legacy messages and user specified text |
||
| 150 | if (!isset($dblog['variables'])) { |
||
| 151 | return $dblog['message']; |
||
| 152 | } |
||
| 153 | // Message to translate with injected variables |
||
| 154 | return t($dblog['message'], $dblog['variables']); |
||
| 155 | } |
||
| 156 | |||
| 157 | /** |
||
| 158 | * Creates a list of database log administration filters that can be applied. |
||
| 159 | * |
||
| 160 | * @return array |
||
|
0 ignored issues
–
show
|
|||
| 161 | * Associative array of filters. The top-level keys are used as the form |
||
| 162 | * element names for the filters, and the values are arrays with the following |
||
| 163 | * elements: |
||
| 164 | * - title: Title of the filter. |
||
| 165 | * - where: The filter condition. |
||
| 166 | * - options: Array of options for the select list for the filter. |
||
| 167 | */ |
||
| 168 | function mongodb_watchdog_filters() { |
||
| 169 | $filters = array(); |
||
| 170 | |||
| 171 | foreach (_dblog_get_message_types() as $type) { |
||
| 172 | $types[$type] = t($type); |
||
|
0 ignored issues
–
show
Coding Style
Comprehensibility
introduced
by
$types was never initialized. Although not strictly required by PHP, it is generally a good practice to add $types = array(); before regardless.
Adding an explicit array definition is generally preferable to implicit array definition as it guarantees a stable state of the code. Let’s take a look at an example: foreach ($collection as $item) {
$myArray['foo'] = $item->getFoo();
if ($item->hasBar()) {
$myArray['bar'] = $item->getBar();
}
// do something with $myArray
}
As you can see in this example, the array This might or might not be intended. To make your intention clear, your code more readible and to avoid accidental bugs, we recommend to add an explicit initialization $myArray = array() either outside or inside the foreach loop. Loading history...
|
|||
| 173 | } |
||
| 174 | |||
| 175 | if (!empty($types)) { |
||
| 176 | $filters['type'] = array( |
||
| 177 | 'title' => t('Type'), |
||
| 178 | 'where' => "w.type = ?", |
||
| 179 | 'options' => $types, |
||
| 180 | ); |
||
| 181 | } |
||
| 182 | |||
| 183 | $filters['severity'] = array( |
||
| 184 | 'title' => t('Severity'), |
||
| 185 | 'where' => 'w.severity = ?', |
||
| 186 | 'options' => RfcLogLevel::getLevels(), |
||
| 187 | ); |
||
| 188 | |||
| 189 | return $filters; |
||
| 190 | } |
||
| 191 | |||
| 192 | /** |
||
| 193 | * Build the filter form. |
||
| 194 | * |
||
| 195 | * @return array |
||
|
0 ignored issues
–
show
|
|||
| 196 | * A form array |
||
| 197 | */ |
||
| 198 | function mongodb_watchdog_filter_form($form) { |
||
| 199 | $filters = mongodb_watchdog_filters(); |
||
| 200 | |||
| 201 | $form['filters'] = array( |
||
| 202 | '#type' => 'fieldset', |
||
| 203 | '#title' => t('Filter log messages'), |
||
| 204 | '#collapsible' => TRUE, |
||
| 205 | '#collapsed' => empty($_SESSION), |
||
| 206 | '#attached' => array( |
||
| 207 | 'css' => array( |
||
| 208 | drupal_get_path('module', 'mongodb_watchdog') . '/mongodb_watchdog.css', |
||
| 209 | )), |
||
| 210 | ); |
||
| 211 | |||
| 212 | View Code Duplication | foreach ($filters as $key => $filter) { |
|
|
0 ignored issues
–
show
This code seems to be duplicated across your project.
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation. You can also find more detailed suggestions in the “Code” section of your repository. Loading history...
|
|||
| 213 | $form['filters']['status'][$key] = array( |
||
| 214 | '#title' => check_plain($filter['title']), |
||
| 215 | '#type' => 'select', |
||
| 216 | '#multiple' => TRUE, |
||
| 217 | '#size' => 8, |
||
| 218 | '#options' => $filter['options'], |
||
| 219 | ); |
||
| 220 | if (!empty($_SESSION['mongodb_watchdog_overview_filter'][$key])) { |
||
| 221 | $form['filters']['status'][$key]['#default_value'] = $_SESSION['mongodb_watchdog_overview_filter'][$key]; |
||
| 222 | } |
||
| 223 | } |
||
| 224 | |||
| 225 | $form['filters']['buttons']['submit'] = array( |
||
| 226 | '#type' => 'submit', |
||
| 227 | '#value' => t('Filter'), |
||
| 228 | ); |
||
| 229 | if (!empty($_SESSION['mongodb_watchdog_overview_filter'])) { |
||
| 230 | $form['filters']['buttons']['reset'] = array( |
||
| 231 | '#type' => 'submit', |
||
| 232 | '#value' => t('Reset') |
||
| 233 | ); |
||
| 234 | } |
||
| 235 | |||
| 236 | return $form; |
||
| 237 | } |
||
| 238 | |||
| 239 | /** |
||
| 240 | * Validate result from mongodb_watchdog administration filter form. |
||
| 241 | */ |
||
| 242 | function mongodb_watchdog_filter_form_validate($form, &$form_state) { |
||
| 243 | if ($form_state['values']['op'] == t('Filter') && empty($form_state['values']['type']) && empty($form_state['values']['severity'])) { |
||
| 244 | form_set_error('type', t('You must select something to filter by.')); |
||
| 245 | } |
||
| 246 | } |
||
| 247 | |||
| 248 | /** |
||
| 249 | * Process result from mongodb_watchdog administration filter form. |
||
| 250 | */ |
||
| 251 | function mongodb_watchdog_filter_form_submit($form, &$form_state) { |
||
| 252 | $op = $form_state['values']['op']; |
||
| 253 | $filters = mongodb_watchdog_filters(); |
||
| 254 | switch ($op) { |
||
| 255 | case t('Filter'): |
||
| 256 | foreach ($filters as $name => $filter) { |
||
| 257 | if (isset($form_state['values'][$name])) { |
||
| 258 | $_SESSION['mongodb_watchdog_overview_filter'][$name] = $form_state['values'][$name]; |
||
| 259 | } |
||
| 260 | } |
||
| 261 | break; |
||
| 262 | |||
| 263 | case t('Reset'): |
||
| 264 | $_SESSION['mongodb_watchdog_overview_filter'] = array(); |
||
| 265 | break; |
||
| 266 | } |
||
| 267 | return 'admin/reports/mongodb'; |
||
| 268 | } |
||
| 269 | |||
| 270 | /** |
||
| 271 | * Gets all available filter types. |
||
| 272 | * |
||
| 273 | * @return array |
||
| 274 | * An array of message type names. |
||
| 275 | */ |
||
| 276 | function _mongodb_watchdog_get_message_types() { |
||
| 277 | // As of version 1.0.1, the PHP driver doesn't expose the 'distinct' command. |
||
| 278 | $collection = mongodb_collection(variable_get('mongodb_watchdog', 'watchdog')); |
||
| 279 | $result = $collection->db->command(array('distinct' => $collection->getName(), 'key' => 'type')); |
||
| 280 | return $result['values']; |
||
| 281 | } |
||
| 282 | |||
| 283 | /** |
||
| 284 | * Return form for mongodb_watchdog clear button. |
||
| 285 | * |
||
| 286 | * @ingroup forms |
||
| 287 | * @see dblog_clear_log_submit() |
||
| 288 | * |
||
| 289 | * @return array |
||
|
0 ignored issues
–
show
|
|||
| 290 | * A form array. |
||
| 291 | */ |
||
| 292 | function mongodb_watchdog_clear_log_form($form) { |
||
| 293 | $form['mongodb_watchdog_clear'] = array( |
||
| 294 | '#type' => 'fieldset', |
||
| 295 | '#title' => t('Clear log messages'), |
||
| 296 | '#description' => t('This will permanently remove the log messages from the database.'), |
||
| 297 | '#collapsible' => TRUE, |
||
| 298 | '#collapsed' => TRUE, |
||
| 299 | ); |
||
| 300 | |||
| 301 | $form['mongodb_watchdog_clear']['clear'] = array( |
||
| 302 | '#type' => 'submit', |
||
| 303 | '#value' => t('Clear log messages'), |
||
| 304 | '#submit' => array('mongodb_watchdog_clear_log_submit'), |
||
| 305 | ); |
||
| 306 | |||
| 307 | return $form; |
||
| 308 | } |
||
| 309 | |||
| 310 | /** |
||
| 311 | * Submit callback: clear database with log messages. |
||
| 312 | */ |
||
| 313 | function mongodb_watchdog_clear_log_submit() { |
||
| 314 | try { |
||
| 315 | // Drop the watchdog collection. |
||
| 316 | $collection = mongodb_collection(variable_get('mongodb_watchdog', 'watchdog')); |
||
| 317 | $collection->db->dropCollection($collection->getName()); |
||
| 318 | |||
| 319 | // Recreate the indexes. |
||
| 320 | module_load_include('install', 'mongodb_watchdog'); |
||
| 321 | mongodb_watchdog_ensure_indexes(); |
||
| 322 | |||
| 323 | // Drop the event collections. |
||
| 324 | foreach ($collection->db->listCollections() as $table) { |
||
| 325 | $parts = explode('.', $table); |
||
| 326 | if (substr($parts[1], 0, 15) == 'watchdog_event_') { |
||
| 327 | $collection->db->dropCollection($table); |
||
| 328 | } |
||
| 329 | } |
||
| 330 | |||
| 331 | drupal_set_message(t('MongoDB log cleared.')); |
||
| 332 | } |
||
| 333 | catch (Exception $e) { |
||
| 334 | drupal_set_message(t('An error occured while clearing the MongoDB log.'), 'error'); |
||
| 335 | } |
||
| 336 | } |
||
| 337 | |||
| 338 | /** |
||
| 339 | * Build a MongoDB query based on the selected filters. |
||
| 340 | * |
||
| 341 | * Refer to the @link https://jira.mongodb.org/browse/PHP-1051 Mongo Issue regarding the $in value @endlink |
||
| 342 | * Refer to the @link https://jira.mongodb.org/browse/PHP-104 Mongo Issue regarding numeric keys on objects @endlink |
||
| 343 | * @return array |
||
| 344 | * An array to build a MongoDB query. |
||
| 345 | */ |
||
| 346 | function mongodb_watchdog_build_filter_query() { |
||
| 347 | if (empty($_SESSION['mongodb_watchdog_overview_filter'])) { |
||
| 348 | return array(); |
||
| 349 | } |
||
| 350 | |||
| 351 | // Build query. |
||
| 352 | $where = $args = array(); |
||
| 353 | $types = $_SESSION['mongodb_watchdog_overview_filter']['type'] ? $_SESSION['mongodb_watchdog_overview_filter']['type'] : NULL; |
||
| 354 | $severities = $_SESSION['mongodb_watchdog_overview_filter']['severity'] ? $_SESSION['mongodb_watchdog_overview_filter']['severity'] : NULL; |
||
| 355 | |||
| 356 | $find = array(); |
||
| 357 | if ($types) { |
||
| 358 | $find['type'] = array('$in' => array_values($types)); |
||
| 359 | } |
||
| 360 | if ($severities) { |
||
| 361 | // MongoDB is picky about types, ensure the severities are all integers. |
||
| 362 | $find['severity'] = array('$in' => array_values(array_map('intval', $severities))); |
||
| 363 | } |
||
| 364 | return $find; |
||
| 365 | } |
||
| 366 |
This check looks for the generic type
arrayas a return type and suggests a more specific type. This type is inferred from the actual code.