client.py 40.4 KB
Newer Older
1 2 3 4 5
"""HTTP/1.1 client library

<intro stuff goes here>
<other stuff, too>

6
HTTPConnection goes through a number of "states", which define when a client
7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
may legally make another request or fetch the response for a particular
request. This diagram details these state transitions:

    (null)
      |
      | HTTPConnection()
      v
    Idle
      |
      | putrequest()
      v
    Request-started
      |
      | ( putheader() )*  endheaders()
      v
    Request-sent
      |
      | response = getresponse()
      v
    Unread-response   [Response-headers-read]
      |\____________________
28 29 30 31 32 33 34 35 36 37 38 39 40
      |                     |
      | response.read()     | putrequest()
      v                     v
    Idle                  Req-started-unread-response
                     ______/|
                   /        |
   response.read() |        | ( putheader() )*  endheaders()
                   v        v
       Request-started    Req-sent-unread-response
                            |
                            | response.read()
                            v
                          Request-sent
41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66

This diagram presents the following rules:
  -- a second request may not be started until {response-headers-read}
  -- a response [object] cannot be retrieved until {request-sent}
  -- there is no differentiation between an unread response body and a
     partially read response body

Note: this enforcement is applied by the HTTPConnection class. The
      HTTPResponse class does not enforce this state machine, which
      implies sophisticated clients may accelerate the request/response
      pipeline. Caution should be taken, though: accelerating the states
      beyond the above pattern may imply knowledge of the server's
      connection-close behavior for certain requests. For example, it
      is impossible to tell whether the server will close the connection
      UNTIL the response headers have been read; this means that further
      requests cannot be placed into the pipeline until it is known that
      the server will NOT be closing the connection.

Logical State                  __state            __response
-------------                  -------            ----------
Idle                           _CS_IDLE           None
Request-started                _CS_REQ_STARTED    None
Request-sent                   _CS_REQ_SENT       None
Unread-response                _CS_IDLE           <response_class>
Req-started-unread-response    _CS_REQ_STARTED    <response_class>
Req-sent-unread-response       _CS_REQ_SENT       <response_class>
67
"""
68

69 70
import email.parser
import email.message
71 72 73
import io
import os
import socket
74
import collections
Jeremy Hylton's avatar
Jeremy Hylton committed
75
from urllib.parse import urlsplit
76
import warnings
77

78
__all__ = ["HTTPResponse", "HTTPConnection",
79
           "HTTPException", "NotConnected", "UnknownProtocol",
80 81 82
           "UnknownTransferEncoding", "UnimplementedFileMode",
           "IncompleteRead", "InvalidURL", "ImproperConnectionState",
           "CannotSendRequest", "CannotSendHeader", "ResponseNotReady",
83
           "BadStatusLine", "error", "responses"]
84

85
HTTP_PORT = 80
86 87
HTTPS_PORT = 443

88 89 90 91 92 93 94
_UNKNOWN = 'UNKNOWN'

# connection states
_CS_IDLE = 'Idle'
_CS_REQ_STARTED = 'Request-started'
_CS_REQ_SENT = 'Request-sent'

95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154
# status codes
# informational
CONTINUE = 100
SWITCHING_PROTOCOLS = 101
PROCESSING = 102

# successful
OK = 200
CREATED = 201
ACCEPTED = 202
NON_AUTHORITATIVE_INFORMATION = 203
NO_CONTENT = 204
RESET_CONTENT = 205
PARTIAL_CONTENT = 206
MULTI_STATUS = 207
IM_USED = 226

# redirection
MULTIPLE_CHOICES = 300
MOVED_PERMANENTLY = 301
FOUND = 302
SEE_OTHER = 303
NOT_MODIFIED = 304
USE_PROXY = 305
TEMPORARY_REDIRECT = 307

# client error
BAD_REQUEST = 400
UNAUTHORIZED = 401
PAYMENT_REQUIRED = 402
FORBIDDEN = 403
NOT_FOUND = 404
METHOD_NOT_ALLOWED = 405
NOT_ACCEPTABLE = 406
PROXY_AUTHENTICATION_REQUIRED = 407
REQUEST_TIMEOUT = 408
CONFLICT = 409
GONE = 410
LENGTH_REQUIRED = 411
PRECONDITION_FAILED = 412
REQUEST_ENTITY_TOO_LARGE = 413
REQUEST_URI_TOO_LONG = 414
UNSUPPORTED_MEDIA_TYPE = 415
REQUESTED_RANGE_NOT_SATISFIABLE = 416
EXPECTATION_FAILED = 417
UNPROCESSABLE_ENTITY = 422
LOCKED = 423
FAILED_DEPENDENCY = 424
UPGRADE_REQUIRED = 426

# server error
INTERNAL_SERVER_ERROR = 500
NOT_IMPLEMENTED = 501
BAD_GATEWAY = 502
SERVICE_UNAVAILABLE = 503
GATEWAY_TIMEOUT = 504
HTTP_VERSION_NOT_SUPPORTED = 505
INSUFFICIENT_STORAGE = 507
NOT_EXTENDED = 510

