Codis源码解析——fe的启动

来源:互联网 发布:高达模型淘宝店 编辑:程序博客网 时间:2024/06/06 21:56

虽然dashboard负责对集群的实际操作,但是用户的最直观操作,都是来自于fe的。这一节我们就来讲fe的启动,没有proxy和dashboard那么复杂。

首先,启动的时候指定fe的监听端口,这个就是我们最后通过浏览器打开fe的端口

--listen=0.0.0.0:18090

然后根据系统参数找到assets文件夹目录,再在这个目录下寻找index.html,没错,就是浏览器中看到的html。如果在本地启动的时候这一步报错,assets目录下找不到index.html,就自己手动写死assets的地址即可。

indexFile := filepath.Join(assets, "index.html")if _, err := os.Stat(indexFile); err != nil {    log.PanicErrorf(err, "get stat of %s failed", indexFile)}

接下来,找启动的时候配置的codis.json。通过codis.json连接到dashboard,fe就算是和集群关联起来了。

if d["--dashboard-list"] != nil {    file := utils.ArgumentMust(d, "--dashboard-list")    //只有一个字符串属性,指向codis.json的位置    loader = &StaticLoader{file}    log.Warnf("set --dashboard-list = %s", file)} .....//router是一个ReverseProxy结构,后面很多操作都是关于这个router的router := NewReverseProxy(loader)type ReverseProxy struct {    sync.Mutex    loadAt time.Time    loader ConfigLoader    //这个httputil.ReverseProxy,相当于一个请求的handler,收到客户端请求,将请求转发给另一个服务器,再将响应发回给客户端    routes map[string]*httputil.ReverseProxy}func NewReverseProxy(loader ConfigLoader) *ReverseProxy {    r := &ReverseProxy{}    r.loader = loader    //到目前为止只是把routes的结构初始化好,里面还是空的    r.routes = make(map[string]*httputil.ReverseProxy)    return r}

使用martini框架,新建路由和handler

m := martini.New()m.Use(martini.Recovery())m.Use(render.Renderer())m.Use(martini.Static(assets, martini.StaticOptions{SkipLogging: true}))//新建一个路由实例r := martini.NewRouter()r.Get("/list", func() (int, string) {    //遍历ReverseProxy的routes,将键值组成字符串切片    names := router.GetNames()    sort.Sort(sort.StringSlice(names))    return rpc.ApiResponseJson(names)})r.Any("/**", func(w http.ResponseWriter, req *http.Request) {    //发送请求,得到对应的响应    name := req.URL.Query().Get("forward")    //在router的routes属性中。取出name对应的ReverseProxy    if p := router.GetProxy(name); p != nil {        p.ServeHTTP(w, req)    } else {        w.WriteHeader(http.StatusForbidden)    }})m.MapTo(r, (*martini.Routes)(nil))m.Action(r.Handle)

最终我们得到了一个拥有完整规则的请求处理器handler,就是m。下一步,监听启动端口,新建路由表并将路由表指向刚才的martini框架的Router。最后一步,hs.Serve(l)这里,服务器接收指定监听器收到的请求,并为每个请求新建goroutine。goroutine负责读取并调用srv.Handler对请求进行相应

//监听10890端口,得到的l是一个Listenerl, err := net.Listen("tcp", listen)//新建路由表h := http.NewServeMux()h.Handle("/", m)hs := &http.Server{Handler: h}if err := hs.Serve(l); err != nil {    log.PanicErrorf(err, "serve %s failed", listen)}

补充一下go语言路由表的知识,路由表实际就是一个map。这个map的键就是路径,比如本例的”/”,值就是对应的handler,比如本例中的m。

go语言web服务器的工作流程如下:

  1. 创建并循环监听listen socket。
  2. 监听器监听到新的请求,并创建网络连接conn,然后开启一个goroutine负责处理该链接。
  3. 从链接根据请求参数构造出http.Request对象,然后根据请求路径在路由表中查找,把请求转发给对应的应用层的处理函数。
  4. 处理函数进行处理,并将响应返回给用户
  5. 应用层处理完该链接请求后关闭该链接,如果是http alive则不关闭

到这里,fe也已经启动成功,后面只需要用户对fe进行操作即可。

这里写图片描述

如果你前面已经成功启动了dashboard和proxy,打开浏览器输入下图中的地址,就能看到完整的页面了

这里写图片描述

说明
如有转载,请注明出处
http://blog.csdn.net/antony9118/article/details/76071846

原创粉丝点击