diff --git a/etc/init.sh b/etc/init.sh index be894db1..aa69a93a 100644 --- a/etc/init.sh +++ b/etc/init.sh @@ -1,9 +1,6 @@ -alias ~ context -alias ! history -alias @ config -alias $ cache -alias & server -alias * message +@debug off +~tcp +listen :9393 +~aaa +login shy shy -~web -listen :9393 etc diff --git a/src/context/aaa/aaa.go b/src/context/aaa/aaa.go new file mode 100644 index 00000000..f4bd483a --- /dev/null +++ b/src/context/aaa/aaa.go @@ -0,0 +1,105 @@ +package aaa // {{{ +// }}} +import ( // {{{ + "context" + "log" + "time" +) + +// }}} + +type AAA struct { + username string + password string + logintime time.Time + *ctx.Context +} + +func (aaa *AAA) Begin(m *ctx.Message) ctx.Server { // {{{ + return aaa +} + +// }}} +func (aaa *AAA) Start(m *ctx.Message) bool { // {{{ + return true +} + +// }}} +func (aaa *AAA) Spawn(c *ctx.Context, m *ctx.Message, arg ...string) ctx.Server { // {{{ + c.Caches = map[string]*ctx.Cache{} + c.Configs = map[string]*ctx.Config{} + c.Commands = map[string]*ctx.Command{} + + s := new(AAA) + s.username = arg[0] + s.password = arg[1] + s.logintime = time.Now() + s.Context = c + return s +} + +// }}} +func (aaa *AAA) Exit(m *ctx.Message, arg ...string) bool { // {{{ + return true +} + +// }}} +var Index = &ctx.Context{Name: "aaa", Help: "会话管理", + Caches: map[string]*ctx.Cache{ + "status": &ctx.Cache{Name: "status", Value: "stop", Help: "服务状态"}, + "root": &ctx.Cache{Name: "root", Value: "root", Help: "初始用户"}, + }, + Configs: map[string]*ctx.Config{}, + Commands: map[string]*ctx.Command{ + "login": &ctx.Command{Name: "login [username [password]]", Help: "会话管理", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + switch len(arg) { + case 0: + m.Target.Travel(func(s *ctx.Context) bool { + aaa := s.Server.(*AAA) + m.Echo("%s(%s): %s\n", s.Name, aaa.username, aaa.logintime.Format("15:04:05")) + return true + }) + case 1: + m.Target.Travel(func(s *ctx.Context) bool { + aaa := s.Server.(*AAA) + if aaa.username == arg[0] { + m.Echo("%s(%s): %s\n", s.Name, aaa.username, aaa.logintime.Format("15:04:05")) + return false + } + return true + }) + case 2: + m.Target.Travel(func(s *ctx.Context) bool { + aaa := s.Server.(*AAA) + if aaa.username == arg[0] { + m.Add("result", arg[0]) + if aaa.password == arg[1] { + m.Add("result", time.Now().Format("15:04:05")) + } + return false + } + return true + }) + if m.Get("result") == arg[0] { + if len(m.Meta["result"]) == 2 { + m.Echo("login success\n") + log.Println("login success") + } else { + m.Echo("login error\n") + log.Println("login error") + } + } else { + m.Start(arg[0], arg[1]) + m.Add("result", arg[0]) + } + } + return "" + }}, + }, +} + +func init() { + aaa := &AAA{username: "root", password: "root", logintime: time.Now()} + aaa.Context = Index + ctx.Index.Register(Index, aaa) +} diff --git a/src/context/cli/cli.go b/src/context/cli/cli.go index e4685969..566b07b0 100644 --- a/src/context/cli/cli.go +++ b/src/context/cli/cli.go @@ -155,8 +155,8 @@ func (cli *CLI) Start(m *ctx.Message) bool { // {{{ cli.Capi("nterm", 1) defer cli.Capi("nterm", -1) - if detail, ok := m.Data["detail"]; ok { - io := detail.(io.ReadWriteCloser) + if stream, ok := m.Data["io"]; ok { + io := stream.(io.ReadWriteCloser) cli.out = io cli.push(io) @@ -206,12 +206,21 @@ func (cli *CLI) Spawn(c *ctx.Context, m *ctx.Message, arg ...string) ctx.Server c.Configs = map[string]*ctx.Config{ "address": &ctx.Config{Name: "address", Value: arg[0], Help: "监听地址"}, "protocol": &ctx.Config{Name: "protocol", Value: arg[1], Help: "监听协议"}, + "init.sh": &ctx.Config{Name: "init.sh", Value: "", Help: "默认启动脚本"}, } c.Commands = cli.Commands c.Messages = make(chan *ctx.Message, 10) s := new(CLI) s.Context = c + s.alias = map[string]string{ + "~": "context", + "!": "history", + "@": "config", + "$": "cache", + "&": "server", + "*": "message", + } return s } @@ -225,7 +234,7 @@ func (cli *CLI) Exit(m *ctx.Message, arg ...string) bool { // {{{ // }}} -var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ +var Index = &ctx.Context{Name: "cli", Help: "管理终端", Caches: map[string]*ctx.Cache{ "nterm": &ctx.Cache{Name: "nterm", Value: "0", Help: "终端数量"}, "status": &ctx.Cache{Name: "status", Value: "stop", Help: "服务状态"}, @@ -244,8 +253,8 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ "slient": &ctx.Config{Name: "slient", Value: "yes", Help: "屏蔽脚本输出"}, "PS1": &ctx.Config{Name: "PS1", Value: "target", Help: "命令行提示符", Hand: func(c *ctx.Context, x *ctx.Config, arg ...string) string { - cli, ok := c.Server.(*CLI) - if ok && cli.target != nil { // {{{ + cli, ok := c.Server.(*CLI) // {{{ + if ok && cli.target != nil { // c = cli.target switch x.Value { case "target": @@ -261,7 +270,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ }}, }, Commands: map[string]*ctx.Command{ - "context": &ctx.Command{"context [spawn|find|search name [which]]|root|back|home", "查看上下文", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "context": &ctx.Command{Name: "context [spawn|find|search name [which]]|root|back|home", Help: "查看上下文", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { cli, ok := c.Server.(*CLI) // {{{ switch len(arg) { case 0: @@ -351,7 +360,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "message": &ctx.Command{"message detail...", "查看上下文", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "message": &ctx.Command{Name: "message detail...", Help: "查看上下文", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { // {{{ ms := []*ctx.Message{ctx.Pulse} for i := 0; i < len(ms); i++ { @@ -362,7 +371,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "server": &ctx.Command{"server start|stop|switch", "服务启动停止切换", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "server": &ctx.Command{Name: "server start|stop|switch", Help: "服务启动停止切换", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { s := m.Target // {{{ switch len(arg) { case 0: @@ -390,7 +399,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "source": &ctx.Command{"source file", "运行脚本", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "source": &ctx.Command{Name: "source file", Help: "运行脚本", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { cli := c.Server.(*CLI) // {{{ switch len(arg) { case 1: @@ -402,7 +411,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "alias": &ctx.Command{"alias [short [long]]", "查看日志", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "alias": &ctx.Command{Name: "alias [short [long]]", Help: "查看日志", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { cli := c.Server.(*CLI) // {{{ switch len(arg) { case 0: @@ -421,7 +430,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "history": &ctx.Command{"history number", "查看日志", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "history": &ctx.Command{Name: "history number", Help: "查看日志", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { cli := c.Server.(*CLI) // {{{ switch len(arg) { case 0: @@ -438,7 +447,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "command": &ctx.Command{"command [name [value [help]]]", "查看修改添加配置", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "command": &ctx.Command{Name: "command [name [value [help]]]", Help: "查看修改添加配置", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { switch len(arg) { // {{{ case 0: for k, v := range m.Target.Commands { @@ -461,7 +470,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "config": &ctx.Command{"config [name [value [help]]]", "查看修改添加配置", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "config": &ctx.Command{Name: "config [name [value [help]]]", Help: "查看修改添加配置", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { switch len(arg) { // {{{ case 0: for k, v := range m.Target.Configs { @@ -478,9 +487,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ delete(m.Target.Configs, arg[1]) } default: - if _, ok := m.Target.Configs[arg[0]]; ok { - m.Target.Conf(arg[0], arg[1:]...) - } + m.Target.Conf(arg[0], arg[1]) } case 4: m.Target.Conf(arg[0], arg[1:]...) @@ -488,7 +495,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "cache": &ctx.Command{"cache [name [value [help]]]", "查看修改添加配置", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "cache": &ctx.Command{Name: "cache [name [value [help]]]", Help: "查看修改添加配置", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { switch len(arg) { // {{{ case 0: for k, v := range m.Target.Caches { @@ -515,7 +522,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "exit": &ctx.Command{"exit", "退出", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "exit": &ctx.Command{Name: "exit", Help: "退出", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { cli, ok := m.Target.Server.(*CLI) // {{{ if !ok { cli, ok = m.Context.Server.(*CLI) @@ -531,7 +538,7 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "remote": &ctx.Command{"remote master|slave listen|dial address protocol", "建立远程连接", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "remote": &ctx.Command{Name: "remote master|slave listen|dial address protocol", Help: "建立远程连接", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { switch len(arg) { // {{{ case 0: case 4: @@ -550,17 +557,18 @@ var Index = &ctx.Context{Name: "cli", Help: "本地控制", // {{{ return "" // }}} }}, - "accept": &ctx.Command{"accept address protocl", "建立远程连接", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { - m.Start(fmt.Sprintf("PTS%d", c.Capi("nterm")), arg[1]) // {{{ - return "" - // }}} - }}, - "void": &ctx.Command{"", "", nil}, + "accept": &ctx.Command{Name: "accept address protocl", Help: "建立远程连接", + Options: map[string]string{"io": "读写流"}, + Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + m.Start(fmt.Sprintf("PTS%d", c.Capi("nterm")), arg[1]) // {{{ + return "" + // }}} + }}, + "void": &ctx.Command{Name: "", Help: "", Hand: nil}, }, Messages: make(chan *ctx.Message, 10), } -// }}} func init() { // {{{ cli := &CLI{alias: map[string]string{ "~": "context", diff --git a/src/context/ctx.go b/src/context/ctx.go index e2801892..bf4f9d6c 100644 --- a/src/context/ctx.go +++ b/src/context/ctx.go @@ -34,9 +34,11 @@ type Config struct { // {{{ // }}} type Command struct { // {{{ - Name string - Help string - Hand func(c *Context, m *Message, key string, arg ...string) string + Name string + Help string + Options map[string]string + Appends map[string]string + Hand func(c *Context, m *Message, key string, arg ...string) string } // }}} @@ -86,25 +88,48 @@ func (m *Message) Spawn(c *Context, key string) *Message { // {{{ // }}} -func (m *Message) Add(key string, value ...string) *Message { // {{{ +func (m *Message) Add(meta string, key string, value ...string) *Message { // {{{ if m.Meta == nil { m.Meta = make(map[string][]string) } - if _, ok := m.Meta[key]; !ok { - m.Meta[key] = make([]string, 0, 3) + if _, ok := m.Meta[meta]; !ok { + m.Meta[meta] = make([]string, 0, 3) + } + switch meta { + case "detail", "result": + m.Meta[meta] = append(m.Meta[meta], key) + m.Meta[meta] = append(m.Meta[meta], value...) + case "option", "append": + if _, ok := m.Meta[key]; !ok { + m.Meta[key] = make([]string, 0, 3) + m.Meta[meta] = append(m.Meta[meta], key) + } + m.Meta[key] = append(m.Meta[key], value...) + default: } - - m.Meta[key] = append(m.Meta[key], value...) return m } // }}} -func (m *Message) Put(key string, value interface{}) *Message { // {{{ +func (m *Message) Put(meta string, key string, value interface{}) *Message { // {{{ + if m.Meta == nil { + m.Meta = make(map[string][]string) + } if m.Data == nil { m.Data = make(map[string]interface{}) } - m.Data[key] = value + switch meta { + case "option", "append": + if _, ok := m.Meta[meta]; !ok { + m.Meta[meta] = make([]string, 0, 3) + } + if _, ok := m.Data[key]; !ok { + m.Meta[meta] = append(m.Meta[meta], key) + } + m.Data[key] = value + } + return m } @@ -226,6 +251,9 @@ type Context struct { func (c *Context) Check(e error) bool { // {{{ if e != nil { log.Println(c.Name, "error:", e) + if c.Conf("debug") == "on" { + fmt.Println(c.Name, "error:", e) + } panic(e) } return true @@ -235,8 +263,9 @@ func (c *Context) Check(e error) bool { // {{{ func (c *Context) Safe(m *Message, hand ...func(c *Context, m *Message)) (ok bool) { // {{{ defer func() { if e := recover(); e != nil { + log.Println(c.Name, "error:", e) if c.Conf("debug") == "on" { - log.Println(c.Name, "error:", e) + fmt.Println(c.Name, "error:", e) if e != io.EOF { debug.PrintStack() } @@ -400,6 +429,20 @@ func (c *Context) Exit(m *Message, arg ...string) { // {{{ // }}} +func (c *Context) Travel(hand func(s *Context) bool) { // {{{ + cs := []*Context{c} + for i := 0; i < len(cs); i++ { + for _, v := range cs[i].Contexts { + cs = append(cs, v) + } + + if !hand(cs[i]) { + return + } + } +} + +// }}} func (c *Context) Find(name []string) (s *Context) { // {{{ cs := c.Contexts for _, v := range name { @@ -601,6 +644,12 @@ func (c *Context) Del(arg ...string) { // {{{ // }}} func (c *Context) Cmd(m *Message, key string, arg ...string) string { // {{{ + if m.Meta == nil { + m.Meta = make(map[string][]string) + } + m.Meta["detail"] = nil + m.Add("detail", key, arg...) + for s := c; s != nil; s = s.Context { if x, ok := s.Commands[key]; ok { log.Printf("%s cmd(%s->%s): %v", c.Name, m.Context.Name, m.Target.Name, m.Meta["detail"]) @@ -608,6 +657,13 @@ func (c *Context) Cmd(m *Message, key string, arg ...string) string { // {{{ if x.Hand == nil { panic(errors.New(fmt.Sprintf(key + "没有权限"))) } + + for _, v := range m.Meta["option"] { + if _, ok := x.Options[v]; !ok { + panic(errors.New(fmt.Sprintf(v + "未知参数"))) + } + } + return x.Hand(c, m, key, arg...) } } @@ -745,7 +801,7 @@ var Index = &Context{Name: "ctx", Help: "根上下文", // {{{ }}, }, Commands: map[string]*Command{ - "void": &Command{"void", "建立远程连接", func(c *Context, m *Message, key string, arg ...string) string { + "void": &Command{Name: "void", Help: "建立远程连接", Hand: func(c *Context, m *Message, key string, arg ...string) string { m.Echo("hello void!\n") // {{{ return "" // }}} @@ -806,7 +862,7 @@ func Start() { for _, s := range Index.Contexts { if ok, _ := regexp.MatchString(Index.Conf("start"), s.Name); ok { n++ - go s.Start(Pulse.Spawn(s, s.Name).Put("detail", os.Stdout)) + go s.Start(Pulse.Spawn(s, s.Name).Put("option", "io", os.Stdout)) } } diff --git a/src/context/tcp/tcp.go b/src/context/tcp/tcp.go index 9da2bb40..e6e351eb 100644 --- a/src/context/tcp/tcp.go +++ b/src/context/tcp/tcp.go @@ -37,7 +37,7 @@ func (tcp *TCP) Start(m *ctx.Message) bool { // {{{ log.Printf("%s accept(%d): %v<-%v", tcp.Name, tcp.Capi("nclient", 1), c.LocalAddr(), c.RemoteAddr()) // defer log.Println(tcp.Name, "close:", tcp.Capi("nclient", -1), c.LocalAddr(), "<-", c.RemoteAddr()) - msg := m.Spawn(m.Context, c.RemoteAddr().String()).Put("detail", c) + msg := m.Spawn(m.Context, c.RemoteAddr().String()).Put("option", "io", c) msg.Cmd("accept", c.RemoteAddr().String(), "tcp") } @@ -88,7 +88,7 @@ var Index = &ctx.Context{Name: "tcp", Help: "网络连接", "address": &ctx.Config{Name: "address", Value: "", Help: "监听地址"}, }, Commands: map[string]*ctx.Command{ - "listen": &ctx.Command{"listen address", "监听端口", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "listen": &ctx.Command{Name: "listen address", Help: "监听端口", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { switch len(arg) { // {{{ case 0: for k, s := range m.Target.Contexts { @@ -100,7 +100,7 @@ var Index = &ctx.Context{Name: "tcp", Help: "网络连接", return "" // }}} }}, - "dial": &ctx.Command{"dial", "建立连接", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "dial": &ctx.Command{Name: "dial", Help: "建立连接", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { tcp := c.Server.(*TCP) // {{{ switch len(arg) { case 0: @@ -116,7 +116,7 @@ var Index = &ctx.Context{Name: "tcp", Help: "网络连接", return "" // }}} }}, - "exit": &ctx.Command{"exit", "退出", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + "exit": &ctx.Command{Name: "exit", Help: "退出", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { tcp, ok := m.Target.Server.(*TCP) // {{{ if !ok { tcp, ok = m.Context.Server.(*TCP) diff --git a/src/context/web/web.go b/src/context/web/web.go index 25de8861..faf38128 100644 --- a/src/context/web/web.go +++ b/src/context/web/web.go @@ -2,46 +2,115 @@ package web // {{{ // }}} import ( // {{{ "context" + "fmt" "log" "net/http" + "path" ) // }}} type WEB struct { + Server *http.Server + Mux *http.ServeMux + hands map[string]bool + + run bool + *ctx.Context } +func (web *WEB) Handle(p string, h http.Handler) { // {{{ + if web.hands == nil { + web.hands = make(map[string]bool) + } + + p = path.Clean(p) + if _, ok := web.hands[p]; ok { + panic(fmt.Sprintln(web.Name, "handle exits", p)) + } + web.hands[p] = true + if p == "/" { + panic(fmt.Sprintln(web.Name, "handle exits", p)) + } + + web.Mux.Handle(p+"/", http.StripPrefix(p, h)) +} + +// }}} +func (web *WEB) HandleFunc(p string, h func(http.ResponseWriter, *http.Request)) { // {{{ + if web.hands == nil { + web.hands = make(map[string]bool) + } + + p = path.Clean(p) + if _, ok := web.hands[p]; ok { + panic(fmt.Sprintln(web.Name, "handle exits", p)) + } + web.hands[p] = true + if p == "/" { + panic(fmt.Sprintln(web.Name, "handle exits", p)) + } + + web.Mux.HandleFunc(p, h) + log.Println(web.Name, "hand:", p) +} + +// }}} +func (web *WEB) ServeHTTP(w http.ResponseWriter, r *http.Request) { // {{{ + log.Println() + log.Println(web.Name, r.RemoteAddr, r.Method, r.URL.Path) + web.Mux.ServeHTTP(w, r) +} + +// }}} + func (web *WEB) Begin(m *ctx.Message) ctx.Server { // {{{ return web } // }}} func (web *WEB) Start(m *ctx.Message) bool { // {{{ - mux := http.NewServeMux() - mux.Handle("/", http.FileServer(http.Dir(web.Conf("directory")))) - for _, v := range m.Meta["detail"][2:] { - if h, ok := m.Data[v].(func(http.ResponseWriter, *http.Request)); ok { - mux.HandleFunc(v, h) + + if !web.run { + if web.Conf("directory") != "" { + web.Mux.Handle("/", http.FileServer(http.Dir(web.Conf("directory")))) + log.Println(web.Name, "directory:", web.Conf("directory")) + } + + for _, v := range web.Contexts { + if s, ok := v.Server.(*WEB); ok && s.Mux != nil { + log.Println(web.Name, "route:", s.Conf("route"), "->", s.Name) + web.Handle(s.Conf("route"), s.Mux) + s.Start(m) + } } } + web.run = true - s := &http.Server{Addr: web.Conf("address"), Handler: mux} - s.ListenAndServe() + if m.Target != web.Context { + return true + } + + web.Server = &http.Server{Addr: web.Conf("address"), Handler: web} + log.Println(web.Name, "protocol:", web.Conf("protocol")) + log.Println(web.Name, "address:", web.Conf("address")) + + if web.Conf("protocol") == "https" { + log.Println(web.Name, "cert:", web.Conf("cert")) + log.Println(web.Name, "key:", web.Conf("key")) + web.Server.ListenAndServeTLS(web.Conf("cert"), web.Conf("key")) + } else { + web.Server.ListenAndServe() + } - log.Println(s.ListenAndServe()) return true } // }}} func (web *WEB) Spawn(c *ctx.Context, m *ctx.Message, arg ...string) ctx.Server { // {{{ - c.Caches = map[string]*ctx.Cache{ - "status": &ctx.Cache{Name: "status", Value: "stop", Help: "服务状态"}, - } - c.Configs = map[string]*ctx.Config{ - "address": &ctx.Config{Name: "listen", Value: arg[0], Help: "监听地址"}, - "directory": &ctx.Config{Name: "directory", Value: arg[1], Help: "服务目录"}, - } + c.Caches = map[string]*ctx.Cache{} + c.Configs = map[string]*ctx.Config{} c.Commands = map[string]*ctx.Command{} s := new(WEB) @@ -56,33 +125,49 @@ func (web *WEB) Exit(m *ctx.Message, arg ...string) bool { // {{{ // }}} -var Index = &ctx.Context{Name: "web", Help: "网页服务", // {{{ - Caches: map[string]*ctx.Cache{}, - Configs: map[string]*ctx.Config{}, +var Index = &ctx.Context{Name: "web", Help: "网页服务", + Caches: map[string]*ctx.Cache{ + "status": &ctx.Cache{Name: "status", Value: "stop", Help: "服务状态"}, + }, + Configs: map[string]*ctx.Config{ + "directory": &ctx.Config{Name: "directory", Value: "./", Help: "服务目录"}, + "protocol": &ctx.Config{Name: "protocol", Value: "http", Help: "服务协议"}, + "address": &ctx.Config{Name: "address", Value: ":9393", Help: "监听地址"}, + "route": &ctx.Config{Name: "route", Value: "/", Help: "请求路径"}, + "default": &ctx.Config{Name: "default", Value: "hello web world", Help: "默认响应体"}, + }, Commands: map[string]*ctx.Command{ - "listen": &ctx.Command{"listen address directory", "设置监听地址和目录", func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { - switch len(arg) { // {{{ - case 0: - default: - m.Add("detail", "/hi") - m.Put("/hi", func(w http.ResponseWriter, r *http.Request) { - w.Write([]byte("hello context world!")) - }) - - m.Start(m.Meta["detail"][1:]...) + "listen": &ctx.Command{Name: "listen [route [address protocol [directory]]]", Help: "开启网页服务", Hand: func(c *ctx.Context, m *ctx.Message, key string, arg ...string) string { + s, ok := m.Target.Server.(*WEB) // {{{ + if !ok { + return "" } + + if len(arg) > 0 { + s.Conf("route", arg[0]) + } + if len(arg) > 2 { + s.Conf("address", arg[1]) + s.Conf("protocol", arg[2]) + } + if len(arg) > 3 { + s.Conf("directory", arg[3]) + } + go s.Start(m) + return "" // }}} }}, }, } -// }}} - -func init() { // {{{ +func init() { web := &WEB{} web.Context = Index ctx.Index.Register(Index, web) -} -// }}} + web.Mux = http.NewServeMux() + web.HandleFunc("/hi", func(w http.ResponseWriter, r *http.Request) { + w.Write([]byte(web.Conf("default"))) + }) +} diff --git a/src/example/bench.go b/src/example/bench.go index 77cd58b7..0a7845ab 100644 --- a/src/example/bench.go +++ b/src/example/bench.go @@ -2,7 +2,10 @@ package main import ( "context" + _ "context/aaa" _ "context/cli" + _ "context/tcp" + _ "context/web" ) func main() {