155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203
# Mapping status codes to official W3C names
responses = {
    100: 'Continue',
    101: 'Switching Protocols',

    200: 'OK',
    201: 'Created',
    202: 'Accepted',
    203: 'Non-Authoritative Information',
    204: 'No Content',
    205: 'Reset Content',
    206: 'Partial Content',

    300: 'Multiple Choices',
    301: 'Moved Permanently',
    302: 'Found',
    303: 'See Other',
    304: 'Not Modified',
    305: 'Use Proxy',
    306: '(Unused)',
    307: 'Temporary Redirect',

    400: 'Bad Request',
    401: 'Unauthorized',
    402: 'Payment Required',
    403: 'Forbidden',
    404: 'Not Found',
    405: 'Method Not Allowed',
    406: 'Not Acceptable',
    407: 'Proxy Authentication Required',
    408: 'Request Timeout',
    409: 'Conflict',
    410: 'Gone',
    411: 'Length Required',
    412: 'Precondition Failed',
    413: 'Request Entity Too Large',
    414: 'Request-URI Too Long',
    415: 'Unsupported Media Type',
    416: 'Requested Range Not Satisfiable',
    417: 'Expectation Failed',

    500: 'Internal Server Error',
    501: 'Not Implemented',
    502: 'Bad Gateway',
    503: 'Service Unavailable',
    504: 'Gateway Timeout',
    505: 'HTTP Version Not Supported',
}

204 205 206
# maximal amount of data to read at one time in _safe_read
MAXAMOUNT = 1048576

207 208 209
# maximal line length when calling readline().
_MAXLINE = 65536

210
class HTTPMessage(email.message.Message):
211 212 213 214 215 216
    # XXX The only usage of this method is in
    # http.server.CGIHTTPRequestHandler.  Maybe move the code there so
    # that it doesn't need to be part of the public API.  The API has
    # never been defined so this could cause backwards compatibility
    # issues.

217 218 219 220 221 222 223 224
    def getallmatchingheaders(self, name):
        """Find all header lines matching a given header name.

        Look through the list of headers and find all lines matching a given
        header name (and their continuation lines).  A list of the lines is
        returned, without interpretation.  If the header does not occur, an
        empty list is returned.  If the header occurs multiple times, all
        occurrences are returned.  Case is not important in the header name.
225 226

        """
227 228 229 230 231 232 233 234 235 236 237 238 239
        name = name.lower() + ':'
        n = len(name)
        lst = []
        hit = 0
        for line in self.keys():
            if line[:n].lower() == name:
                hit = 1
            elif not line[:1].isspace():
                hit = 0
            if hit:
                lst.append(line)
        return lst

240
def parse_headers(fp, _class=HTTPMessage):
241 242 243 244 245 246 247 248 249 250 251
    """Parses only RFC2822 headers from a file pointer.

    email Parser wants to see strings rather than bytes.
    But a TextIOWrapper around self.rfile would buffer too many bytes
    from the stream, bytes which we later need to read as bytes.
    So we read the correct bytes here, as bytes, for email Parser
    to parse.

    """
    headers = []
    while True:
252 253 254
        line = fp.readline(_MAXLINE + 1)
        if len(line) > _MAXLINE:
            raise LineTooLong("header line")
255 256 257 258
        headers.append(line)
        if line in (b'\r\n', b'\n', b''):
            break
    hstring = b''.join(headers).decode('iso-8859-1')
259
    return email.parser.Parser(_class=_class).parsestr(hstring)
260

Jeremy Hylton's avatar
Jeremy Hylton committed
261

262 263 264
_strict_sentinel = object()

class HTTPResponse(io.RawIOBase):
Jeremy Hylton's avatar
Jeremy Hylton committed
265 266 267

    # See RFC 2616 sec 19.6 and RFC 1945 sec 6 for details.

268 269 270 271 272
    # The bytes from the socket object are iso-8859-1 strings.
    # See RFC 2616 sec 2.2 which notes an exception for MIME-encoded
    # text following RFC 2047.  The basic status line parsing only
    # accepts iso-8859-1.

273
    def __init__(self, sock, debuglevel=0, strict=_strict_sentinel, method=None, url=None):
274 275
        # If the response includes a content-length header, we need to
        # make sure that the client doesn't read more than the
276
        # specified number of bytes.  If it does, it will block until
277 278 279 280
        # the server times out and closes the connection.  This will
        # happen if a self.fp.read() is done (without a size) whether
        # self.fp is buffered or not.  So, no self.fp.read() by
        # clients unless they know what they are doing.
281
        self.fp = sock.makefile("rb")
282
        self.debuglevel = debuglevel
283 284 285 286
        if strict is not _strict_sentinel:
            warnings.warn("the 'strict' argument isn't supported anymore; "
                "http.client now always assumes HTTP/1.x compliant servers.",
                DeprecationWarning, 2)
287
        self._method = method
288

289 290 291 292 293 294 295
        # The HTTPResponse object is returned via urllib.  The clients
        # of http and urllib expect different attributes for the
        # headers.  headers is used here and supports urllib.  msg is
        # provided as a backwards compatibility layer for http
        # clients.

        self.headers = self.msg = None
296 297

        # from the Status-Line of the response
Tim Peters's avatar
Tim Peters committed
298 299 300
        self.version = _UNKNOWN # HTTP-Version
        self.status = _UNKNOWN  # Status-Code
        self.reason = _UNKNOWN  # Reason-Phrase
301

Tim Peters's avatar
Tim Peters committed
302 303 304 305
        self.chunked = _UNKNOWN         # is "chunked" being used?
        self.chunk_left = _UNKNOWN      # bytes left to read in current chunk
        self.length = _UNKNOWN          # number of bytes left in response
        self.will_close = _UNKNOWN      # conn will close at end of response
