| OLD | NEW |
| 1 #!/usr/bin/python | 1 #!/usr/bin/python |
| 2 | 2 |
| 3 """ | 3 """ |
| 4 Copyright 2013 Google Inc. | 4 Copyright 2013 Google Inc. |
| 5 | 5 |
| 6 Use of this source code is governed by a BSD-style license that can be | 6 Use of this source code is governed by a BSD-style license that can be |
| 7 found in the LICENSE file. | 7 found in the LICENSE file. |
| 8 | 8 |
| 9 HTTP server for our HTML rebaseline viewer. | 9 HTTP server for our HTML rebaseline viewer. |
| 10 """ | 10 """ |
| 11 | 11 |
| 12 # System-level imports | 12 # System-level imports |
| 13 import argparse | 13 import argparse |
| 14 import BaseHTTPServer | 14 import BaseHTTPServer |
| 15 import json | 15 import json |
| 16 import logging | 16 import logging |
| 17 import os | 17 import os |
| 18 import posixpath | 18 import posixpath |
| 19 import re | 19 import re |
| 20 import shutil | 20 import shutil |
| 21 import socket |
| 21 import sys | 22 import sys |
| 22 import thread | 23 import thread |
| 23 import time | 24 import time |
| 24 import urlparse | 25 import urlparse |
| 25 | 26 |
| 26 # Imports from within Skia | 27 # Imports from within Skia |
| 27 # | 28 # |
| 28 # We need to add the 'tools' directory, so that we can import svn.py within | 29 # We need to add the 'tools' directory, so that we can import svn.py within |
| 29 # that directory. | 30 # that directory. |
| 30 # Make sure that the 'tools' dir is in the PYTHONPATH, but add it at the *end* | 31 # Make sure that the 'tools' dir is in the PYTHONPATH, but add it at the *end* |
| (...skipping 27 matching lines...) Expand all Loading... |
| 58 | 59 |
| 59 DEFAULT_ACTUALS_DIR = '.gm-actuals' | 60 DEFAULT_ACTUALS_DIR = '.gm-actuals' |
| 60 DEFAULT_EXPECTATIONS_DIR = os.path.join(TRUNK_DIRECTORY, 'expectations', 'gm') | 61 DEFAULT_EXPECTATIONS_DIR = os.path.join(TRUNK_DIRECTORY, 'expectations', 'gm') |
| 61 DEFAULT_PORT = 8888 | 62 DEFAULT_PORT = 8888 |
| 62 | 63 |
| 63 _HTTP_HEADER_CONTENT_LENGTH = 'Content-Length' | 64 _HTTP_HEADER_CONTENT_LENGTH = 'Content-Length' |
| 64 _HTTP_HEADER_CONTENT_TYPE = 'Content-Type' | 65 _HTTP_HEADER_CONTENT_TYPE = 'Content-Type' |
| 65 | 66 |
| 66 _SERVER = None # This gets filled in by main() | 67 _SERVER = None # This gets filled in by main() |
| 67 | 68 |
| 69 def get_routable_ip_address(): |
| 70 """Returns routable IP address of this host (the IP address of its network |
| 71 interface that would be used for most traffic, not its localhost |
| 72 interface). See http://stackoverflow.com/a/166589 """ |
| 73 sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) |
| 74 sock.connect(('8.8.8.8', 80)) |
| 75 host = sock.getsockname()[0] |
| 76 sock.close() |
| 77 return host |
| 78 |
| 79 |
| 68 class Server(object): | 80 class Server(object): |
| 69 """ HTTP server for our HTML rebaseline viewer. """ | 81 """ HTTP server for our HTML rebaseline viewer. """ |
| 70 | 82 |
| 71 def __init__(self, | 83 def __init__(self, |
| 72 actuals_dir=DEFAULT_ACTUALS_DIR, | 84 actuals_dir=DEFAULT_ACTUALS_DIR, |
| 73 expectations_dir=DEFAULT_EXPECTATIONS_DIR, | 85 expectations_dir=DEFAULT_EXPECTATIONS_DIR, |
| 74 port=DEFAULT_PORT, export=False, editable=True, | 86 port=DEFAULT_PORT, export=False, editable=True, |
| 75 reload_seconds=0): | 87 reload_seconds=0): |
| 76 """ | 88 """ |
| 77 Args: | 89 Args: |
| (...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 157 time.sleep(self._reload_seconds) | 169 time.sleep(self._reload_seconds) |
| 158 self.update_results() | 170 self.update_results() |
| 159 | 171 |
| 160 def run(self): | 172 def run(self): |
| 161 self.results_lock = thread.allocate_lock() | 173 self.results_lock = thread.allocate_lock() |
| 162 self.update_results() | 174 self.update_results() |
| 163 thread.start_new_thread(self._result_reloader, ()) | 175 thread.start_new_thread(self._result_reloader, ()) |
| 164 | 176 |
| 165 if self._export: | 177 if self._export: |
| 166 server_address = ('', self._port) | 178 server_address = ('', self._port) |
| 179 host = get_routable_ip_address() |
| 167 if self._editable: | 180 if self._editable: |
| 168 logging.warning('Running with combination of "export" and "editable" ' | 181 logging.warning('Running with combination of "export" and "editable" ' |
| 169 'flags. Users on other machines will ' | 182 'flags. Users on other machines will ' |
| 170 'be able to modify your GM expectations!') | 183 'be able to modify your GM expectations!') |
| 171 else: | 184 else: |
| 172 server_address = ('127.0.0.1', self._port) | 185 host = '127.0.0.1' |
| 186 server_address = (host, self._port) |
| 173 http_server = BaseHTTPServer.HTTPServer(server_address, HTTPRequestHandler) | 187 http_server = BaseHTTPServer.HTTPServer(server_address, HTTPRequestHandler) |
| 174 logging.info('Ready for requests on http://%s:%d' % ( | 188 logging.info('Ready for requests on http://%s:%d' % (host, http_server.serve
r_port)) |
| 175 http_server.server_name, http_server.server_port)) | |
| 176 http_server.serve_forever() | 189 http_server.serve_forever() |
| 177 | 190 |
| 178 | 191 |
| 179 class HTTPRequestHandler(BaseHTTPServer.BaseHTTPRequestHandler): | 192 class HTTPRequestHandler(BaseHTTPServer.BaseHTTPRequestHandler): |
| 180 """ HTTP request handlers for various types of queries this server knows | 193 """ HTTP request handlers for various types of queries this server knows |
| 181 how to handle (static HTML and Javascript, expected/actual results, etc.) | 194 how to handle (static HTML and Javascript, expected/actual results, etc.) |
| 182 """ | 195 """ |
| 183 def do_GET(self): | 196 def do_GET(self): |
| 184 """ Handles all GET requests, forwarding them to the appropriate | 197 """ Handles all GET requests, forwarding them to the appropriate |
| 185 do_GET_* dispatcher. """ | 198 do_GET_* dispatcher. """ |
| (...skipping 239 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 425 args = parser.parse_args() | 438 args = parser.parse_args() |
| 426 global _SERVER | 439 global _SERVER |
| 427 _SERVER = Server(actuals_dir=args.actuals_dir, | 440 _SERVER = Server(actuals_dir=args.actuals_dir, |
| 428 expectations_dir=args.expectations_dir, | 441 expectations_dir=args.expectations_dir, |
| 429 port=args.port, export=args.export, editable=args.editable, | 442 port=args.port, export=args.export, editable=args.editable, |
| 430 reload_seconds=args.reload) | 443 reload_seconds=args.reload) |
| 431 _SERVER.run() | 444 _SERVER.run() |
| 432 | 445 |
| 433 if __name__ == '__main__': | 446 if __name__ == '__main__': |
| 434 main() | 447 main() |
| OLD | NEW |