74 lines
1.8 KiB
Go
74 lines
1.8 KiB
Go
package condflow
|
|
|
|
import (
|
|
"strings"
|
|
|
|
"git.fsdpf.net/go/reflux"
|
|
"git.fsdpf.net/go/reflux/valuex"
|
|
)
|
|
|
|
type result struct {
|
|
key string
|
|
value valuex.Accessor
|
|
}
|
|
|
|
// lookuper 从 flowContext 独立出来的查找器实现
|
|
// 用于为 valuex.Schema 提供数据源
|
|
type lookuper struct {
|
|
// results 记录每一次 PushResult
|
|
results []result
|
|
}
|
|
|
|
// MustLookup 根据路径查找并直接返回对应值的访问器
|
|
// 如果路径不存在,返回 Nil 访问器(所有方法返回零值)
|
|
func (c *lookuper) MustLookup(key string) valuex.Accessor {
|
|
if v, ok := c.Lookup(key); ok {
|
|
return v
|
|
}
|
|
return valuex.Nil
|
|
}
|
|
|
|
// Lookup 根据路径查找并返回对应值的访问器
|
|
// 支持点号分隔的路径查找,格式: "key.field"
|
|
// - 如果 key 不包含点号,从 Input 中查找
|
|
// - 如果 key 包含点号,从 results 中从后往前查找匹配的 key
|
|
func (c *lookuper) Lookup(key string) (valuex.Accessor, bool) {
|
|
index := strings.SplitN(key, ".", 2)
|
|
|
|
if len(index) == 2 {
|
|
// 先从结果记录中从后往前查找
|
|
for i := len(c.results) - 1; i >= 0; i-- {
|
|
if c.results[i].key == index[0] {
|
|
return c.results[i].value.Lookup(index[1])
|
|
}
|
|
}
|
|
}
|
|
|
|
return c.Input().Lookup(key)
|
|
}
|
|
|
|
// LastResult 获取上一个 PushResult 的值
|
|
func (c *lookuper) LastResult() valuex.Accessor {
|
|
if len(c.results) == 0 {
|
|
return valuex.Nil
|
|
}
|
|
return c.results[len(c.results)-1].value
|
|
}
|
|
|
|
// PushResult 设置上一个 Flow Handler 执行结果
|
|
func (c *lookuper) PushResult(key string, value reflux.R) {
|
|
c.results = append(c.results, result{
|
|
key: key,
|
|
value: value,
|
|
})
|
|
}
|
|
|
|
// Input 获取初始输入数据
|
|
func (c *lookuper) Input() valuex.Accessor {
|
|
// input 总是存储在第一个位置
|
|
if len(c.results) > 0 && c.results[0].key == inputKey {
|
|
return c.results[0].value
|
|
}
|
|
return nil
|
|
}
|