圈圈套圈圈(水)

package main

import (
    "encoding/json"
    "flag"
    "github.com/elazarl/goproxy"
    "gopkg.in/mgo.v2"
    "gopkg.in/mgo.v2/bson"
    "log"
    "net/http"
    _ "os"
    _ "reflect"
    "time"
)

type SimpleReq struct {
    host  string
    count int
}

func doWriting(reqChan chan string) {

    // W100:
    for {
        sess, err := mgo.Dial("localhost")
        if err != nil {
            time.Sleep(20 * time.Second)
            continue
        }
        log.Println("db recording is ready")
        collect := sess.DB("netstat").C("req")
        incEvt := mgo.Change{
            Upsert:    true,
            ReturnNew: true,
            Update:    bson.M{"$inc": bson.M{"time": 1}},
        }
    B100:
        for {
            select {
            // case <-closeSig:
            //  break W100
            case reqHost := <-reqChan:
                var result interface{}
                _, er1 := collect.Find(bson.M{"reqHost": reqHost}).Apply(incEvt, &result)
                if er1 != nil {
                    log.Println("db failure")
                    break B100
                }
                //~ 删掉一个域??
                if resChunk, e := json.Marshal(result); e == nil {
                    log.Printf("%v", string(resChunk))
                }
            }
        }
    }
}

func main() {
    verbose := flag.Bool("v", false, "should every proxy request be logged to stdout")
    addr := flag.String("addr", ":8080", "proxy listen address")
    flag.Parse()
    proxy := goproxy.NewProxyHttpServer()
    proxy.Verbose = *verbose

    interchange := make(chan string, 1024)
    go doWriting(interchange)

    proxy.OnRequest().DoFunc(func(req *http.Request, ctx *goproxy.ProxyCtx) (*http.Request, *http.Response) {
        // log.Printf("request url: <%v>", req.URL)
        // log.Printf("request url path: <%v>", req.URL.Path)
        // log.Printf("request for <%v> from <%v>", req.URL.Host, req.RemoteAddr)

        //~ Record all the host
        interchange <- req.URL.Host

        // Attempt 1: // It will drain the Body. Fails.
        // bytes, _ := io.ioutil.ReadAll(req.Body)

        // Attempt 2: // Fails. GetBody is nil
        // body, _ := req.GetBody()         // call to nil func
        // bytes, _ := ioutil.ReadAll(body) // instead of req.Body

        // Attempt 3:
        // if req.Body != nil {
        //  body, _ := ioutil.ReadAll(req.Body)
        //  req.Body = &FakeReadCloser{bytes.NewReader(body)}
        //  //log.Printf("request body is <%v>", string(body))
        // }
        //log.Println()
        return req, nil
    })

    log.Fatal(http.ListenAndServe(*addr, proxy))
}

若需看帮助的话, mgo的这货带有“点“:
go doc mgo.v2.Collection
go doc mgo.v2.Query.Apply
帮助还是挺详尽的。

你可能感兴趣的:(golang)