306

307
    def _read_status(self):
308 309 310
        line = str(self.fp.readline(_MAXLINE + 1), "iso-8859-1")
        if len(line) > _MAXLINE:
            raise LineTooLong("status line")
311
        if self.debuglevel > 0:
312
            print("reply:", repr(line))
313 314 315 316
        if not line:
            # Presumably, the server closed the connection before
            # sending a valid response.
            raise BadStatusLine(line)
317
        try:
318
            version, status, reason = line.split(None, 2)
319 320
        except ValueError:
            try:
321
                version, status = line.split(None, 1)
322 323
                reason = ""
            except ValueError:
324
                # empty version will cause next test to fail.
Jeremy Hylton's avatar
Jeremy Hylton committed
325
                version = ""
326
        if not version.startswith("HTTP/"):
327 328
            self.close()
            raise BadStatusLine(line)
329

330 331
        # The status code is a three-digit number
        try:
332
            status = int(status)
333 334 335 336
            if status < 100 or status > 999:
                raise BadStatusLine(line)
        except ValueError:
            raise BadStatusLine(line)
337 338
        return version, status, reason

339
    def begin(self):
340
        if self.headers is not None:
341 342
            # we've already started reading the response
            return
343

344
        # read until we get a non-100 response
Raymond Hettinger's avatar
Raymond Hettinger committed
345
        while True:
346
            version, status, reason = self._read_status()
347
            if status != CONTINUE:
348 349
                break
            # skip the header from the 100 response
Raymond Hettinger's avatar
Raymond Hettinger committed
350
            while True:
351 352 353 354
                skip = self.fp.readline(_MAXLINE + 1)
                if len(skip) > _MAXLINE:
                    raise LineTooLong("header line")
                skip = skip.strip()
355 356 357
                if not skip:
                    break
                if self.debuglevel > 0:
358
                    print("header:", skip)
Tim Peters's avatar
Tim Peters committed
359

360
        self.code = self.status = status
361
        self.reason = reason.strip()
362 363
        if version in ("HTTP/1.0", "HTTP/0.9"):
            # Some servers might still return "0.9", treat it as 1.0 anyway
364
            self.version = 10
365
        elif version.startswith("HTTP/1."):
Tim Peters's avatar
Tim Peters committed
366
            self.version = 11   # use HTTP/1.1 code for HTTP/1.x where x>=1
367 368
        else:
            raise UnknownProtocol(version)
369

370
        self.headers = self.msg = parse_headers(self.fp)
371

372
        if self.debuglevel > 0:
373
            for hdr in self.headers:
374
                print("header:", hdr, end=" ")
375 376

        # are we using the chunked-style of transfer encoding?
377
        tr_enc = self.headers.get("transfer-encoding")
378
        if tr_enc and tr_enc.lower() == "chunked":
379
            self.chunked = True
380 381
            self.chunk_left = None
        else:
382
            self.chunked = False
383 384

        # will the connection close at the end of the response?
385
        self.will_close = self._check_close()
386 387 388

        # do we have a Content-Length?
        # NOTE: RFC 2616, S4.4, #3 says we ignore this if tr_enc is "chunked"
389
        self.length = None
390
        length = self.headers.get("content-length")
391 392

         # are we using the chunked-style of transfer encoding?
393
        tr_enc = self.headers.get("transfer-encoding")
394
        if length and not self.chunked:
395 396 397
            try:
                self.length = int(length)
            except ValueError:
398 399 400 401 402 403
                self.length = None
            else:
                if self.length < 0:  # ignore nonsensical negative lengths
                    self.length = None
        else:
            self.length = None
404 405

        # does the body have a fixed length? (of zero)
406
        if (status == NO_CONTENT or status == NOT_MODIFIED or
407
            100 <= status < 200 or      # 1xx codes
408
            self._method == "HEAD"):
409 410 411 412 413
            self.length = 0

        # if the connection remains open, and we aren't using chunked, and
        # a content-length was not provided, then assume that the connection
        # WILL close.
414 415 416
        if (not self.will_close and
            not self.chunked and
            self.length is None):
417
            self.will_close = True
418

419
    def _check_close(self):
420
        conn = self.headers.get("connection")
421 422 423
        if self.version == 11:
            # An HTTP/1.1 proxy is assumed to stay open unless
            # explicitly closed.
424
            conn = self.headers.get("connection")
425
            if conn and "close" in conn.lower():
426 427 428
                return True
            return False

429 430
        # Some HTTP/1.0 implementations have support for persistent
        # connections, using rules different than HTTP/1.1.
431

432
        # For older HTTP, Keep-Alive indicates persistent connection.
433
        if self.headers.get("keep-alive"):
434
            return False
Tim Peters's avatar
Tim Peters committed
435

436 437 438 439 440
        # At least Akamai returns a "Connection: Keep-Alive" header,
        # which was supposed to be sent by the client.
        if conn and "keep-alive" in conn.lower():
            return False

441
        # Proxy-Connection is a netscape hack.
442
        pconn = self.headers.get("proxy-connection")
443
        if pconn and "keep-alive" in pconn.lower():
444 445 446 447 448
            return False

        # otherwise, assume it will close
        return True

