mirror of https://github.com/golang/go.git
document http
R=r DELTA=84 (63 added, 4 deleted, 17 changed) OCL=25950 CL=26126
This commit is contained in:
parent
5559ff6ece
commit
32bf48c6d8
|
|
@ -4,6 +4,11 @@
|
|||
|
||||
// HTTP Request reading and parsing.
|
||||
|
||||
// The http package implements parsing of HTTP requests and URLs
|
||||
// and provides an extensible HTTP server.
|
||||
//
|
||||
// In the future it should also implement parsing of HTTP replies
|
||||
// and provide methods to fetch URLs via HTTP.
|
||||
package http
|
||||
|
||||
import (
|
||||
|
|
@ -20,6 +25,7 @@ const (
|
|||
maxHeaderLines = 1024;
|
||||
)
|
||||
|
||||
// HTTP request parsing errors.
|
||||
var (
|
||||
LineTooLong = os.NewError("http header line too long");
|
||||
ValueTooLong = os.NewError("http header value too long");
|
||||
|
|
@ -29,29 +35,67 @@ var (
|
|||
BadHTTPVersion = os.NewError("unsupported http version");
|
||||
)
|
||||
|
||||
// HTTP Request
|
||||
// A Request represents a parsed HTTP request header.
|
||||
type Request struct {
|
||||
Method string; // GET, PUT,etc.
|
||||
RawUrl string;
|
||||
Url *URL; // URI after GET, PUT etc.
|
||||
RawUrl string; // The raw URL given in the request.
|
||||
Url *URL; // URL after GET, PUT etc.
|
||||
Proto string; // "HTTP/1.0"
|
||||
ProtoMajor int; // 1
|
||||
ProtoMinor int; // 0
|
||||
|
||||
// A header mapping request lines to their values.
|
||||
// If the header says
|
||||
//
|
||||
// Accept-Language: en-us
|
||||
// accept-encoding: gzip, deflate
|
||||
// Connection: keep-alive
|
||||
//
|
||||
// then
|
||||
//
|
||||
// Header = map[string]string{
|
||||
// "Accept-Encoding": "en-us",
|
||||
// "Accept-Language": "gzip, deflate",
|
||||
// "Connection": "keep-alive"
|
||||
// }
|
||||
//
|
||||
// HTTP defines that header names are case-insensitive.
|
||||
// The request parser implements this by canonicalizing the
|
||||
// name, making the first character and any characters
|
||||
// following a hyphen uppercase and the rest lowercase.
|
||||
Header map[string] string;
|
||||
|
||||
// Whether to close the connection after replying to this request.
|
||||
Close bool;
|
||||
|
||||
// The host on which the URL is sought.
|
||||
// Per RFC 2616, this is either the value of the Host: header
|
||||
// or the host name given in the URL itself.
|
||||
Host string;
|
||||
Referer string; // referer [sic]
|
||||
|
||||
// The referring URL, if sent in the request.
|
||||
//
|
||||
// Referer is misspelled as in the request itself,
|
||||
// a mistake from the earliest days of HTTP.
|
||||
// This value can also be fetched from the Header map
|
||||
// as Header["Referer"]; the benefit of making it
|
||||
// available as a structure field is that the compiler
|
||||
// can diagnose programs that use the alternate
|
||||
// (correct English) spelling req.Referrer but cannot
|
||||
// diagnose programs that use Header["Referrer"].
|
||||
Referer string;
|
||||
|
||||
// The User-Agent: header string, if sent in the request.
|
||||
UserAgent string;
|
||||
}
|
||||
|
||||
// ProtoAtLeast returns whether the HTTP protocol used
|
||||
// in the request is at least major.minor.
|
||||
func (r *Request) ProtoAtLeast(major, minor int) bool {
|
||||
return r.ProtoMajor > major ||
|
||||
r.ProtoMajor == major && r.ProtoMinor >= minor
|
||||
}
|
||||
|
||||
|
||||
// Read a line of bytes (up to \n) from b.
|
||||
// Give up if the line exceeds maxLineLength.
|
||||
// The returned bytes are a pointer into storage in
|
||||
|
|
@ -188,6 +232,11 @@ func parseHTTPVersion(vers string) (int, int, bool) {
|
|||
|
||||
var cmap = make(map[string]string)
|
||||
|
||||
// CanonicalHeaderKey returns the canonical format of the
|
||||
// HTTP header key s. The canonicalization converts the first
|
||||
// letter and any letter following a hyphen to upper case;
|
||||
// the rest are converted to lowercase. For example, the
|
||||
// canonical key for "accept-encoding" is "Accept-Encoding".
|
||||
func CanonicalHeaderKey(s string) string {
|
||||
if t, ok := cmap[s]; ok {
|
||||
return t;
|
||||
|
|
@ -216,8 +265,7 @@ func CanonicalHeaderKey(s string) string {
|
|||
return t;
|
||||
}
|
||||
|
||||
|
||||
// Read and parse a request from b.
|
||||
// ReadRequest reads and parses a request from b.
|
||||
func ReadRequest(b *bufio.BufRead) (req *Request, err *os.Error) {
|
||||
req = new(Request);
|
||||
|
||||
|
|
|
|||
|
|
@ -2,10 +2,9 @@
|
|||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
// HTTP status codes. See RFC 2616.
|
||||
|
||||
package http
|
||||
|
||||
// HTTP status codes, defined in RFC 2616.
|
||||
const (
|
||||
StatusContinue = 100;
|
||||
StatusSwitchingProtocols = 101;
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ import (
|
|||
"strings"
|
||||
)
|
||||
|
||||
// Errors introduced by ParseURL.
|
||||
var (
|
||||
BadURL = os.NewError("bad url syntax")
|
||||
)
|
||||
|
|
@ -40,7 +41,10 @@ func unhex(c byte) byte {
|
|||
return 0
|
||||
}
|
||||
|
||||
// Unescape %xx into hex.
|
||||
// URLUnescape unescapes a URL-encoded string,
|
||||
// converting %AB into the byte 0xAB.
|
||||
// It returns a BadURL error if each % is not followed
|
||||
// by two hexadecimal digits.
|
||||
func URLUnescape(s string) (string, *os.Error) {
|
||||
// Count %, check that they're well-formed.
|
||||
n := 0;
|
||||
|
|
@ -76,16 +80,19 @@ func URLUnescape(s string) (string, *os.Error) {
|
|||
return string(t), nil;
|
||||
}
|
||||
|
||||
// A URL represents a parsed URL (technically, a URI reference).
|
||||
// The general form represented is:
|
||||
// scheme://[userinfo@]host/path[?query][#fragment]
|
||||
type URL struct {
|
||||
Raw string;
|
||||
Scheme string;
|
||||
RawPath string;
|
||||
Authority string;
|
||||
Userinfo string;
|
||||
Host string;
|
||||
Path string;
|
||||
Query string;
|
||||
Fragment string;
|
||||
Raw string; // the original string
|
||||
Scheme string; // scheme
|
||||
RawPath string; // //[userinfo@]host/path[?query][#fragment]
|
||||
Authority string; // [userinfo@]host
|
||||
Userinfo string; // userinfo
|
||||
Host string; // host
|
||||
Path string; // /path
|
||||
Query string; // query
|
||||
Fragment string; // fragment
|
||||
}
|
||||
|
||||
// Maybe rawurl is of the form scheme:path.
|
||||
|
|
@ -126,7 +133,12 @@ func split(s string, c byte, cutc bool) (string, string) {
|
|||
return s, ""
|
||||
}
|
||||
|
||||
// Parse rawurl into a URL structure.
|
||||
// BUG(rsc): ParseURL should canonicalize the path,
|
||||
// removing unnecessary . and .. elements.
|
||||
|
||||
// ParseURL parses rawurl into a URL structure.
|
||||
// The string rawurl is assumed not to have a #fragment suffix.
|
||||
// (Web browsers strip #fragment before sending the URL to a web server.)
|
||||
func ParseURL(rawurl string) (url *URL, err *os.Error) {
|
||||
if rawurl == "" {
|
||||
return nil, BadURL
|
||||
|
|
@ -171,7 +183,7 @@ func ParseURL(rawurl string) (url *URL, err *os.Error) {
|
|||
return url, nil
|
||||
}
|
||||
|
||||
// A URL reference is a URL with #frag potentially added. Parse it.
|
||||
// ParseURLReference is like ParseURL but allows a trailing #fragment.
|
||||
func ParseURLReference(rawurlref string) (url *URL, err *os.Error) {
|
||||
// Cut off #frag.
|
||||
rawurl, frag := split(rawurlref, '#', true);
|
||||
|
|
|
|||
Loading…
Reference in New Issue