Quellcode durchsuchen

[fix] proper search timeout handling

Adam Tauber vor 10 Jahren
Ursprung
Commit
a5324d9d82
1 geänderte Dateien mit 19 neuen und 6 gelöschten Zeilen
  1. 19
    6
      searx/search.py

+ 19
- 6
searx/search.py Datei anzeigen

@@ -21,6 +21,8 @@ import re
21 21
 from itertools import izip_longest, chain
22 22
 from datetime import datetime
23 23
 from operator import itemgetter
24
+from Queue import Queue
25
+from time import time
24 26
 from urlparse import urlparse, unquote
25 27
 from searx.engines import (
26 28
     categories, engines
@@ -34,6 +36,8 @@ number_of_searches = 0
34 36
 
35 37
 
36 38
 def threaded_requests(requests):
39
+    timeout_limit = max(r[2]['timeout'] for r in requests)
40
+    search_start = time()
37 41
     for fn, url, request_args in requests:
38 42
         th = threading.Thread(
39 43
             target=fn,
@@ -45,7 +49,11 @@ def threaded_requests(requests):
45 49
 
46 50
     for th in threading.enumerate():
47 51
         if th.name == 'search_request':
48
-            th.join()
52
+            remaining_time = max(0.0, timeout_limit - (time() - search_start))
53
+            th.join(remaining_time)
54
+            if th.isAlive():
55
+                print('engine timeout')
56
+
49 57
 
50 58
 
51 59
 # get default reqest parameter
@@ -56,7 +64,7 @@ def default_request_params():
56 64
 
57 65
 # create a callback wrapper for the search engine results
58 66
 def make_callback(engine_name,
59
-                  results,
67
+                  results_queue,
60 68
                   suggestions,
61 69
                   answers,
62 70
                   infoboxes,
@@ -74,7 +82,7 @@ def make_callback(engine_name,
74 82
         except Exception, e:
75 83
             # increase errors stats
76 84
             engines[engine_name].stats['errors'] += 1
77
-            results[engine_name] = cb_res
85
+            results_queue.put_nowait((engine_name, cb_res))
78 86
 
79 87
             # print engine name and specific error message
80 88
             print '[E] Error with engine "{0}":\n\t{1}'.format(
@@ -104,7 +112,7 @@ def make_callback(engine_name,
104 112
             # append result
105 113
             cb_res.append(result)
106 114
 
107
-        results[engine_name] = cb_res
115
+        results_queue.put_nowait((engine_name, cb_res))
108 116
 
109 117
         # update stats with current page-load-time
110 118
         engines[engine_name].stats['page_load_time'] += \
@@ -420,7 +428,7 @@ class Search(object):
420 428
 
421 429
         # init vars
422 430
         requests = []
423
-        results = {}
431
+        results_queue = Queue()
424 432
         suggestions = set()
425 433
         answers = set()
426 434
         infoboxes = []
@@ -468,7 +476,7 @@ class Search(object):
468 476
             # create a callback wrapper for the search engine results
469 477
             callback = make_callback(
470 478
                 selected_engine['name'],
471
-                results,
479
+                results_queue,
472 480
                 suggestions,
473 481
                 answers,
474 482
                 infoboxes,
@@ -502,6 +510,11 @@ class Search(object):
502 510
         # send all search-request
503 511
         threaded_requests(requests)
504 512
 
513
+        results = {}
514
+        while not results_queue.empty():
515
+            engine_name, engine_results = results_queue.get_nowait()
516
+            results[engine_name] = engine_results
517
+
505 518
         # update engine-specific stats
506 519
         for engine_name, engine_results in results.items():
507 520
             engines[engine_name].stats['search_count'] += 1