449 450 451 452 453
    def close(self):
        if self.fp:
            self.fp.close()
            self.fp = None

454 455 456 457 458 459 460 461 462 463 464 465
    # These implementations are for the benefit of io.BufferedReader.

    # XXX This class should probably be revised to act more like
    # the "raw stream" that BufferedReader expects.

    @property
    def closed(self):
        return self.isclosed()

    def flush(self):
        self.fp.flush()

466 467 468
    def readable(self):
        return True

469 470
    # End of "raw stream" methods

471 472 473 474 475 476 477 478 479 480 481
    def isclosed(self):
        # NOTE: it is possible that we will not ever call self.close(). This
        #       case occurs when will_close is TRUE, length is None, and we
        #       read up to the last byte, but NOT past it.
        #
        # IMPLIES: if will_close is FALSE, then self.close() will ALWAYS be
        #          called, meaning self.isclosed() is meaningful.
        return self.fp is None

    def read(self, amt=None):
        if self.fp is None:
482
            return b""
483 484

        if self._method == "HEAD":
485
            self.close()
486
            return b""
487 488

        if self.chunked:
489
            return self._read_chunked(amt)
Tim Peters's avatar
Tim Peters committed
490

491
        if amt is None:
492
            # unbounded read
493
            if self.length is None:
494 495 496
                s = self.fp.read()
            else:
                s = self._safe_read(self.length)
497
                self.length = 0
Tim Peters's avatar
Tim Peters committed
498
            self.close()        # we read everything
499 500 501 502 503 504 505 506 507 508 509
            return s

        if self.length is not None:
            if amt > self.length:
                # clip the read to the "end of response"
                amt = self.length

        # we do not use _safe_read() here because this may be a .will_close
        # connection, and the user is reading more bytes than will be provided
        # (for example, reading in 1k chunks)
        s = self.fp.read(amt)
510 511
        if self.length is not None:
            self.length -= len(s)
512 513
            if not self.length:
                self.close()
514 515
        return s

516 517 518
    def _read_chunked(self, amt):
        assert self.chunked != _UNKNOWN
        chunk_left = self.chunk_left
519
        value = []
Raymond Hettinger's avatar
Raymond Hettinger committed
520
        while True:
521
            if chunk_left is None:
522 523 524
                line = self.fp.readline(_MAXLINE + 1)
                if len(line) > _MAXLINE:
                    raise LineTooLong("chunk size")
525
                i = line.find(b";")
526 527
                if i >= 0:
                    line = line[:i] # strip chunk-extensions
528 529 530 531 532 533
                try:
                    chunk_left = int(line, 16)
                except ValueError:
                    # close the connection as protocol synchronisation is
                    # probably lost
                    self.close()
534
                    raise IncompleteRead(b''.join(value))
535 536 537
                if chunk_left == 0:
                    break
            if amt is None:
538
                value.append(self._safe_read(chunk_left))
539
            elif amt < chunk_left:
540
                value.append(self._safe_read(amt))
541
                self.chunk_left = chunk_left - amt
542
                return b''.join(value)
543
            elif amt == chunk_left:
544
                value.append(self._safe_read(amt))
545 546
                self._safe_read(2)  # toss the CRLF at the end of the chunk
                self.chunk_left = None
547
                return b''.join(value)
548
            else:
549
                value.append(self._safe_read(chunk_left))
550 551 552 553 554 555 556 557
                amt -= chunk_left

            # we read the whole chunk, get another
            self._safe_read(2)      # toss the CRLF at the end of the chunk
            chunk_left = None

        # read and discard trailer up to the CRLF terminator
        ### note: we shouldn't have any trailers!
Raymond Hettinger's avatar
Raymond Hettinger committed
558
        while True:
559 560 561
            line = self.fp.readline(_MAXLINE + 1)
            if len(line) > _MAXLINE:
                raise LineTooLong("trailer line")
Christian Heimes's avatar
Christian Heimes committed
562 563 564 565
            if not line:
                # a vanishingly small number of sites EOF without
                # sending the trailer
                break
566
            if line == b"\r\n":
567 568 569 570 571
                break

        # we read everything; close the "file"
        self.close()

572
        return b''.join(value)
Tim Peters's avatar
Tim Peters committed
573

574 575 576 577 578 579 580 581 582 583 584 585 586 587
    def _safe_read(self, amt):
        """Read the number of bytes requested, compensating for partial reads.

        Normally, we have a blocking socket, but a read() can be interrupted
        by a signal (resulting in a partial read).

        Note that we cannot distinguish between EOF and an interrupt when zero
        bytes have been read. IncompleteRead() will be raised in this
        situation.

        This function should be used when <amt> bytes "should" be present for
        reading. If the bytes are truly not available (due to EOF), then the
        IncompleteRead exception can be used to detect the problem.
        """
588
        s = []
589
        while amt > 0:
590
            chunk = self.fp.read(min(amt, MAXAMOUNT))
591
            if not chunk:
592
                raise IncompleteRead(b''.join(s), amt)
593
            s.append(chunk)
Raymond Hettinger's avatar
Raymond Hettinger committed
594
            amt -= len(chunk)
595
        return b"".join(s)
596

597 598 599
    def fileno(self):
        return self.fp.fileno()

600
    def getheader(self, name, default=None):
601
        if self.headers is None:
602
            raise ResponseNotReady()
