Minor CSS fix for links.
1 #! /usr/bin/env python3
4 Author: Eugen Sawin <sawine@me73.com>
17 from operator import itemgetter
18 from urllib.parse import urlparse
19 from urllib.request import urlopen
20 from tempfile import NamedTemporaryFile
21 from http.server import BaseHTTPRequestHandler, HTTPServer
22 from pseudoword import Database
25 from argparse import ArgumentParser
27 from external.argparse import ArgumentParser
32 parser = ArgumentParser(description='')
33 parser.add_argument('-p', type=int, default=8080, help='port')
34 parser.add_argument('-a', default='localhost', help='host address')
35 parser.add_argument('-l', default='log/server.log', help='log file')
36 parser.add_argument('-w', default='data/names', help='word database')
37 parser.add_argument('-d', default='httpdocs', help='http docs path')
38 return parser.parse_args()
43 logging.basicConfig(filename=args.l, level=logging.DEBUG,
44 format='[%(levelname)s@%(asctime)s] %(message)s',
45 datefmt='%d.%m.%Y %I:%M:%S')
47 server = Server(args.a, args.p, args.d, db, GetHandler)
51 class GetHandler(BaseHTTPRequestHandler):
54 request = Request(self.path, self.server.docs_path, self.server.db)
55 logging.info('Request: %s' % request)
56 code, content_type, data = request()
57 self.send_response(code)
58 self.send_header('Content-type', content_type)
60 self.wfile.write(data)
62 def log_message(self, format, *args):
66 class Server(HTTPServer):
68 def __init__(self, host, port, docs_path, db, handler):
69 HTTPServer.__init__(self, (host, port), handler)
72 self.docs_path = docs_path
76 logging.info('Server ready and listening at port {0}.'.format(self.port))
83 def _content_type(cls, doc):
84 if doc.endswith('.html'):
86 elif doc.endswith('.css'):
88 elif doc.endswith('.js'):
89 return 'application/javascript'
90 elif doc.endswith('.ttf'):
91 return 'application/octet-stream'
95 def __init__(self, query, docs_path, db):
96 self.docs_path = docs_path
98 self.parsed = urlparse(query)
100 if len(self.parsed.query):
101 self.args = dict([a.split('=') for a in self.parsed.query.split('&')])
102 if self.parsed.path[1:] in commands:
103 self.__class__ = commands[self.parsed.path[1:]]
105 self.__class__ = WebRequest
106 self.args['doc'] = self.parsed.path
109 return '{0}({1})'.format(str(self.__class__).partition('.')[-1].rstrip('">'),
110 ', '.join(['{0}: {1}'.format(k, str(v))
111 for k, v in self.args.items()]))
114 def client_rating(rating):
115 return int(rating * 1000)
118 class WordsRequest(Request):
121 w1, w2 = self.db.pick_words()
122 data = '{{"words":[["{w1}", {r1}], ["{w2}", {r2}]]}}'.format(w1=w1[0],
126 return (200, 'application/javascript', bytes(data, ENCODING))
129 class RateRequest(Request):
134 w3, w4 = self.db.rate(w3, w4)
135 w1, w2 = self.db.pick_words()
136 data = '{{"words":[["{w1}",{r1}],["{w2}",{r2}],'.format(w1=w1[0], r1=client_rating(w1[1]),
137 w2=w2[0], r2=client_rating(w2[1]))
138 data += '["{w3}",{r3}],["{w4}",{r4}]]}}'.format(w3=w3[0], r3=client_rating(w3[1]),
139 w4=w4[0], r4=client_rating(w4[1]))
140 return (200, 'application/javascript', bytes(data, ENCODING))
143 commands = {'words': WordsRequest,
147 class WebRequest(Request):
150 if self.args['doc'] == '/':
151 self.args['doc'] = '/index.html'
152 content_type = self._content_type(self.args['doc'])
153 data = bytes('', ENCODING)
154 rel_path = self.docs_path + self.args['doc']
155 if os.path.exists(rel_path):
156 with open(rel_path, 'r+b') as f:
161 return (code, content_type, data)
164 if __name__ == '__main__':