comparison forum/Sources/ManageSearchEngines.php @ 76:e3e11437ecea website

Add forum code
author Chris Cannam
date Sun, 07 Jul 2013 11:25:48 +0200
parents
children
comparison
equal deleted inserted replaced
75:72f59aa7e503 76:e3e11437ecea
1 <?php
2
3 /**
4 * Simple Machines Forum (SMF)
5 *
6 * @package SMF
7 * @author Simple Machines http://www.simplemachines.org
8 * @copyright 2011 Simple Machines
9 * @license http://www.simplemachines.org/about/smf/license.php BSD
10 *
11 * @version 2.0
12 */
13
14 if (!defined('SMF'))
15 die('Hacking attempt...');
16
17 /* This file contains all the screens that relate to search engines.
18
19 // !!!
20 */
21
22 // Entry point for this section.
23 function SearchEngines()
24 {
25 global $context, $txt, $scripturl;
26
27 isAllowedTo('admin_forum');
28
29 loadLanguage('Search');
30 loadTemplate('ManageSearch');
31
32 $subActions = array(
33 'editspiders' => 'EditSpider',
34 'logs' => 'SpiderLogs',
35 'settings' => 'ManageSearchEngineSettings',
36 'spiders' => 'ViewSpiders',
37 'stats' => 'SpiderStats',
38 );
39
40 // Ensure we have a valid subaction.
41 $context['sub_action'] = isset($_REQUEST['sa']) && isset($subActions[$_REQUEST['sa']]) ? $_REQUEST['sa'] : 'stats';
42
43 $context['page_title'] = $txt['search_engines'];
44
45 // Some more tab data.
46 $context[$context['admin_menu_name']]['tab_data'] = array(
47 'title' => $txt['search_engines'],
48 'description' => $txt['search_engines_description'],
49 );
50
51 // Call the function!
52 $subActions[$context['sub_action']]();
53 }
54
55 // This is really just the settings page.
56 function ManageSearchEngineSettings($return_config = false)
57 {
58 global $context, $txt, $modSettings, $scripturl, $sourcedir, $smcFunc;
59
60 $config_vars = array(
61 // How much detail?
62 array('select', 'spider_mode', array($txt['spider_mode_off'], $txt['spider_mode_standard'], $txt['spider_mode_high'], $txt['spider_mode_vhigh']), 'onchange' => 'disableFields();'),
63 'spider_group' => array('select', 'spider_group', array($txt['spider_group_none'], $txt['membergroups_members'])),
64 array('select', 'show_spider_online', array($txt['show_spider_online_no'], $txt['show_spider_online_summary'], $txt['show_spider_online_detail'], $txt['show_spider_online_detail_admin'])),
65 );
66
67 // Set up a message.
68 $context['settings_message'] = '<span class="smalltext">' . sprintf($txt['spider_settings_desc'], $scripturl . '?action=admin;area=logs;sa=pruning;' . $context['session_var'] . '=' . $context['session_id']) . '</span>';
69
70 // Do some javascript.
71 $javascript_function = '
72 function disableFields()
73 {
74 disabledState = document.getElementById(\'spider_mode\').value == 0;';
75
76 foreach ($config_vars as $variable)
77 if ($variable[1] != 'spider_mode')
78 $javascript_function .= '
79 if (document.getElementById(\'' . $variable[1] . '\'))
80 document.getElementById(\'' . $variable[1] . '\').disabled = disabledState;';
81
82 $javascript_function .= '
83 }
84 disableFields();';
85
86 if ($return_config)
87 return $config_vars;
88
89 // We need to load the groups for the spider group thingy.
90 $request = $smcFunc['db_query']('', '
91 SELECT id_group, group_name
92 FROM {db_prefix}membergroups
93 WHERE id_group != {int:admin_group}
94 AND id_group != {int:moderator_group}',
95 array(
96 'admin_group' => 1,
97 'moderator_group' => 3,
98 )
99 );
100 while ($row = $smcFunc['db_fetch_assoc']($request))
101 $config_vars['spider_group'][2][$row['id_group']] = $row['group_name'];
102 $smcFunc['db_free_result']($request);
103
104 // Make sure it's valid - note that regular members are given id_group = 1 which is reversed in Load.php - no admins here!
105 if (isset($_POST['spider_group']) && !isset($config_vars['spider_group'][2][$_POST['spider_group']]))
106 $_POST['spider_group'] = 0;
107
108 // We'll want this for our easy save.
109 require_once($sourcedir . '/ManageServer.php');
110
111 // Setup the template.
112 $context['page_title'] = $txt['settings'];
113 $context['sub_template'] = 'show_settings';
114
115 // Are we saving them - are we??
116 if (isset($_GET['save']))
117 {
118 checkSession();
119
120 saveDBSettings($config_vars);
121 recacheSpiderNames();
122 redirectexit('action=admin;area=sengines;sa=settings');
123 }
124
125 // Final settings...
126 $context['post_url'] = $scripturl . '?action=admin;area=sengines;save;sa=settings';
127 $context['settings_title'] = $txt['settings'];
128 $context['settings_insert_below'] = '
129 <script type="text/javascript"><!-- // --><![CDATA[
130 ' . $javascript_function . '
131 // ]]></script>';
132
133 // Prepare the settings...
134 prepareDBSettingContext($config_vars);
135 }
136
137 // View a list of all the spiders we know about.
138 function ViewSpiders()
139 {
140 global $context, $txt, $sourcedir, $scripturl, $smcFunc;
141
142 if (!isset($_SESSION['spider_stat']) || $_SESSION['spider_stat'] < time() - 60)
143 {
144 consolidateSpiderStats();
145 $_SESSION['spider_stat'] = time();
146 }
147
148 // Are we adding a new one?
149 if (!empty($_POST['addSpider']))
150 return EditSpider();
151 // User pressed the 'remove selection button'.
152 elseif (!empty($_POST['removeSpiders']) && !empty($_POST['remove']) && is_array($_POST['remove']))
153 {
154 checkSession();
155
156 // Make sure every entry is a proper integer.
157 foreach ($_POST['remove'] as $index => $spider_id)
158 $_POST['remove'][(int) $index] = (int) $spider_id;
159
160 // Delete them all!
161 $smcFunc['db_query']('', '
162 DELETE FROM {db_prefix}spiders
163 WHERE id_spider IN ({array_int:remove_list})',
164 array(
165 'remove_list' => $_POST['remove'],
166 )
167 );
168 $smcFunc['db_query']('', '
169 DELETE FROM {db_prefix}log_spider_hits
170 WHERE id_spider IN ({array_int:remove_list})',
171 array(
172 'remove_list' => $_POST['remove'],
173 )
174 );
175 $smcFunc['db_query']('', '
176 DELETE FROM {db_prefix}log_spider_stats
177 WHERE id_spider IN ({array_int:remove_list})',
178 array(
179 'remove_list' => $_POST['remove'],
180 )
181 );
182
183 cache_put_data('spider_search', null, 300);
184 recacheSpiderNames();
185 }
186
187 // Get the last seens.
188 $request = $smcFunc['db_query']('', '
189 SELECT id_spider, MAX(last_seen) AS last_seen_time
190 FROM {db_prefix}log_spider_stats
191 GROUP BY id_spider',
192 array(
193 )
194 );
195
196 $context['spider_last_seen'] = array();
197 while ($row = $smcFunc['db_fetch_assoc']($request))
198 $context['spider_last_seen'][$row['id_spider']] = $row['last_seen_time'];
199 $smcFunc['db_free_result']($request);
200
201 $listOptions = array(
202 'id' => 'spider_list',
203 'items_per_page' => 20,
204 'base_href' => $scripturl . '?action=admin;area=sengines;sa=spiders',
205 'default_sort_col' => 'name',
206 'get_items' => array(
207 'function' => 'list_getSpiders',
208 ),
209 'get_count' => array(
210 'function' => 'list_getNumSpiders',
211 ),
212 'no_items_label' => $txt['spiders_no_entries'],
213 'columns' => array(
214 'name' => array(
215 'header' => array(
216 'value' => $txt['spider_name'],
217 ),
218 'data' => array(
219 'function' => create_function('$rowData', '
220 global $scripturl;
221
222 return sprintf(\'<a href="%1$s?action=admin;area=sengines;sa=editspiders;sid=%2$d">%3$s</a>\', $scripturl, $rowData[\'id_spider\'], htmlspecialchars($rowData[\'spider_name\']));
223 '),
224 ),
225 'sort' => array(
226 'default' => 'spider_name',
227 'reverse' => 'spider_name DESC',
228 ),
229 ),
230 'last_seen' => array(
231 'header' => array(
232 'value' => $txt['spider_last_seen'],
233 ),
234 'data' => array(
235 'function' => create_function('$rowData', '
236 global $context, $txt;
237
238 return isset($context[\'spider_last_seen\'][$rowData[\'id_spider\']]) ? timeformat($context[\'spider_last_seen\'][$rowData[\'id_spider\']]) : $txt[\'spider_last_never\'];
239 '),
240 ),
241 ),
242 'user_agent' => array(
243 'header' => array(
244 'value' => $txt['spider_agent'],
245 ),
246 'data' => array(
247 'db_htmlsafe' => 'user_agent',
248 ),
249 'sort' => array(
250 'default' => 'user_agent',
251 'reverse' => 'user_agent DESC',
252 ),
253 ),
254 'ip_info' => array(
255 'header' => array(
256 'value' => $txt['spider_ip_info'],
257 ),
258 'data' => array(
259 'db_htmlsafe' => 'ip_info',
260 'class' => 'smalltext',
261 ),
262 'sort' => array(
263 'default' => 'ip_info',
264 'reverse' => 'ip_info DESC',
265 ),
266 ),
267 'check' => array(
268 'header' => array(
269 'value' => '<input type="checkbox" onclick="invertAll(this, this.form);" class="input_check" />',
270 ),
271 'data' => array(
272 'sprintf' => array(
273 'format' => '<input type="checkbox" name="remove[]" value="%1$d" class="input_check" />',
274 'params' => array(
275 'id_spider' => false,
276 ),
277 ),
278 'style' => 'text-align: center',
279 ),
280 ),
281 ),
282 'form' => array(
283 'href' => $scripturl . '?action=admin;area=sengines;sa=spiders',
284 ),
285 'additional_rows' => array(
286 array(
287 'position' => 'below_table_data',
288 'value' => '
289 <input type="submit" name="addSpider" value="' . $txt['spiders_add'] . '" class="button_submit" />
290 <input type="submit" name="removeSpiders" value="' . $txt['spiders_remove_selected'] . '" onclick="return confirm(\'' . $txt['spider_remove_selected_confirm'] . '\');" class="button_submit" />
291 ',
292 'style' => 'text-align: right;',
293 ),
294 ),
295 );
296
297 require_once($sourcedir . '/Subs-List.php');
298 createList($listOptions);
299
300 $context['sub_template'] = 'show_list';
301 $context['default_list'] = 'spider_list';
302 }
303
304 function list_getSpiders($start, $items_per_page, $sort)
305 {
306 global $smcFunc;
307
308 $request = $smcFunc['db_query']('', '
309 SELECT id_spider, spider_name, user_agent, ip_info
310 FROM {db_prefix}spiders
311 ORDER BY ' . $sort . '
312 LIMIT ' . $start . ', ' . $items_per_page,
313 array(
314 )
315 );
316 $spiders = array();
317 while ($row = $smcFunc['db_fetch_assoc']($request))
318 $spiders[$row['id_spider']] = $row;
319 $smcFunc['db_free_result']($request);
320
321 return $spiders;
322 }
323
324 function list_getNumSpiders()
325 {
326 global $smcFunc;
327
328 $request = $smcFunc['db_query']('', '
329 SELECT COUNT(*) AS num_spiders
330 FROM {db_prefix}spiders',
331 array(
332 )
333 );
334 list ($numSpiders) = $smcFunc['db_fetch_row']($request);
335 $smcFunc['db_free_result']($request);
336
337 return $numSpiders;
338 }
339
340 // Here we can add, and edit, spider info!
341 function EditSpider()
342 {
343 global $context, $smcFunc, $txt;
344
345 // Some standard stuff.
346 $context['id_spider'] = !empty($_GET['sid']) ? (int) $_GET['sid'] : 0;
347 $context['page_title'] = $context['id_spider'] ? $txt['spiders_edit'] : $txt['spiders_add'];
348 $context['sub_template'] = 'spider_edit';
349
350 // Are we saving?
351 if (!empty($_POST['save']))
352 {
353 checkSession();
354
355 $ips = array();
356 // Check the IP range is valid.
357 $ip_sets = explode(',', $_POST['spider_ip']);
358 foreach ($ip_sets as $set)
359 {
360 $test = ip2range(trim($set));
361 if (!empty($test))
362 $ips[] = $set;
363 }
364 $ips = implode(',', $ips);
365
366 // Goes in as it is...
367 if ($context['id_spider'])
368 $smcFunc['db_query']('', '
369 UPDATE {db_prefix}spiders
370 SET spider_name = {string:spider_name}, user_agent = {string:spider_agent},
371 ip_info = {string:ip_info}
372 WHERE id_spider = {int:current_spider}',
373 array(
374 'current_spider' => $context['id_spider'],
375 'spider_name' => $_POST['spider_name'],
376 'spider_agent' => $_POST['spider_agent'],
377 'ip_info' => $ips,
378 )
379 );
380 else
381 $smcFunc['db_insert']('insert',
382 '{db_prefix}spiders',
383 array(
384 'spider_name' => 'string', 'user_agent' => 'string', 'ip_info' => 'string',
385 ),
386 array(
387 $_POST['spider_name'], $_POST['spider_agent'], $ips,
388 ),
389 array('id_spider')
390 );
391
392 // Order by user agent length.
393 sortSpiderTable();
394
395 cache_put_data('spider_search', null, 300);
396 recacheSpiderNames();
397
398 redirectexit('action=admin;area=sengines;sa=spiders');
399 }
400
401 // The default is new.
402 $context['spider'] = array(
403 'id' => 0,
404 'name' => '',
405 'agent' => '',
406 'ip_info' => '',
407 );
408
409 // An edit?
410 if ($context['id_spider'])
411 {
412 $request = $smcFunc['db_query']('', '
413 SELECT id_spider, spider_name, user_agent, ip_info
414 FROM {db_prefix}spiders
415 WHERE id_spider = {int:current_spider}',
416 array(
417 'current_spider' => $context['id_spider'],
418 )
419 );
420 if ($row = $smcFunc['db_fetch_assoc']($request))
421 $context['spider'] = array(
422 'id' => $row['id_spider'],
423 'name' => $row['spider_name'],
424 'agent' => $row['user_agent'],
425 'ip_info' => $row['ip_info'],
426 );
427 $smcFunc['db_free_result']($request);
428 }
429
430 }
431
432 //!!! Should this not be... you know... in a different file?
433 // Do we think the current user is a spider?
434 function SpiderCheck()
435 {
436 global $modSettings, $smcFunc;
437
438 if (isset($_SESSION['id_robot']))
439 unset($_SESSION['id_robot']);
440 $_SESSION['robot_check'] = time();
441
442 // We cache the spider data for five minutes if we can.
443 if (!empty($modSettings['cache_enable']))
444 $spider_data = cache_get_data('spider_search', 300);
445
446 if (!isset($spider_data) || $spider_data === NULL)
447 {
448 $request = $smcFunc['db_query']('spider_check', '
449 SELECT id_spider, user_agent, ip_info
450 FROM {db_prefix}spiders',
451 array(
452 )
453 );
454 $spider_data = array();
455 while ($row = $smcFunc['db_fetch_assoc']($request))
456 $spider_data[] = $row;
457 $smcFunc['db_free_result']($request);
458
459 if (!empty($modSettings['cache_enable']))
460 cache_put_data('spider_search', $spider_data, 300);
461 }
462
463 if (empty($spider_data))
464 return false;
465
466 // Only do these bits once.
467 $ci_user_agent = strtolower($_SERVER['HTTP_USER_AGENT']);
468 preg_match('/^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/', $_SERVER['REMOTE_ADDR'], $ip_parts);
469
470 foreach ($spider_data as $spider)
471 {
472 // User agent is easy.
473 if (!empty($spider['user_agent']) && strpos($ci_user_agent, strtolower($spider['user_agent'])) !== false)
474 $_SESSION['id_robot'] = $spider['id_spider'];
475 // IP stuff is harder.
476 elseif (!empty($ip_parts))
477 {
478 $ips = explode(',', $spider['ip_info']);
479 foreach ($ips as $ip)
480 {
481 $ip = ip2range($ip);
482 if (!empty($ip))
483 {
484 foreach ($ip as $key => $value)
485 {
486 if ($value['low'] > $ip_parts[$key + 1] || $value['high'] < $ip_parts[$key + 1])
487 break;
488 elseif ($key == 3)
489 $_SESSION['id_robot'] = $spider['id_spider'];
490 }
491 }
492 }
493 }
494
495 if (isset($_SESSION['id_robot']))
496 break;
497 }
498
499 // If this is low server tracking then log the spider here as oppossed to the main logging function.
500 if (!empty($modSettings['spider_mode']) && $modSettings['spider_mode'] == 1 && !empty($_SESSION['id_robot']))
501 logSpider();
502
503 return !empty($_SESSION['id_robot']) ? $_SESSION['id_robot'] : 0;
504 }
505
506 // Log the spider presence online.
507 //!!! Different file?
508 function logSpider()
509 {
510 global $smcFunc, $modSettings, $context;
511
512 if (empty($modSettings['spider_mode']) || empty($_SESSION['id_robot']))
513 return;
514
515 // Attempt to update today's entry.
516 if ($modSettings['spider_mode'] == 1)
517 {
518 $date = strftime('%Y-%m-%d', forum_time(false));
519 $smcFunc['db_query']('', '
520 UPDATE {db_prefix}log_spider_stats
521 SET last_seen = {int:current_time}, page_hits = page_hits + 1
522 WHERE id_spider = {int:current_spider}
523 AND stat_date = {date:current_date}',
524 array(
525 'current_date' => $date,
526 'current_time' => time(),
527 'current_spider' => $_SESSION['id_robot'],
528 )
529 );
530
531 // Nothing updated?
532 if ($smcFunc['db_affected_rows']() == 0)
533 {
534 $smcFunc['db_insert']('ignore',
535 '{db_prefix}log_spider_stats',
536 array(
537 'id_spider' => 'int', 'last_seen' => 'int', 'stat_date' => 'date', 'page_hits' => 'int',
538 ),
539 array(
540 $_SESSION['id_robot'], time(), $date, 1,
541 ),
542 array('id_spider', 'stat_date')
543 );
544 }
545 }
546 // If we're tracking better stats than track, better stats - we sort out the today thing later.
547 else
548 {
549 if ($modSettings['spider_mode'] > 2)
550 {
551 $url = $_GET + array('USER_AGENT' => $_SERVER['HTTP_USER_AGENT']);
552 unset($url['sesc'], $url[$context['session_var']]);
553 $url = serialize($url);
554 }
555 else
556 $url = '';
557
558 $smcFunc['db_insert']('insert',
559 '{db_prefix}log_spider_hits',
560 array('id_spider' => 'int', 'log_time' => 'int', 'url' => 'string'),
561 array($_SESSION['id_robot'], time(), $url),
562 array()
563 );
564 }
565 }
566
567 // This function takes any unprocessed hits and turns them into stats.
568 function consolidateSpiderStats()
569 {
570 global $smcFunc;
571
572 $request = $smcFunc['db_query']('consolidate_spider_stats', '
573 SELECT id_spider, MAX(log_time) AS last_seen, COUNT(*) AS num_hits
574 FROM {db_prefix}log_spider_hits
575 WHERE processed = {int:not_processed}
576 GROUP BY id_spider, MONTH(log_time), DAYOFMONTH(log_time)',
577 array(
578 'not_processed' => 0,
579 )
580 );
581 $spider_hits = array();
582 while ($row = $smcFunc['db_fetch_assoc']($request))
583 $spider_hits[] = $row;
584 $smcFunc['db_free_result']($request);
585
586 if (empty($spider_hits))
587 return;
588
589 // Attempt to update the master data.
590 $stat_inserts = array();
591 foreach ($spider_hits as $stat)
592 {
593 // We assume the max date is within the right day.
594 $date = strftime('%Y-%m-%d', $stat['last_seen']);
595 $smcFunc['db_query']('', '
596 UPDATE {db_prefix}log_spider_stats
597 SET page_hits = page_hits + ' . $stat['num_hits'] . ',
598 last_seen = CASE WHEN last_seen > {int:last_seen} THEN last_seen ELSE {int:last_seen} END
599 WHERE id_spider = {int:current_spider}
600 AND stat_date = {date:last_seen_date}',
601 array(
602 'last_seen_date' => $date,
603 'last_seen' => $stat['last_seen'],
604 'current_spider' => $stat['id_spider'],
605 )
606 );
607 if ($smcFunc['db_affected_rows']() == 0)
608 $stat_inserts[] = array($date, $stat['id_spider'], $stat['num_hits'], $stat['last_seen']);
609 }
610
611 // New stats?
612 if (!empty($stat_inserts))
613 $smcFunc['db_insert']('ignore',
614 '{db_prefix}log_spider_stats',
615 array('stat_date' => 'date', 'id_spider' => 'int', 'page_hits' => 'int', 'last_seen' => 'int'),
616 $stat_inserts,
617 array('stat_date', 'id_spider')
618 );
619
620 // All processed.
621 $smcFunc['db_query']('', '
622 UPDATE {db_prefix}log_spider_hits
623 SET processed = {int:is_processed}
624 WHERE processed = {int:not_processed}',
625 array(
626 'is_processed' => 1,
627 'not_processed' => 0,
628 )
629 );
630 }
631
632 // See what spiders have been up to.
633 function SpiderLogs()
634 {
635 global $context, $txt, $sourcedir, $scripturl, $smcFunc, $modSettings;
636
637 // Load the template and language just incase.
638 loadLanguage('Search');
639 loadTemplate('ManageSearch');
640
641 // Did they want to delete some entries?
642 if (!empty($_POST['delete_entries']) && isset($_POST['older']))
643 {
644 checkSession();
645
646 $deleteTime = time() - (((int) $_POST['older']) * 24 * 60 * 60);
647
648 // Delete the entires.
649 $smcFunc['db_query']('', '
650 DELETE FROM {db_prefix}log_spider_hits
651 WHERE log_time < {int:delete_period}',
652 array(
653 'delete_period' => $deleteTime,
654 )
655 );
656 }
657
658 $listOptions = array(
659 'id' => 'spider_logs',
660 'items_per_page' => 20,
661 'title' => $txt['spider_logs'],
662 'no_items_label' => $txt['spider_logs_empty'],
663 'base_href' => $context['admin_area'] == 'sengines' ? $scripturl . '?action=admin;area=sengines;sa=logs' : $scripturl . '?action=admin;area=logs;sa=spiderlog',
664 'default_sort_col' => 'log_time',
665 'get_items' => array(
666 'function' => 'list_getSpiderLogs',
667 ),
668 'get_count' => array(
669 'function' => 'list_getNumSpiderLogs',
670 ),
671 'columns' => array(
672 'name' => array(
673 'header' => array(
674 'value' => $txt['spider'],
675 ),
676 'data' => array(
677 'db' => 'spider_name',
678 ),
679 'sort' => array(
680 'default' => 's.spider_name',
681 'reverse' => 's.spider_name DESC',
682 ),
683 ),
684 'log_time' => array(
685 'header' => array(
686 'value' => $txt['spider_time'],
687 ),
688 'data' => array(
689 'function' => create_function('$rowData', '
690 return timeformat($rowData[\'log_time\']);
691 '),
692 ),
693 'sort' => array(
694 'default' => 'sl.id_hit DESC',
695 'reverse' => 'sl.id_hit',
696 ),
697 ),
698 'viewing' => array(
699 'header' => array(
700 'value' => $txt['spider_viewing'],
701 ),
702 'data' => array(
703 'db' => 'url',
704 ),
705 ),
706 ),
707 'additional_rows' => array(
708 array(
709 'position' => 'after_title',
710 'value' => $txt['spider_logs_info'],
711 'class' => 'smalltext',
712 ),
713 ),
714 );
715
716 require_once($sourcedir . '/Subs-List.php');
717 createList($listOptions);
718
719 // Now determine the actions of the URLs.
720 if (!empty($context['spider_logs']['rows']))
721 {
722 $urls = array();
723 // Grab the current /url.
724 foreach ($context['spider_logs']['rows'] as $k => $row)
725 {
726 // Feature disabled?
727 if (empty($row['viewing']['value']) && isset($modSettings['spider_mode']) && $modSettings['spider_mode'] < 3)
728 $context['spider_logs']['rows'][$k]['viewing']['value'] = '<em>' . $txt['spider_disabled'] . '</em>';
729 else
730 $urls[$k] = array($row['viewing']['value'], -1);
731 }
732
733 // Now stick in the new URLs.
734 require_once($sourcedir . '/Who.php');
735 $urls = determineActions($urls, 'whospider_');
736 foreach ($urls as $k => $new_url)
737 {
738 $context['spider_logs']['rows'][$k]['viewing']['value'] = $new_url;
739 }
740 }
741
742 $context['page_title'] = $txt['spider_logs'];
743 $context['sub_template'] = 'show_spider_logs';
744 $context['default_list'] = 'spider_logs';
745 }
746
747 function list_getSpiderLogs($start, $items_per_page, $sort)
748 {
749 global $smcFunc;
750
751 $request = $smcFunc['db_query']('', '
752 SELECT sl.id_spider, sl.url, sl.log_time, s.spider_name
753 FROM {db_prefix}log_spider_hits AS sl
754 INNER JOIN {db_prefix}spiders AS s ON (s.id_spider = sl.id_spider)
755 ORDER BY ' . $sort . '
756 LIMIT ' . $start . ', ' . $items_per_page,
757 array(
758 )
759 );
760 $spider_logs = array();
761 while ($row = $smcFunc['db_fetch_assoc']($request))
762 $spider_logs[] = $row;
763 $smcFunc['db_free_result']($request);
764
765 return $spider_logs;
766 }
767
768 function list_getNumSpiderLogs()
769 {
770 global $smcFunc;
771
772 $request = $smcFunc['db_query']('', '
773 SELECT COUNT(*) AS num_logs
774 FROM {db_prefix}log_spider_hits',
775 array(
776 )
777 );
778 list ($numLogs) = $smcFunc['db_fetch_row']($request);
779 $smcFunc['db_free_result']($request);
780
781 return $numLogs;
782 }
783
784 // Show the spider statistics.
785 function SpiderStats()
786 {
787 global $context, $txt, $sourcedir, $scripturl, $smcFunc;
788
789 // Force an update of the stats every 60 seconds.
790 if (!isset($_SESSION['spider_stat']) || $_SESSION['spider_stat'] < time() - 60)
791 {
792 consolidateSpiderStats();
793 $_SESSION['spider_stat'] = time();
794 }
795
796 // Get the earliest and latest dates.
797 $request = $smcFunc['db_query']('', '
798 SELECT MIN(stat_date) AS first_date, MAX(stat_date) AS last_date
799 FROM {db_prefix}log_spider_stats',
800 array(
801 )
802 );
803
804 list ($min_date, $max_date) = $smcFunc['db_fetch_row']($request);
805 $smcFunc['db_free_result']($request);
806
807 $min_year = (int) substr($min_date, 0, 4);
808 $max_year = (int) substr($max_date, 0, 4);
809 $min_month = (int) substr($min_date, 5, 2);
810 $max_month = (int) substr($max_date, 5, 2);
811
812 // Prepare the dates for the drop down.
813 $date_choices = array();
814 for ($y = $min_year; $y <= $max_year; $y++)
815 for ($m = 1; $m <= 12; $m++)
816 {
817 // This doesn't count?
818 if ($y == $min_year && $m < $min_month)
819 continue;
820 if ($y == $max_year && $m > $max_month)
821 break;
822
823 $date_choices[$y . $m] = $txt['months_short'][$m] . ' ' . $y;
824 }
825
826 // What are we currently viewing?
827 $current_date = isset($_REQUEST['new_date']) && isset($date_choices[$_REQUEST['new_date']]) ? $_REQUEST['new_date'] : $max_date;
828
829 // Prepare the HTML.
830 $date_select = '
831 ' . $txt['spider_stats_select_month'] . ':
832 <select name="new_date" onchange="document.spider_stat_list.submit();">';
833
834 if (empty($date_choices))
835 $date_select .= '
836 <option></option>';
837 else
838 foreach ($date_choices as $id => $text)
839 $date_select .= '
840 <option value="' . $id . '"' . ($current_date == $id ? ' selected="selected"' : '') . '>' . $text . '</option>';
841
842 $date_select .= '
843 </select>
844 <noscript>
845 <input type="submit" name="go" value="' . $txt['go'] . '" class="button_submit" />
846 </noscript>';
847
848 // If we manually jumped to a date work out the offset.
849 if (isset($_REQUEST['new_date']))
850 {
851 $date_query = sprintf('%04d-%02d-01', substr($current_date, 0, 4), substr($current_date, 4));
852
853 $request = $smcFunc['db_query']('', '
854 SELECT COUNT(*) AS offset
855 FROM {db_prefix}log_spider_stats
856 WHERE stat_date < {date:date_being_viewed}',
857 array(
858 'date_being_viewed' => $date_query,
859 )
860 );
861 list ($_REQUEST['start']) = $smcFunc['db_fetch_row']($request);
862 $smcFunc['db_free_result']($request);
863 }
864
865 $listOptions = array(
866 'id' => 'spider_stat_list',
867 'items_per_page' => 20,
868 'base_href' => $scripturl . '?action=admin;area=sengines;sa=stats',
869 'default_sort_col' => 'stat_date',
870 'get_items' => array(
871 'function' => 'list_getSpiderStats',
872 ),
873 'get_count' => array(
874 'function' => 'list_getNumSpiderStats',
875 ),
876 'no_items_label' => $txt['spider_stats_no_entries'],
877 'columns' => array(
878 'stat_date' => array(
879 'header' => array(
880 'value' => $txt['date'],
881 ),
882 'data' => array(
883 'db' => 'stat_date',
884 ),
885 'sort' => array(
886 'default' => 'stat_date',
887 'reverse' => 'stat_date DESC',
888 ),
889 ),
890 'name' => array(
891 'header' => array(
892 'value' => $txt['spider_name'],
893 ),
894 'data' => array(
895 'db' => 'spider_name',
896 ),
897 'sort' => array(
898 'default' => 's.spider_name',
899 'reverse' => 's.spider_name DESC',
900 ),
901 ),
902 'page_hits' => array(
903 'header' => array(
904 'value' => $txt['spider_stats_page_hits'],
905 ),
906 'data' => array(
907 'db' => 'page_hits',
908 ),
909 'sort' => array(
910 'default' => 'ss.page_hits',
911 'reverse' => 'ss.page_hits DESC',
912 ),
913 ),
914 ),
915 'form' => array(
916 'href' => $scripturl . '?action=admin;area=sengines;sa=stats',
917 'name' => 'spider_stat_list',
918 ),
919 'additional_rows' => array(
920 array(
921 'position' => 'below_table_data',
922 'value' => $date_select,
923 'style' => 'text-align: right;',
924 ),
925 ),
926 );
927
928 require_once($sourcedir . '/Subs-List.php');
929 createList($listOptions);
930
931 $context['sub_template'] = 'show_list';
932 $context['default_list'] = 'spider_stat_list';
933 }
934
935 function list_getSpiderStats($start, $items_per_page, $sort)
936 {
937 global $smcFunc;
938
939 $request = $smcFunc['db_query']('', '
940 SELECT ss.id_spider, ss.stat_date, ss.page_hits, s.spider_name
941 FROM {db_prefix}log_spider_stats AS ss
942 INNER JOIN {db_prefix}spiders AS s ON (s.id_spider = ss.id_spider)
943 ORDER BY ' . $sort . '
944 LIMIT ' . $start . ', ' . $items_per_page,
945 array(
946 )
947 );
948 $spider_stats = array();
949 while ($row = $smcFunc['db_fetch_assoc']($request))
950 $spider_stats[] = $row;
951 $smcFunc['db_free_result']($request);
952
953 return $spider_stats;
954 }
955
956 function list_getNumSpiderStats()
957 {
958 global $smcFunc;
959
960 $request = $smcFunc['db_query']('', '
961 SELECT COUNT(*) AS num_stats
962 FROM {db_prefix}log_spider_stats',
963 array(
964 )
965 );
966 list ($numStats) = $smcFunc['db_fetch_row']($request);
967 $smcFunc['db_free_result']($request);
968
969 return $numStats;
970 }
971
972 // Recache spider names?
973 function recacheSpiderNames()
974 {
975 global $smcFunc;
976
977 $request = $smcFunc['db_query']('', '
978 SELECT id_spider, spider_name
979 FROM {db_prefix}spiders',
980 array(
981 )
982 );
983 $spiders = array();
984 while ($row = $smcFunc['db_fetch_assoc']($request))
985 $spiders[$row['id_spider']] = $row['spider_name'];
986 $smcFunc['db_free_result']($request);
987
988 updateSettings(array('spider_name_cache' => serialize($spiders)));
989 }
990
991 // Sort the search engine table by user agent name to avoid misidentification of engine.
992 function sortSpiderTable()
993 {
994 global $smcFunc;
995
996 db_extend('packages');
997
998 // Add a sorting column.
999 $smcFunc['db_add_column']('{db_prefix}spiders', array('name' => 'temp_order', 'size' => 8, 'type' => 'mediumint', 'null' => false));
1000
1001 // Set the contents of this column.
1002 $smcFunc['db_query']('set_spider_order', '
1003 UPDATE {db_prefix}spiders
1004 SET temp_order = LENGTH(user_agent)',
1005 array(
1006 )
1007 );
1008
1009 // Order the table by this column.
1010 $smcFunc['db_query']('alter_table_spiders', '
1011 ALTER TABLE {db_prefix}spiders
1012 ORDER BY temp_order DESC',
1013 array(
1014 'db_error_skip' => true,
1015 )
1016 );
1017
1018 // Remove the sorting column.
1019 $smcFunc['db_remove_column']('{db_prefix}spiders', 'temp_order');
1020 }
1021
1022 ?>