1
0
forked from x/icebergs

add favor search

This commit is contained in:
shaoying 2020-04-06 15:14:00 +08:00
parent 71ec21039d
commit 35730461cb
7 changed files with 149 additions and 78 deletions

View File

@ -29,7 +29,7 @@ func (f *Frame) Start(m *ice.Message, arg ...string) bool {
if !ok { if !ok {
return true return true
} }
m.Log(ice.LOG_SIGNAL, "%v: %v", s, m.Confv(ice.GDB_SIGNAL, kit.Keys(kit.MDB_HASH, s))) // m.Log(ice.LOG_SIGNAL, "%v: %v", s, m.Confv(ice.GDB_SIGNAL, kit.Keys(kit.MDB_HASH, s)))
m.Cmd(m.Confv(ice.GDB_SIGNAL, kit.Keys(kit.MDB_HASH, s)), kit.Keys(s)) m.Cmd(m.Confv(ice.GDB_SIGNAL, kit.Keys(kit.MDB_HASH, s)), kit.Keys(s))
case t, ok := <-f.t: case t, ok := <-f.t:
@ -76,7 +76,7 @@ var Index = &ice.Context{Name: "gdb", Help: "事件模块",
"2", []interface{}{"exit", "0"}, "2", []interface{}{"exit", "0"},
"3", []interface{}{"exit", "1"}, "3", []interface{}{"exit", "1"},
"15", []interface{}{"exit", "1"}, "15", []interface{}{"exit", "1"},
"20", []interface{}{"cli.daemon", "exit"}, "20", []interface{}{},
"30", []interface{}{"exit"}, "30", []interface{}{"exit"},
"31", []interface{}{"exit", "1"}, "31", []interface{}{"exit", "1"},
"28", "WINCH", "28", "WINCH",

View File

@ -20,6 +20,7 @@ import (
"os" "os"
"path" "path"
"strings" "strings"
"sync"
"text/template" "text/template"
"time" "time"
) )
@ -155,7 +156,7 @@ func (web *Frame) HandleWSS(m *ice.Message, safe bool, c *websocket.Conn, name s
socket, msg := c, m.Spawn(b) socket, msg := c, m.Spawn(b)
source := kit.Simple(msg.Optionv(ice.MSG_SOURCE), name) source := kit.Simple(msg.Optionv(ice.MSG_SOURCE), name)
target := kit.Simple(msg.Optionv(ice.MSG_TARGET)) target := kit.Simple(msg.Optionv(ice.MSG_TARGET))
msg.Info("recv %v %v->%v %v", t, source, target, msg.Format("meta")) msg.Info("recv %v<-%v %v", target, source, msg.Format("meta"))
if len(target) == 0 { if len(target) == 0 {
// 本地执行 // 本地执行
@ -182,7 +183,6 @@ func (web *Frame) HandleWSS(m *ice.Message, safe bool, c *websocket.Conn, name s
} else if call, ok := web.send[msg.Option(ice.MSG_TARGET)]; len(target) == 1 && ok { } else if call, ok := web.send[msg.Option(ice.MSG_TARGET)]; len(target) == 1 && ok {
// 接收响应 // 接收响应
delete(web.send, msg.Option(ice.MSG_TARGET)) delete(web.send, msg.Option(ice.MSG_TARGET))
msg.Info("space done")
call.Back(msg) call.Back(msg)
break break
@ -248,12 +248,13 @@ func (web *Frame) HandleCGI(m *ice.Message, alias map[string]interface{}, which
func (web *Frame) HandleCmd(m *ice.Message, key string, cmd *ice.Command) { func (web *Frame) HandleCmd(m *ice.Message, key string, cmd *ice.Command) {
web.HandleFunc(key, func(w http.ResponseWriter, r *http.Request) { web.HandleFunc(key, func(w http.ResponseWriter, r *http.Request) {
m.TryCatch(m.Spawns(), true, func(msg *ice.Message) { m.TryCatch(m.Spawns(), true, func(msg *ice.Message) {
defer func() { msg.Cost("%s %v", r.URL.Path, msg.Optionv("cmds")) }() defer func() { msg.Cost("%s %v %v", r.URL.Path, msg.Optionv("cmds"), msg.Format("append")) }()
// 请求地址 // 请求地址
msg.Option(ice.MSG_USERUA, r.Header.Get("User-Agent")) msg.Option(ice.MSG_USERUA, r.Header.Get("User-Agent"))
msg.Option(ice.MSG_USERIP, r.Header.Get(ice.MSG_USERIP)) msg.Option(ice.MSG_USERIP, r.Header.Get(ice.MSG_USERIP))
msg.Option(ice.MSG_USERURL, r.URL.Path) msg.Option(ice.MSG_USERURL, r.URL.Path)
msg.Option(ice.MSG_USERPOD, "")
msg.Option(ice.MSG_SESSID, "") msg.Option(ice.MSG_SESSID, "")
msg.Option(ice.MSG_OUTPUT, "") msg.Option(ice.MSG_OUTPUT, "")
msg.R, msg.W = r, w msg.R, msg.W = r, w
@ -881,20 +882,17 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
m.Set(ice.MSG_DETAIL, arg[1:]...) m.Set(ice.MSG_DETAIL, arg[1:]...)
m.Optionv(ice.MSG_TARGET, target[1:]) m.Optionv(ice.MSG_TARGET, target[1:])
m.Optionv(ice.MSG_SOURCE, []string{id}) m.Optionv(ice.MSG_SOURCE, []string{id})
m.Info("send %s %s", id, m.Format("meta")) m.Info("send %s->%v %s", id, target, m.Format("meta"))
// 下发命令 // 下发命令
m.Target().Server().(*Frame).send[id] = m m.Target().Server().(*Frame).send[id] = m
socket.WriteMessage(MSG_MAPS, []byte(m.Format("meta"))) socket.WriteMessage(MSG_MAPS, []byte(m.Format("meta")))
t := time.AfterFunc(kit.Duration(m.Conf(ice.WEB_SPACE, "meta.timeout.c")), func() {
m.Log(ice.LOG_WARN, "timeout")
})
m.Call(true, func(msg *ice.Message) *ice.Message { m.Call(m.Option("_async") == "", func(res *ice.Message) *ice.Message {
m.Log("cost", "%s: %s %v", m.Format("cost"), arg[0], arg[1:]) if res != nil && m != nil {
if t.Stop(); msg != nil && m != nil {
// 返回结果 // 返回结果
m.Copy(msg) m.Log("cost", "%s: %s %v %v", m.Format("cost"), arg[0], arg[1:], res.Format("append"))
return m.Copy(res)
} }
return nil return nil
}) })
@ -1124,6 +1122,28 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
return return
}) })
return return
case "search":
m.Option("cache.limit", -2)
wg := &sync.WaitGroup{}
m.Richs(ice.WEB_FAVOR, nil, "*", func(key string, val map[string]interface{}) {
favor := kit.Format(kit.Value(val, "meta.name"))
wg.Add(1)
m.Info("routine %v", favor)
m.Gos(m, func(m *ice.Message) {
m.Grows(ice.WEB_FAVOR, kit.Keys(kit.MDB_HASH, key), "", "", func(index int, value map[string]interface{}) {
if strings.Contains(kit.Format(value["name"]), arg[1]) || strings.Contains(kit.Format(value["text"]), arg[1]) {
m.Push("pod", strings.Join(kit.Simple(m.Optionv("user.pod")), "."))
m.Push("favor", favor)
m.Push("", value, []string{"id", "type", "name", "text"})
}
})
wg.Done()
})
})
wg.Wait()
return
} }
m.Option("favor", arg[0]) m.Option("favor", arg[0])
@ -1756,18 +1776,8 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
} }
m.Richs(ice.WEB_SPACE, nil, kit.Select("*", arg, 0), func(key string, value map[string]interface{}) { m.Richs(ice.WEB_SPACE, nil, kit.Select("*", arg, 0), func(key string, value map[string]interface{}) {
switch value[kit.MDB_TYPE] {
case ice.WEB_MASTER:
return
case ice.WEB_BETTER:
return
}
if value[kit.MDB_NAME] == m.Conf(ice.CLI_RUNTIME, "node.name") {
// 避免循环
return
}
if len(arg) > 1 { if len(arg) > 1 {
m.Call(false, func(res *ice.Message) *ice.Message { return res })
// 发送命令 // 发送命令
m.Cmdy(ice.WEB_SPACE, value[kit.MDB_NAME], arg[1:]) m.Cmdy(ice.WEB_SPACE, value[kit.MDB_NAME], arg[1:])
return return
@ -1775,6 +1785,11 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
switch value[kit.MDB_TYPE] { switch value[kit.MDB_TYPE] {
case ice.WEB_SERVER: case ice.WEB_SERVER:
if value[kit.MDB_NAME] == m.Conf(ice.CLI_RUNTIME, "node.name") {
// 避免循环
return
}
// 远程查询 // 远程查询
m.Cmd(ice.WEB_SPACE, value[kit.MDB_NAME], ice.WEB_ROUTE).Table(func(index int, val map[string]string, head []string) { m.Cmd(ice.WEB_SPACE, value[kit.MDB_NAME], ice.WEB_ROUTE).Table(func(index int, val map[string]string, head []string) {
m.Push(kit.MDB_TYPE, val[kit.MDB_TYPE]) m.Push(kit.MDB_TYPE, val[kit.MDB_TYPE])
@ -1890,11 +1905,11 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
}}, }},
ice.WEB_LABEL: {Name: "label", Help: "标签", Meta: kit.Dict( ice.WEB_LABEL: {Name: "label", Help: "标签", Meta: kit.Dict(
"exports", []string{"lab", "label"}, "exports", []string{"lab", "label"},
"detail", []string{"退还"}, "detail", []string{"还"},
), List: ice.ListLook("label", "name"), Hand: func(m *ice.Message, c *ice.Context, cmd string, arg ...string) { ), List: ice.ListLook("label", "name"), Hand: func(m *ice.Message, c *ice.Context, cmd string, arg ...string) {
if len(arg) > 1 && arg[0] == "action" { if len(arg) > 1 && arg[0] == "action" {
switch arg[1] { switch arg[1] {
case "del", "退还": case "del", "还":
if m.Option("label") != "" && m.Option("name") != "" { if m.Option("label") != "" && m.Option("name") != "" {
m.Cmdy(ice.WEB_LABEL, m.Option("label"), "del", m.Option("name")) m.Cmdy(ice.WEB_LABEL, m.Option("label"), "del", m.Option("name"))
} }
@ -1902,15 +1917,21 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
return return
} }
if len(arg) < 2 { if len(arg) < 3 {
// 分组列表
m.Richs(cmd, nil, kit.Select("*", arg, 0), func(key string, value map[string]interface{}) { m.Richs(cmd, nil, kit.Select("*", arg, 0), func(key string, value map[string]interface{}) {
if len(arg) < 1 { if len(arg) == 0 {
// 分组列表
m.Push(key, value[kit.MDB_META]) m.Push(key, value[kit.MDB_META])
return return
} }
m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), "*", func(key string, value map[string]interface{}) { m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), kit.Select("*", arg, 1), func(key string, value map[string]interface{}) {
if len(arg) == 1 {
// 设备列表
m.Push(key, value) m.Push(key, value)
return
}
// 设备详情
m.Push("detail", value)
}) })
}) })
m.Logs(ice.LOG_SELECT, cmd, m.Format(ice.MSG_APPEND)) m.Logs(ice.LOG_SELECT, cmd, m.Format(ice.MSG_APPEND))
@ -1919,44 +1940,50 @@ var Index = &ice.Context{Name: "web", Help: "网络模块",
if m.Richs(cmd, nil, arg[0], nil) == nil { if m.Richs(cmd, nil, arg[0], nil) == nil {
// 添加分组 // 添加分组
n := m.Rich(cmd, nil, kit.Data(kit.MDB_SHORT, kit.MDB_NAME, cmd, arg[0])) m.Logs(ice.LOG_CREATE, cmd, m.Rich(cmd, nil, kit.Data(kit.MDB_SHORT, kit.MDB_NAME, cmd, arg[0])))
m.Logs(ice.LOG_CREATE, cmd, n)
} }
m.Richs(cmd, nil, arg[0], func(key string, value map[string]interface{}) { m.Richs(cmd, nil, arg[0], func(key string, value map[string]interface{}) {
if m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), arg[1], func(key string, value map[string]interface{}) {
// 分组详情
m.Push("detail", value)
}) != nil {
return
}
switch arg[1] { switch arg[1] {
case "add": case "add":
if pod := m.Cmdx(ice.WEB_GROUP, arg[2], "get", arg[3:]); pod != "" { if pod := m.Cmdx(ice.WEB_GROUP, arg[2], "get", arg[3:]); pod != "" {
if m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), pod, func(key string, value map[string]interface{}) { if m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), pod, func(key string, value map[string]interface{}) {
if value[kit.MDB_STATUS] == "void" { if value[kit.MDB_STATUS] == "void" {
// 更新设备
value[kit.MDB_STATUS] = "free" value[kit.MDB_STATUS] = "free"
}
m.Logs(ice.LOG_MODIFY, cmd, key, kit.MDB_NAME, pod, kit.MDB_STATUS, value[kit.MDB_STATUS]) m.Logs(ice.LOG_MODIFY, cmd, key, kit.MDB_NAME, pod, kit.MDB_STATUS, value[kit.MDB_STATUS])
}
}) == nil { }) == nil {
// 获取设备
m.Logs(ice.LOG_INSERT, cmd, key, kit.MDB_NAME, pod) m.Logs(ice.LOG_INSERT, cmd, key, kit.MDB_NAME, pod)
m.Rich(cmd, kit.Keys(kit.MDB_HASH, key), kit.Dict(kit.MDB_NAME, pod, "group", arg[2], kit.MDB_STATUS, "free")) m.Rich(cmd, kit.Keys(kit.MDB_HASH, key), kit.Dict(kit.MDB_NAME, pod, "group", arg[2], kit.MDB_STATUS, "free"))
} }
} }
m.Echo(arg[0]) m.Echo(arg[0])
case "del": case "del":
m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), arg[2], func(sub string, value map[string]interface{}) { m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), arg[2], func(sub string, value map[string]interface{}) {
// 归还设备
m.Cmdx(ice.WEB_GROUP, value["group"], "put", arg[2]) m.Cmdx(ice.WEB_GROUP, value["group"], "put", arg[2])
m.Logs(ice.LOG_MODIFY, cmd, key, kit.MDB_NAME, arg[2], kit.MDB_STATUS, "void") m.Logs(ice.LOG_MODIFY, cmd, key, kit.MDB_NAME, arg[2], kit.MDB_STATUS, "void")
value[kit.MDB_STATUS] = "void" value[kit.MDB_STATUS] = "void"
m.Echo(arg[2]) m.Echo(arg[2])
}) })
default: default:
m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), "*", func(key string, value map[string]interface{}) { wg := &sync.WaitGroup{}
m.Option("_async", "true")
m.Richs(cmd, kit.Keys(kit.MDB_HASH, key), arg[1], func(key string, value map[string]interface{}) {
wg.Add(1)
// 远程命令 // 远程命令
m.Cmdy(ice.WEB_PROXY, value["name"], arg[1:]) m.Option("user.pod", value["name"])
m.Cmd(ice.WEB_PROXY, value["name"], arg[2:]).Call(false, func(res *ice.Message) *ice.Message {
if wg.Done(); res != nil && m != nil {
m.Copy(res)
}
return nil
}) })
})
wg.Wait()
} }
}) })
}}, }},

View File

@ -33,6 +33,7 @@ const ( // MSG
MSG_USERIP = "user.ip" MSG_USERIP = "user.ip"
MSG_USERUA = "user.ua" MSG_USERUA = "user.ua"
MSG_USERURL = "user.url" MSG_USERURL = "user.url"
MSG_USERPOD = "user.pod"
MSG_USERNICK = "user.nick" MSG_USERNICK = "user.nick"
MSG_USERNAME = "user.name" MSG_USERNAME = "user.name"
MSG_USERROLE = "user.role" MSG_USERROLE = "user.role"

View File

@ -221,7 +221,7 @@ var Index = &ice.Context{Name: "code", Help: "编程中心",
m.Cmd(ice.WEB_FAVOR, "pprof", "shell", "text", m.Cmdx(ice.CLI_SYSTEM, "go", "tool", "pprof", "-text", msg.Append("text"))) m.Cmd(ice.WEB_FAVOR, "pprof", "shell", "text", m.Cmdx(ice.CLI_SYSTEM, "go", "tool", "pprof", "-text", msg.Append("text")))
m.Cmd(ice.WEB_FAVOR, "pprof", "pprof", name, msg.Append("data")) m.Cmd(ice.WEB_FAVOR, "pprof", "pprof", name, msg.Append("data"))
arg = kit.Simple("web", value["bin"], value[kit.MDB_TEXT], name) arg = kit.Simple("web", value[kit.MDB_TEXT], msg.Append("text"))
}) })
fallthrough fallthrough

View File

@ -8,6 +8,7 @@ import (
"os" "os"
"path" "path"
"strings" "strings"
"sync"
"time" "time"
) )
@ -90,12 +91,15 @@ var Index = &ice.Context{Name: "git", Help: "代码库",
// 提交统计 // 提交统计
days := 0 days := 0
commit, adds, dels, rest := 0, 0, 0, 0 commit, adds, dels, rest := 0, 0, 0, 0
wg := &sync.WaitGroup{}
m.Richs("repos", nil, "*", func(key string, value map[string]interface{}) { m.Richs("repos", nil, "*", func(key string, value map[string]interface{}) {
if m.Conf("total", kit.Keys("meta.skip", kit.Value(value, "meta.name"))) == "true" { if m.Conf("total", kit.Keys("meta.skip", kit.Value(value, "meta.name"))) == "true" {
return return
} }
wg.Add(1)
m.Push("name", kit.Value(value, "meta.name")) m.Push("name", kit.Value(value, "meta.name"))
m.Copy(m.Cmd("_sum", kit.Value(value, "meta.path"), "total", "10000").Table(func(index int, value map[string]string, head []string) { m.Gos(m, func(m *ice.Message) {
msg := m.Cmd("_sum", kit.Value(value, "meta.path"), "total", "10000").Table(func(index int, value map[string]string, head []string) {
if kit.Int(value["days"]) > days { if kit.Int(value["days"]) > days {
days = kit.Int(value["days"]) days = kit.Int(value["days"])
} }
@ -103,8 +107,12 @@ var Index = &ice.Context{Name: "git", Help: "代码库",
adds += kit.Int(value["adds"]) adds += kit.Int(value["adds"])
dels += kit.Int(value["dels"]) dels += kit.Int(value["dels"])
rest += kit.Int(value["rest"]) rest += kit.Int(value["rest"])
}))
}) })
m.Copy(msg)
wg.Done()
})
})
wg.Wait()
m.Push("name", "total") m.Push("name", "total")
m.Push("days", days) m.Push("days", days)
m.Push("commit", commit) m.Push("commit", commit)

View File

@ -7,10 +7,26 @@ init_shy="etc/init.shy"
local_shy="etc/local.shy" local_shy="etc/local.shy"
exit_shy="etc/exit.shy" exit_shy="etc/exit.shy"
main_go="src/main.go" main_go="src/main.go"
main_js="src/main.js"
readme="README.md" readme="README.md"
shy="hi.shy" shy="src/main.shy"
prepare() { prepare() {
[ -d src ] || mkdir src
[ -f ${main_go} ] || cat >> ${main_go} <<END
package main
import (
"github.com/shylinux/icebergs"
_ "github.com/shylinux/icebergs/base"
_ "github.com/shylinux/icebergs/core"
_ "github.com/shylinux/icebergs/misc"
)
func main() { println(ice.Run()) }
END
[ -f ${shy} ] || cat >> ${shy} <<END [ -f ${shy} ] || cat >> ${shy} <<END
title "${ice_mod}" title "${ice_mod}"
@ -25,44 +41,45 @@ field "系统架构" favor args "系统架构"
field "编译原理" favor args "编译原理" field "编译原理" favor args "编译原理"
END END
[ -d src ] || mkdir src [ -f ${main_js} ] || cat >> ${main_js} <<END
[ -f ${main_go} ] || cat >> ${main_go} <<END Volcanos("onimport", {help: "导入数据", list: [],
package main "init": function(can, msg, cb, output, action, option) {},
})
import ( Volcanos("onaction", {help: "控件菜单", list: []})
"github.com/shylinux/icebergs" Volcanos("onchoice", {help: "控件交互", list: ["刷新"]
_ "github.com/shylinux/icebergs/base" "刷新": function(event, can, value, cmd, target) {},
_ "github.com/shylinux/icebergs/core" })
_ "github.com/shylinux/icebergs/misc" Volcanos("ondetail", {help: "控件详情", list: []})
) Volcanos("onexport", {help: "导出数据", list: []})
func main() {
println(ice.Run())
}
END END
[ -f go.mod ] || go mod init ${ice_mod} [ -f go.mod ] || go mod init ${ice_mod}
[ -f Makefile ] || cat >> Makefile <<END [ -f Makefile ] || cat >> Makefile <<END
export GOPROXY=https://goproxy.cn
export GOPRIVATE=github.com
export CGO_ENABLED=0
all: all:
@echo && date @echo && date
GOPRIVATE=github.com GOPROXY=https://goproxy.cn CGO_ENABLED=0 go build -o ${ice_bin} ${main_go} && chmod u+x ${ice_bin} && ./${ice_sh} restart go build -o ${ice_bin} ${main_go} && chmod u+x ${ice_bin} && ./${ice_sh} restart
END END
[ -d etc ] || mkdir etc [ -d etc ] || mkdir etc
[ -f ${init_shy} ] || cat >> ${init_shy} <<END [ -f ${init_shy} ] || cat >> ${init_shy} <<END
~web ~web
# web.code.tmux.init
# web.code.git.init
~ssh ~ssh
source etc/local.shy source etc/local.shy
END END
[ -f ${local_shy} ] || cat >> ${local_shy} <<END [ -f ${local_shy} ] || cat >> ${local_shy} <<END
~aaa
~web ~web
END END
[ -f ${exit_shy} ] || cat >> "${exit_shy}" <<END [ -f ${exit_shy} ] || cat >> "${exit_shy}" <<END
~web
END END
[ -d bin ] || mkdir bin [ -d bin ] || mkdir bin

26
type.go
View File

@ -929,19 +929,37 @@ func (m *Message) Done() bool {
return true return true
} }
func (m *Message) Call(sync bool, cb func(*Message) *Message) *Message { func (m *Message) Call(sync bool, cb func(*Message) *Message) *Message {
if sync { wait := make(chan bool, 2)
wait := make(chan bool) t := time.AfterFunc(kit.Duration("10s"), func() {
m.Log(LOG_WARN, "timeout")
m.Back(nil)
wait <- false
})
m.cb = func(sub *Message) *Message { m.cb = func(sub *Message) *Message {
if sync {
t.Stop()
wait <- true wait <- true
}
return cb(sub) return cb(sub)
} }
if sync {
<-wait <-wait
} else {
t.Stop()
} }
return m return m
} }
func (m *Message) Back(sub *Message) *Message { func (m *Message) Back(res *Message) *Message {
if m.cb != nil { if m.cb != nil {
m.cb(sub) // if res != nil {
// m.Info("back %v", res.Format("prefix"))
// } else {
// m.Info("back %v", nil)
// }
if sub := m.cb(res); m.message != nil {
m.message.Back(sub)
}
} }
return m return m
} }