func Handle(pattern string, handler Handler)将handler按照指定的格式注册到
DefaultServeMux,ServeMux解释了模式匹配规则
func HandleFunc(pattern string, handler func(ResponseWriter, *Request))同上,主要用来实现动
态文件内容的展示,这点与ServerFile()不同的地方。
func ListenAndServe(addr string, handler Handler) error监听TCP网络地址addr然后调用具有
handler的Serve去处理连接请求.通常情况下Handler是nil,使用默认的DefaultServeMux
func ListenAndServeTLS(addr string, certFile string, keyFile string, handler Handler)
error该函数与ListenAndServe功能基本相同,二者不同之处是该函数需要HTTPS连接.也就是说,必须给该服务
Serve提供一个包含整数的秘钥的文件,如果证书是由证书机构签署的,那么证书文件必须是服务证书之后跟着CA
证书.
func ServeFile(w ResponseWriter, r *Request, name string)利用指定的文件或者目录的内容来响应
相应的请求.
func SetCookie(w ResponseWriter, cookie *Cookie)给w设定cookie
func StatusText(code int) string对于http状态码返回文本表示,如果这个code未知,则返回空的字符串
func MaxBytesReader(w ResponseWriter, r io.ReadCloser, n int64) io.ReadCloser该函数类似于
io.LimitReader但是该函数是用来限制请求体的大小.与io.LimitReader不同的是,该函数返回一个
ReaderCloser,当读超过限制时,返回一个non-EOF,并且当Close方法调用时,关闭底层的reader.该函数组织
客户端恶意发送大量请求,浪费服务器资源.
func ParseHTTPVersion(vers string) (major, minor int, ok bool)解析http字符串版本进行解
析,”HTTP/1.0” 返回 (1, 0, true)
func ProxyURL(fixedURL *url.URL) func(*Request) (*url.URL, error)返回一个用于传输的代理函
数,该函数总是返回相同的URL
func Redirect(w ResponseWriter, r *Request, urlStr string, code int)返回一个重定向的url给指
定的请求,这个重定向url可能是一个相对请求路径的一个相对路径.
func Serve(l net.Listener, handler Handler) error该函数接受listener l的传入http连接,对于每
一个连接创建一个新的服务协程,这个服务协程读取请求然后调用handler来给他们响应.handler一般为nil,这
样默认的DefaultServeMux被使用.
Client具有Do,Get,Head,Post以及PostForm等方法。 其中Do方法可以对Request进行一系列的设定,而其
他的对request设定较少。如果Client使用默认的Client,则其中的Get,Head,Post以及PostForm方法相当于
默认的http.Get,http.Post,http.Head以及http.PostForm函数。
func (c *Client) Do(req *Request) (resp *Response, err error)Do发送http请求并且返回一个http响
应,遵守client的策略,如重定向,cookies以及auth等.错误经常是由于策略引起的,当err是nil时,resp总会包含
一个非nil的resp.body.当调用者读完resp.body之后应该关闭它,如果resp.body没有关闭,则Client底层
RoundTripper将无法重用存在的TCP连接去服务接下来的请求,如果resp.body非nil,则必须对其进行关闭.通常
来说,经常使用Get,Post,或者PostForm来替代Do.
func (c *Client) Get(url string) (resp *Response, err error)利用get方法请求指定的url.Get请求
指定的页面信息,并返回实体主体。
func (c *Client) Head(url string) (resp *Response, err error)利用head方法请求指定的url,Head
只返回页面的首部。
func (c *Client) Post(url string, bodyType string, body io.Reader) (resp *Response, err
error)利用post方法请求指定的URl,如果body也是一个io.Closer,则在请求之后关闭它
func (c *Client) PostForm(url string, data url.Values) (resp *Response, err error)利用post方
法请求指定的url,利用data的key和value作为请求体.
Do方法可以灵活的对request进行配置,然后进行请求。利用http.Client以及http.NewRequest来模拟请求。模
拟request中带有cookie的请求。示例如下:
package main
import (
// "encoding/json"
"fmt"
"io/ioutil"
"net/http"
"strconv"
)
func main() {
client := &http.Client{}
request, err := http.NewRequest("GET", "http://www.baidu.com", nil)
if err != nil {
fmt.Println(err)
}
cookie := &http.Cookie{Name: "userId", Value: strconv.Itoa(12345)}
request.AddCookie(cookie) //request中添加cookie
//设置request的header
request.Header.Set("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8")
request.Header.Set("Accept-Charset", "GBK,utf-8;q=0.7,*;q=0.3")
request.Header.Set("Accept-Encoding", "gzip,deflate,sdch")
request.Header.Set("Accept-Language", "zh-CN,zh;q=0.8")
request.Header.Set("Cache-Control", "max-age=0")
request.Header.Set("Connection", "keep-alive")
response, err := client.Do(request)
if err != nil {
fmt.Println(err)
return
}
defer response.Body.Close()
fmt.Println(response.StatusCode)
if response.StatusCode == 200 {
r, err := ioutil.ReadAll(response.Body)
if err != nil {
fmt.Println(err)
}
fmt.Println(string(r))
}
}
type Client
Client是一个http客户端,默认客户端(DefaultClient)将使用默认的发送机制的客户端.Client的Transport字段一般会含有内部状态(缓存TCP连接),因此Client类型值应尽量被重用而不是创建新的。多个协程并发使用Clients是安全的.
type Client struct {
// Transport指定执行独立、单次HTTP请求的机制如果Transport为nil,则使用DefaultTransport。
Transport RoundTripper
// CheckRedirect指定处理重定向的策略,如果CheckRedirect非nil,client将会在调用重定向之前调用它。参
数req和via是将要执行的请求和已经执行的请求(时间越久的请求优先执行),如果CheckRedirect返回一个错
误,client的GetGet方法不会发送请求req,而是回之前得到的响应和该错误。如果CheckRedirect为nil,会采用
默认策略:在连续10次请求后停止。
CheckRedirect func(req *Request, via []*Request) error
// Jar指定cookie管理器,如果Jar为nil,在请求中不会发送cookie,在回复中cookie也会被忽略。
Jar CookieJar
// Timeout指定Client请求的时间限制,该超时限制包括连接时间、重定向和读取response body时间。计时器
会在Head,Get,Post或Do方法返回后开始计时并在读到response.body后停止计时。Timeout为零值表示不设置超
时。Client的Transport字段必须支持CancelRequest方法,否则Client会在尝试用Head,Get,Post或Do方法执
行请求时返回错误。Client的Transport字段默认值(DefaultTransport)支持CancelRequest方法。
Timeout time.Duration
}
type ConnState表示客户端连接服务端的状态,其中ConnState常用状态变量如下:
const (
// StateNew代表一个新的连接,将要立刻发送请求。
// 连接从这个状态开始,然后转变为StateAlive或StateClosed。
StateNew ConnState = iota
// StateActive代表一个已经读取了请求数据1到多个字节的连接。
// 用于StateAlive的Server.ConnState回调函数在将连接交付给处理器之前被触发,
// 等到请求被处理完后,Server.ConnState回调函数再次被触发。
// 在请求被处理后,连接状态改变为StateClosed、StateHijacked或StateIdle。
StateActive
// StateIdle代表一个已经处理完了请求、处在闲置状态、等待新请求的连接。
// 连接状态可以从StateIdle改变为StateActive或StateClosed。
StateIdle
// 代表一个被劫持的连接。这是一个终止状态,不会转变为StateClosed。
StateHijacked
// StateClosed代表一个关闭的连接。
// 这是一个终止状态。被劫持的连接不会转变为StateClosed。
StateClosed
)
type Cookie常用SetCooker用来给http的请求或者http的response设置cookie
type Cookie struct {
Name string //名字
Value string //值
Path string //路径
Domain string
Expires time.Time //过期时间
RawExpires string
// MaxAge=0 意味着 没有'Max-Age'属性指定.
// MaxAge<0 意味着 立即删除cookie
// MaxAge>0 意味着设定了MaxAge属性,并且其单位是秒
MaxAge int
Secure bool
HttpOnly bool
Raw string
Unparsed []string // 未解析的属性值对
}
func (c *Cookie) String() string
该函数返回cookie的序列化结果。如果只设置了Name和Value字段,序列化结果可用于HTTP请求的Cookie头或者HTTP回复的Set-Cookie头;如果设置了其他字段,序列化结果只能用于HTTP回复的Set-Cookie头。 type CookieJar
在http请求中,CookieJar管理存储和使用cookies.Cookiejar的实现必须被多协程并发使用时是安全的.
type CookieJar interface {
// SetCookies 处理从url接收到的cookie,是否存储这个cookies取决于jar的策略和实现
SetCookies(u *url.URL, cookies []*Cookie)
// Cookies 返回发送到指定url的cookies
Cookies(u *url.URL) []*Cookie
}
type Dir使用一个局限于指定目录树的本地文件系统实现一个文件系统.一个空目录被当做当前目录
type Dir string
func (d Dir) Open(name string) (File, error)type FileFile是通过FileSystem的Open方法返回的,并且能够被FileServer实现.该方法与*os.File行为表现一样
type File interface {
io.Closer
io.Reader
Readdir(count int) ([]os.FileInfo, error)
Seek(offset int64, whence int) (int64, error)
Stat() (os.FileInfo, error)
}
type FileSystem实现了对一系列指定文件的访问,其中文件路径之间通过分隔符进行分割
type FileSystem interface {
Open(name string) (File, error)
}
type Flusherresponsewriters允许http控制器将缓存数据刷新入client.然而如果client是通过http代理连接服务器,这个缓存数据也可能是在整个response结束后才能到达客户端
type Flusher interface {
// Flush将任何缓存数据发送到client
Flush()
}
type Handler实现Handler接口的对象可以注册到HTTP服务端,为指定的路径或者子树提供服务。ServeHTTP应该将回复的header和数据写入ResponseWriter接口然后返回。返回意味着该请求已经结束,HTTP服务端可以转移向该连接上的下一个请求。如果ServeHTTP崩溃panic,那么ServeHTTP的调用者假定这个panic的影响与活动请求是隔离的,二者互不影响.调用者恢复panic,将stack trace记录到错误日志中,然后挂起这个连接.
type Handler interface {
ServeHTTP(ResponseWriter, *Request)
}
func FileServer(root FileSystem) HandlerFileServer返回一个使用FileSystem接口提供文件访问服务的HTTP处理器。可以使用httpDir来使用操作系统的FileSystem接口实现。其主要用来实现静态文件的展示。
func NotFoundHandler() Handler返回一个简单的请求处理器,该处理器对任何请求都会返回”404 page not found”
func RedirectHandler(url string, code int) Handler使用给定的状态码将它接受到的任何请求都重定向到给定的url
func StripPrefix(prefix string, h Handler) Handler将请求url.path中移出指定的前缀,然后将省下的请求交给handler h来处理,对于那些不是以指定前缀开始的路径请求,该函数返回一个http 404 not found 的错误.
func TimeoutHandler(h Handler, dt time.Duration, msg string) Handler具有超时限制的handler,该函数返回的新Handler调用h中的ServerHTTP来处理每次请求,但是如果一次调用超出时间限制,那么就会返回给请求者一个503服务请求不可达的消息,并且在ResponseWriter返回超时错误.
其中FileServer经常和StripPrefix一起连用,用来实现静态文件展示,举例如下:
package main
import (
"fmt"
"net/http"
)
func main() {
http.Handle("/test/", http.FileServer(http.Dir("/home/work/"))) ///home/work/test/中必须有内容
http.Handle("/download/", http.StripPrefix("/download/", http.FileServer(http.Dir("/home/work/"))))
http.Handle("/tmpfiles/", http.StripPrefix("/tmpfiles/", http.FileServer(http.Dir("/tmp")))) //127.0.0.1:9999/tmpfiles/访问的本地文件/tmp中的内容
http.ListenAndServe(":9999", nil)
}
type HandlerFuncHandlerFunc type是一个适配器,通过类型转换我们可以将普通的函数作为HTTP处理器使用。如果f是一个具有适当签名的函数,HandlerFunc(f)通过调用f实现了Handler接口。
type Hijacker interface {
// Hijack让调用者接管连接,在调用Hijack()后,http server库将不再对该连接进行处理,对于该连接的管理和关闭责任将由调用者接管.
Hijack() (net.Conn, *bufio.ReadWriter, error) //conn表示连接对象,bufrw代表该连接的读写缓存对象。
}
Hijacker用法如下所示:
package main
import (
"fmt"
"net/http"
)
func HiJack(w http.ResponseWriter, r *http.Request) {
hj, ok := w.(http.Hijacker)
if !ok {
http.Error(w, "webserver doesn't support hijacking", http.StatusInternalServerError)
return
}
conn, bufrw, err := hj.Hijack()
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
defer conn.Close()
bufrw.WriteString("Now we're speaking raw TCP. Say hi: \n")
bufrw.Flush()
fmt.Fprintf(bufrw, "You said: %s Bye.\n", "Good")
bufrw.Flush()
}
func main() {
http.HandleFunc("/hijack", HiJack)
err := http.ListenAndServe(":9999", nil)
if err != nil {
fmt.Println(err)
}
}