1
0
mirror of https://shylinux.com/x/ContextOS synced 2025-04-25 16:58:06 +08:00
2017-11-08 17:31:11 +08:00

168 lines
3.7 KiB
Go

package web // {{{
// }}}
import ( // {{{
"context"
"log"
"net/http"
"path"
)
// }}}
type Request struct {
R *http.Request
W http.ResponseWriter
X interface{}
*WEB
}
type WEB struct {
Run bool
*Request
*http.ServeMux
*http.Server
*ctx.Context
}
func (web *WEB) ServeHTTP(w http.ResponseWriter, r *http.Request) { // {{{
log.Println()
log.Println(web.Name, r.RemoteAddr, r.Method, r.URL)
defer log.Println()
if web.Conf("logheaders") == "yes" {
for k, v := range r.Header {
log.Println(k+":", v[0])
}
log.Println()
}
r.ParseForm()
if len(r.PostForm) > 0 {
for k, v := range r.PostForm {
log.Printf("%s: %s", k, v[0])
}
log.Println()
}
web.ServeMux.ServeHTTP(w, r)
if web.Conf("logheaders") == "yes" {
for k, v := range w.Header() {
log.Println(k+":", v[0])
}
}
}
// }}}
func (web *WEB) Begin(m *ctx.Message) ctx.Server { // {{{
return web
}
// }}}
func (web *WEB) Start(m *ctx.Message) bool { // {{{
if !web.Run {
if web.Conf("directory") != "" {
web.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.(http.Handler); ok {
log.Println(web.Name, "route:", v.Conf("route"), "->", v.Name)
web.Handle(v.Conf("route"), http.StripPrefix(path.Dir(v.Conf("route")), s))
v.Start(m)
}
}
}
web.Run = true
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()
}
return true
}
// }}}
func (web *WEB) 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(WEB)
s.Context = c
return s
}
// }}}
func (web *WEB) Exit(m *ctx.Message, arg ...string) bool { // {{{
return true
}
// }}}
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{
"logheaders": &ctx.Config{Name: "logheaders", Value: "yes", Help: "日志输出请求头"},
"directory": &ctx.Config{Name: "directory", Value: "./", Help: "服务目录"},
"protocol": &ctx.Config{Name: "protocol", Value: "https", Help: "服务协议"},
"address": &ctx.Config{Name: "address", Value: ":443", 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{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() {
web := &WEB{}
web.Context = Index
ctx.Index.Register(Index, web)
web.ServeMux = http.NewServeMux()
web.HandleFunc("/hi", func(w http.ResponseWriter, r *http.Request) {
w.Write([]byte(web.Conf("default")))
})
}