603 604 605 606 607
        headers = self.headers.get_all(name) or default
        if isinstance(headers, str) or not hasattr(headers, '__iter__'):
            return headers
        else:
            return ', '.join(headers)
608

609 610
    def getheaders(self):
        """Return list of (header, value) tuples."""
611
        if self.headers is None:
612
            raise ResponseNotReady()
613
        return list(self.headers.items())
614

615 616 617 618 619
    # We override IOBase.__iter__ so that it doesn't check for closed-ness

    def __iter__(self):
        return self

620 621 622 623 624 625 626 627 628 629
    # For compatibility with old-style urllib responses.

    def info(self):
        return self.headers

    def geturl(self):
        return self.url

    def getcode(self):
        return self.status
630 631 632

class HTTPConnection:

633 634 635 636 637 638
    _http_vsn = 11
    _http_vsn_str = 'HTTP/1.1'

    response_class = HTTPResponse
    default_port = HTTP_PORT
    auto_open = 1
639
    debuglevel = 0
640

641
    def __init__(self, host, port=None, strict=_strict_sentinel,
642
                 timeout=socket._GLOBAL_DEFAULT_TIMEOUT, source_address=None):
643 644 645 646
        if strict is not _strict_sentinel:
            warnings.warn("the 'strict' argument isn't supported anymore; "
                "http.client now always assumes HTTP/1.x compliant servers.",
                DeprecationWarning, 2)
647
        self.timeout = timeout
648
        self.source_address = source_address
649
        self.sock = None
650
        self._buffer = []
651 652
        self.__response = None
        self.__state = _CS_IDLE
653
        self._method = None
654 655
        self._tunnel_host = None
        self._tunnel_port = None
Tim Peters's avatar
Tim Peters committed
656

657 658
        self._set_hostport(host, port)

659 660 661 662 663 664
    def set_tunnel(self, host, port=None, headers=None):
        """ Sets up the host and the port for the HTTP CONNECT Tunnelling.

        The headers argument should be a mapping of extra HTTP headers
        to send with the CONNECT request.
        """
665 666
        self._tunnel_host = host
        self._tunnel_port = port
667 668 669 670
        if headers:
            self._tunnel_headers = headers
        else:
            self._tunnel_headers.clear()
671

672 673
    def _set_hostport(self, host, port):
        if port is None:
674
            i = host.rfind(':')
675 676
            j = host.rfind(']')         # ipv6 addresses have [...]
            if i > j:
677 678 679
                try:
                    port = int(host[i+1:])
                except ValueError:
680
                    raise InvalidURL("nonnumeric port: '%s'" % host[i+1:])
681 682 683
                host = host[:i]
            else:
                port = self.default_port
684
            if host and host[0] == '[' and host[-1] == ']':
Brett Cannon's avatar
Brett Cannon committed
685
                host = host[1:-1]
686 687 688
        self.host = host
        self.port = port

689 690 691
    def set_debuglevel(self, level):
        self.debuglevel = level

692 693
    def _tunnel(self):
        self._set_hostport(self._tunnel_host, self._tunnel_port)
694
        connect_str = "CONNECT %s:%d HTTP/1.0\r\n" %(self.host, self.port)
695 696
        connect_bytes = connect_str.encode("ascii")
        self.send(connect_bytes)
697 698
        for header, value in self._tunnel_headers.iteritems():
            header_str = "%s: %s\r\n" % (header, value)
699
            header_bytes = header_str.encode("latin1")
700 701
            self.send(header_bytes)

702
        response = self.response_class(self.sock, method = self._method)
703
        (version, code, message) = response._read_status()
704

705 706 707 708 709
        if code != 200:
            self.close()
            raise socket.error("Tunnel connection failed: %d %s" % (code,
                                                                    message.strip()))
        while True:
710 711 712
            line = response.fp.readline(_MAXLINE + 1)
            if len(line) > _MAXLINE:
                raise LineTooLong("header line")
713 714 715
            if line == b'\r\n':
                break

716 717
    def connect(self):
        """Connect to the host and port specified in __init__."""
718
        self.sock = socket.create_connection((self.host,self.port),
719
                                             self.timeout, self.source_address)
720 721
        if self._tunnel_host:
            self._tunnel()
722 723 724 725

    def close(self):
        """Close the connection to the HTTP server."""
        if self.sock:
Tim Peters's avatar
Tim Peters committed
726
            self.sock.close()   # close it manually... there may be other refs
727 728 729 730 731 732
            self.sock = None
        if self.__response:
            self.__response.close()
            self.__response = None
        self.__state = _CS_IDLE

733
    def send(self, data):
734 735 736 737 738
        """Send `data' to the server.
        ``data`` can be a string object, a bytes object, an array object, a
        file-like object that supports a .read() method, or an iterable object.
        """

739 740 741 742 743 744
        if self.sock is None:
            if self.auto_open:
                self.connect()
            else:
                raise NotConnected()

745
        if self.debuglevel > 0:
746
            print("send:", repr(data))
747
        blocksize = 8192
748
        if hasattr(data, "read") :
749 750 751
            if self.debuglevel > 0:
                print("sendIng a read()able")
            encode = False
752
            try:
753
                mode = data.mode
754 755 756 757 758 759 760 761 762
            except AttributeError:
                # io.BytesIO and other file-like objects don't have a `mode`
                # attribute.
                pass
            else:
                if "b" not in mode:
                    encode = True
                    if self.debuglevel > 0:
                        print("encoding file using iso-8859-1")
