Changeset 773
- Timestamp:
- 10/31/05 17:23:57
- Files:
-
- trunk/cherrypy/_cphttptools.py (modified) (5 diffs)
- trunk/cherrypy/lib/cptools.py (modified) (3 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
trunk/cherrypy/_cphttptools.py
r772 r773 7 7 import sys 8 8 import types 9 import urllib10 from urlparse import urlparse11 9 12 10 import cherrypy … … 164 162 self.headerMap = KeyTitlingDict() 165 163 self.simpleCookie = Cookie.SimpleCookie() 166 167 164 self.rfile = rfile 168 165 … … 211 208 212 209 def processRequestLine(self, requestLine): 213 self.requestLine = requestLine.strip() 214 self.method, path, self.protocol = self.requestLine.split() 215 self.processRequestBody = self.method in ("POST", "PUT") 216 217 # path may be an abs_path (including "http://host.domain.tld"); 218 # Ignore scheme, location, and fragments (so config lookups work). 219 # [Therefore, this assumes all hosts are valid for this server.] 220 scheme, location, path, params, qs, frag = urlparse(path) 210 self.requestLine = rl = requestLine.strip() 211 method, path, qs, proto = cptools.parseRequestLine(rl) 221 212 if path == "*": 222 # "...the request does not apply to a particular resource,223 # but to the server itself". See224 # http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5.1.2225 213 path = "global" 226 else: 227 if params: 228 params = ";" + params 229 path = path + params 230 231 # Unquote the path (e.g. "/this%20path" -> "this path"). 232 # http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5.1.2 233 # Note that cgi.parse_qs will decode the querystring for us. 234 path = urllib.unquote(path) 235 236 # Save original value (in case it gets modified by filters) 237 self.path = self.originalPath = path 214 215 self.method = method 216 self.processRequestBody = method in ("POST", "PUT") 217 218 self.path = path 238 219 self.queryString = qs 220 self.protocol = proto 239 221 240 222 # Change objectPath in filters to change … … 266 248 cherrypy.response.version = min(self.version, server_v) 267 249 268 # build a paramMap dictionary from queryString 269 if re.match(r"[0-9]+,[0-9]+", self.queryString): 270 # Server-side image map. Map the coords to 'x' and 'y' 271 # (like CGI::Request does). 272 pm = self.queryString.split(",") 273 pm = {'x': int(pm[0]), 'y': int(pm[1])} 274 else: 275 pm = cgi.parse_qs(self.queryString, keep_blank_values=True) 276 for key, val in pm.items(): 277 if len(val) == 1: 278 pm[key] = val[0] 279 self.paramMap = pm 250 self.paramMap = cptools.parseQueryString(self.queryString) 280 251 281 252 # Process the headers into self.headerMap … … 337 308 self.body = forms.file 338 309 else: 339 for key in forms.keys(): 340 valueList = forms[key] 341 if isinstance(valueList, list): 342 self.paramMap[key] = [] 343 for item in valueList: 344 if item.filename is not None: 345 value = item # It's a file upload 346 else: 347 value = item.value # It's a regular field 348 self.paramMap[key].append(value) 349 else: 350 if valueList.filename is not None: 351 value = valueList # It's a file upload 352 else: 353 value = valueList.value # It's a regular field 354 self.paramMap[key] = value 310 self.paramMap.update(cptools.paramsFromCGIForm(forms)) 355 311 356 312 def main(self, path=None): trunk/cherrypy/lib/cptools.py
r768 r773 4 4 responseCodes = BaseHTTPRequestHandler.responses.copy() 5 5 6 import cgi 6 7 import inspect 7 8 import mimetools … … 12 13 13 14 import os 15 import re 14 16 import sys 15 17 import time 16 18 import urllib 19 from urlparse import urlparse 17 20 18 21 import cherrypy … … 342 345 343 346 return code, reason, message 347 348 def parseRequestLine(requestLine): 349 """Return (method, path, querystring, protocol) from a requestLine.""" 350 method, path, protocol = requestLine.split() 351 352 # path may be an abs_path (including "http://host.domain.tld"); 353 # Ignore scheme, location, and fragments (so config lookups work). 354 # [Therefore, this assumes all hosts are valid for this server.] 355 scheme, location, path, params, qs, frag = urlparse(path) 356 if path == "*": 357 # "...the request does not apply to a particular resource, 358 # but to the server itself". See 359 # http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5.1.2 360 pass 361 else: 362 if params: 363 params = ";" + params 364 path = path + params 365 366 # Unquote the path (e.g. "/this%20path" -> "this path"). 367 # http://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5.1.2 368 # Note that cgi.parse_qs will decode the querystring for us. 369 path = urllib.unquote(path) 370 371 return method, path, qs, protocol 372 373 def parseQueryString(queryString, keep_blank_values=True): 374 """Build a paramMap dictionary from a queryString.""" 375 if re.match(r"[0-9]+,[0-9]+", queryString): 376 # Server-side image map. Map the coords to 'x' and 'y' 377 # (like CGI::Request does). 378 pm = queryString.split(",") 379 pm = {'x': int(pm[0]), 'y': int(pm[1])} 380 else: 381 pm = cgi.parse_qs(queryString, keep_blank_values) 382 for key, val in pm.items(): 383 if len(val) == 1: 384 pm[key] = val[0] 385 return pm 386 387 def paramsFromCGIForm(form): 388 paramMap = {} 389 for key in form.keys(): 390 valueList = form[key] 391 if isinstance(valueList, list): 392 paramMap[key] = [] 393 for item in valueList: 394 if item.filename is not None: 395 value = item # It's a file upload 396 else: 397 value = item.value # It's a regular field 398 paramMap[key].append(value) 399 else: 400 if valueList.filename is not None: 401 value = valueList # It's a file upload 402 else: 403 value = valueList.value # It's a regular field 404 paramMap[key] = value 405 return paramMap 406 407