763
            while 1:
764 765
                datablock = data.read(blocksize)
                if not datablock:
766 767
                    break
                if encode:
768 769
                    datablock = datablock.encode("iso-8859-1")
                self.sock.sendall(datablock)
770 771

        try:
772
            self.sock.sendall(data)
773 774 775 776 777
        except TypeError:
            if isinstance(data, collections.Iterable):
                for d in data:
                    self.sock.sendall(d)
            else:
778
                raise TypeError("data should be a bytes-like object\
779
                        or an iterable, got %r " % type(it))
780

781 782
    def _output(self, s):
        """Add a line of output to the current request buffer.
Tim Peters's avatar
Tim Peters committed
783

784
        Assumes that the line does *not* end with \\r\\n.
785 786 787
        """
        self._buffer.append(s)

788
    def _send_output(self, message_body=None):
789 790
        """Send the currently buffered request and clear the buffer.

791
        Appends an extra \\r\\n to the buffer.
792
        A message_body may be specified, to be appended to the request.
793
        """
Martin v. Löwis's avatar
Martin v. Löwis committed
794 795
        self._buffer.extend((b"", b""))
        msg = b"\r\n".join(self._buffer)
796
        del self._buffer[:]
797 798 799
        # If msg and message_body are sent in a single send() call,
        # it will avoid performance problems caused by the interaction
        # between delayed ack and the Nagle algorithim.
800
        if isinstance(message_body, bytes):
801
            msg += message_body
802
            message_body = None
803
        self.send(msg)
804
        if message_body is not None:
805 806
            # message_body was not a string (i.e. it is a file), and
            # we must run the risk of Nagle.
807
            self.send(message_body)
808

809
    def putrequest(self, method, url, skip_host=0, skip_accept_encoding=0):
810 811 812 813
        """Send a request to the server.

        `method' specifies an HTTP request method, e.g. 'GET'.
        `url' specifies the object being requested, e.g. '/index.html'.
814 815 816
        `skip_host' if True does not add automatically a 'Host:' header
        `skip_accept_encoding' if True does not add automatically an
           'Accept-Encoding:' header
817 818
        """

819
        # if a prior response has been completed, then forget about it.
820 821 822
        if self.__response and self.__response.isclosed():
            self.__response = None

Tim Peters's avatar
Tim Peters committed
823

824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844
        # in certain cases, we cannot issue another request on this connection.
        # this occurs when:
        #   1) we are in the process of sending a request.   (_CS_REQ_STARTED)
        #   2) a response to a previous request has signalled that it is going
        #      to close the connection upon completion.
        #   3) the headers for the previous response have not been read, thus
        #      we cannot determine whether point (2) is true.   (_CS_REQ_SENT)
        #
        # if there is no prior response, then we can request at will.
        #
        # if point (2) is true, then we will have passed the socket to the
        # response (effectively meaning, "there is no prior response"), and
        # will open a new one when a new request is made.
        #
        # Note: if a prior response exists, then we *can* start a new request.
        #       We are not allowed to begin fetching the response to this new
        #       request, however, until that prior response is complete.
        #
        if self.__state == _CS_IDLE:
            self.__state = _CS_REQ_STARTED
        else:
845
            raise CannotSendRequest(self.__state)
846

847 848
        # Save the method we use, we need it later in the response phase
        self._method = method
849 850
        if not url:
            url = '/'
Martin v. Löwis's avatar
Martin v. Löwis committed
851
        request = '%s %s %s' % (method, url, self._http_vsn_str)
852

Martin v. Löwis's avatar
Martin v. Löwis committed
853 854
        # Non-ASCII characters should have been eliminated earlier
        self._output(request.encode('ascii'))
855 856 857 858

        if self._http_vsn == 11:
            # Issue some standard headers for better HTTP/1.1 compliance

Jeremy Hylton's avatar
Jeremy Hylton committed
859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878
            if not skip_host:
                # this header is issued *only* for HTTP/1.1
                # connections. more specifically, this means it is
                # only issued when the client uses the new
                # HTTPConnection() class. backwards-compat clients
                # will be using HTTP/1.0 and those clients may be
                # issuing this header themselves. we should NOT issue
                # it twice; some web servers (such as Apache) barf
                # when they see two Host: headers

                # If we need a non-standard port,include it in the
                # header.  If the request is going through a proxy,
                # but the host of the actual URL, not the host of the
                # proxy.

                netloc = ''
                if url.startswith('http'):
                    nil, netloc, nil, nil, nil = urlsplit(url)

                if netloc:
879 880 881 882 883
                    try:
                        netloc_enc = netloc.encode("ascii")
                    except UnicodeEncodeError:
                        netloc_enc = netloc.encode("idna")
                    self.putheader('Host', netloc_enc)
Jeremy Hylton's avatar
Jeremy Hylton committed
884
                else:
885 886 887 888
                    try:
                        host_enc = self.host.encode("ascii")
                    except UnicodeEncodeError:
                        host_enc = self.host.encode("idna")
889 890 891 892 893 894 895

                    # As per RFC 273, IPv6 address should be wrapped with []
                    # when used as Host header

                    if self.host.find(':') >= 0:
                        host_enc = b'[' + host_enc + b']'

Georg Brandl's avatar
Georg Brandl committed
896
                    if self.port == self.default_port:
897 898
                        self.putheader('Host', host_enc)
                    else:
899
                        host_enc = host_enc.decode("ascii")
900
                        self.putheader('Host', "%s:%s" % (host_enc, self.port))
901 902 903 904 905 906 907 908 909

            # note: we are assuming that clients will not attempt to set these
            #       headers since *this* library must deal with the
            #       consequences. this also means that when the supporting
            #       libraries are updated to recognize other forms, then this
            #       code should be changed (removed or updated).

            # we only want a Content-Encoding of "identity" since we don't
            # support encodings such as x-gzip or x-deflate.
910 911
            if not skip_accept_encoding:
                self.putheader('Accept-Encoding', 'identity')
912 913 914 915 916 917 918 919

            # we can accept "chunked" Transfer-Encodings, but no others
            # NOTE: no TE header implies *only* "chunked"
            #self.putheader('TE', 'chunked')

            # if TE is supplied in the header, then it must appear in a
            # Connection header.
            #self.putheader('Connection', 'TE')
920

921 922 923 924
        else:
            # For HTTP/1.0, the server will assume "not chunked"
            pass

925
    def putheader(self, header, *values):
926 927 928 929 930 931 932
        """Send a request header line to the server.

        For example: h.putheader('Accept', 'text/html')
        """
        if self.__state != _CS_REQ_STARTED:
            raise CannotSendHeader()

933 934
        if hasattr(header, 'encode'):
            header = header.encode('ascii')
935 936 937
        values = list(values)
        for i, one_value in enumerate(values):
            if hasattr(one_value, 'encode'):
938
                values[i] = one_value.encode('latin1')
939 940
            elif isinstance(one_value, int):
                values[i] = str(one_value).encode('ascii')
941
        value = b'\r\n\t'.join(values)
942 943
        header = header + b': ' + value
        self._output(header)
944

945 946
    def endheaders(self, message_body=None):
        """Indicate that the last header line has been sent to the server.
947

948 949 950 951 952 953
        This method sends the request to the server.  The optional
        message_body argument can be used to pass message body
        associated with the request.  The message body will be sent in
        the same packet as the message headers if possible.  The
        message_body should be a string.
        """
954 955 956 957
        if self.__state == _CS_REQ_STARTED:
            self.__state = _CS_REQ_SENT
        else:
            raise CannotSendHeader()
958
        self._send_output(message_body)
959 960 961

    def request(self, method, url, body=None, headers={}):
        """Send a complete request to the server."""
962
        self._send_request(method, url, body, headers)
963

964 965 966 967 968 969 970 971 972 973 974 975 976 977 978 979 980
    def _set_content_length(self, body):
        # Set the content-length based on the body.
        thelen = None
        try:
            thelen = str(len(body))
        except TypeError as te:
            # If this is a file-like object, try to
            # fstat its file descriptor
            try:
                thelen = str(os.fstat(body.fileno()).st_size)
            except (AttributeError, OSError):
                # Don't send a length if this failed
                if self.debuglevel > 0: print("Cannot stat!!")

        if thelen is not None:
            self.putheader('Content-Length', thelen)

981
    def _send_request(self, method, url, body, headers):
982
        # Honor explicitly requested Host: and Accept-Encoding: headers.
983 984 985 986 987 988
        header_names = dict.fromkeys([k.lower() for k in headers])
        skips = {}
        if 'host' in header_names:
            skips['skip_host'] = 1
        if 'accept-encoding' in header_names:
            skips['skip_accept_encoding'] = 1
989

990 991 992
        self.putrequest(method, url, **skips)

        if body and ('content-length' not in header_names):
993
            self._set_content_length(body)
994
        for hdr, value in headers.items():
995
            self.putheader(hdr, value)
Jeremy Hylton's avatar
Jeremy Hylton committed
996
        if isinstance(body, str):
997 998 999
            # RFC 2616 Section 3.7.1 says that text default has a
            # default charset of iso-8859-1.
            body = body.encode('iso-8859-1')
Jeremy Hylton's avatar
Jeremy Hylton committed
1000
        self.endheaders(body)
1001 1002

    def getresponse(self):
1003 1004 1005 1006 1007 1008 1009 1010 1011 1012 1013 1014
        """Get the response from the server.

        If the HTTPConnection is in the correct state, returns an
        instance of HTTPResponse or of whatever object is returned by
        class the response_class variable.

        If a request has not been sent or if a previous response has
        not be handled, ResponseNotReady is raised.  If the HTTP
        response indicates that the connection should be closed, then
        it will be closed before the response is returned.  When the
        connection is closed, the underlying socket is closed.
        """
1015

1016
        # if a prior response has been completed, then forget about it.
1017 1018 1019 1020 1021 1022 1023 1024 1025 1026 1027 1028 1029 1030 1031 1032 1033 1034 1035
        if self.__response and self.__response.isclosed():
            self.__response = None

        # if a prior response exists, then it must be completed (otherwise, we
        # cannot read this response's header to determine the connection-close
        # behavior)
        #
        # note: if a prior response existed, but was connection-close, then the
        # socket and response were made independent of this HTTPConnection
        # object since a new request requires that we open a whole new
        # connection
        #
        # this means the prior response had one of two states:
        #   1) will_close: this connection was reset and the prior socket and
        #                  response operate independently
        #   2) persistent: the response was retained and we await its
        #                  isclosed() status to become true.
        #
        if self.__state != _CS_REQ_SENT or self.__response:
1036
            raise ResponseNotReady(self.__state)
1037

1038
        if self.debuglevel > 0:
Jeremy Hylton's avatar
Jeremy Hylton committed
1039
            response = self.response_class(self.sock, self.debuglevel,
1040
                                           method=self._method)
1041
        else:
1042
            response = self.response_class(self.sock, method=self._method)
1043

1044
        response.begin()
1045
        assert response.will_close != _UNKNOWN
1046 1047 1048
        self.__state = _CS_IDLE

        if response.will_close:
1049 1050
            # this effectively passes the connection to the response
            self.close()
1051 1052 1053 1054 1055
        else:
            # remember this, so we can tell when it is complete
            self.__response = response

        return response
1056

1057 1058 1059 1060 1061 1062 1063
try:
    import ssl
except ImportError:
    pass
else:
    class HTTPSConnection(HTTPConnection):
        "This class allows communication via SSL."
1064

1065
        default_port = HTTPS_PORT
1066

1067 1068
        # XXX Should key_file and cert_file be deprecated in favour of context?

1069
        def __init__(self, host, port=None, key_file=None, cert_file=None,
1070
                     strict=_strict_sentinel, timeout=socket._GLOBAL_DEFAULT_TIMEOUT,
1071
                     source_address=None, *, context=None, check_hostname=None):
1072 1073
            super(HTTPSConnection, self).__init__(host, port, strict, timeout,
                                                  source_address)
1074 1075
            self.key_file = key_file
            self.cert_file = cert_file
1076 1077 1078 1079 1080 1081 1082 1083 1084 1085 1086
            if context is None:
                # Some reasonable defaults
                context = ssl.SSLContext(ssl.PROTOCOL_SSLv23)
                context.options |= ssl.OP_NO_SSLv2
            will_verify = context.verify_mode != ssl.CERT_NONE
            if check_hostname is None:
                check_hostname = will_verify
            elif check_hostname and not will_verify:
                raise ValueError("check_hostname needs a SSL context with "
                                 "either CERT_OPTIONAL or CERT_REQUIRED")
            if key_file or cert_file:
1087
                context.load_cert_chain(cert_file, key_file)
1088 1089
            self._context = context
            self._check_hostname = check_hostname
1090

1091 1092
        def connect(self):
            "Connect to a host on a given (SSL) port."
1093

1094
            sock = socket.create_connection((self.host, self.port),
1095
                                            self.timeout, self.source_address)
1096 1097 1098 1099 1100

            if self._tunnel_host:
                self.sock = sock
                self._tunnel()

1101 1102 1103
            server_hostname = self.host if ssl.HAS_SNI else None
            self.sock = self._context.wrap_socket(sock,
                                                  server_hostname=server_hostname)
1104 1105 1106 1107 1108 1109 1110
            try:
                if self._check_hostname:
                    ssl.match_hostname(self.sock.getpeercert(), self.host)
            except Exception:
                self.sock.shutdown(socket.SHUT_RDWR)
                self.sock.close()
                raise
1111

1112
    __all__.append("HTTPSConnection")
1113 1114

class HTTPException(Exception):
Jeremy Hylton's avatar
Jeremy Hylton committed
1115 1116
    # Subclasses that define an __init__ must call Exception.__init__
    # or define self.args.  Otherwise, str() will fail.
1117
    pass
1118 1119

class NotConnected(HTTPException):
1120
    pass
1121

1122 1123 1124
class InvalidURL(HTTPException):
    pass

1125
class UnknownProtocol(HTTPException):
1126
    def __init__(self, version):
Jeremy Hylton's avatar
Jeremy Hylton committed
1127
        self.args = version,
1128
        self.version = version
1129 1130

class UnknownTransferEncoding(HTTPException):
1131
    pass
1132 1133

class UnimplementedFileMode(HTTPException):
1134
    pass
1135 1136

class IncompleteRead(HTTPException):
1137
    def __init__(self, partial, expected=None):
Jeremy Hylton's avatar
Jeremy Hylton committed
1138
        self.args = partial,
1139
        self.partial = partial
1140 1141 1142 1143 1144 1145 1146 1147 1148
        self.expected = expected
    def __repr__(self):
        if self.expected is not None:
            e = ', %i more expected' % self.expected
        else:
            e = ''
        return 'IncompleteRead(%i bytes read%s)' % (len(self.partial), e)
    def __str__(self):
        return repr(self)
1149 1150

class ImproperConnectionState(HTTPException):
1151
    pass
1152 1153

class CannotSendRequest(ImproperConnectionState):
1154
    pass
1155 1156

class CannotSendHeader(ImproperConnectionState):
1157
    pass
1158 1159

class ResponseNotReady(ImproperConnectionState):
1160
    pass
1161 1162

class BadStatusLine(HTTPException):
1163
    def __init__(self, line):
1164 1165
        if not line:
            line = repr(line)
Jeremy Hylton's avatar
Jeremy Hylton committed
1166
        self.args = line,
1167
        self.line = line
1168

1169 1170 1171 1172 1173
class LineTooLong(HTTPException):
    def __init__(self, line_type):
        HTTPException.__init__(self, "got more than %d bytes when reading %s"
                                     % (_MAXLINE, line_type))

1174 1175
# for backwards compatibility
error = HTTPException