TODO: 解决改版后递归逻辑错误

This commit is contained in:
huangsimin 2020-04-08 17:40:02 +08:00
parent d7c4848d63
commit 9a7bfe6c4d
5 changed files with 138 additions and 44 deletions

View File

@ -4,11 +4,15 @@ import "github.com/474420502/requests"
// TaskContext 上下文
type TaskContext struct {
share map[string]interface{}
hunter *Hunter
curNode ITaskNode
session *requests.Session
curPath string
curTaskID string
workflow *requests.Workflow
parent ITaskNode
current ITaskNode
}
// NewContext 任务上下文
@ -18,24 +22,23 @@ func NewContext() *TaskContext {
// AddTask 添加到当前子任务队列
func (cxt *TaskContext) AddTask(itask ITask) {
if children := cxt.curNode.Children(); children == nil {
cxt.curNode.SetChildren(cxt.hunter.createQueue())
if children := cxt.current.Children(); children == nil {
cxt.current.SetChildren(cxt.hunter.createQueue())
}
bt := &BaseTask{task: itask}
cxt.curNode.Children().Push(bt)
cxt.current.Children().Push(bt)
}
// AddParentTask 添加到当前任务队列
func (cxt *TaskContext) AddParentTask(itask ITask) {
bt := &BaseTask{task: itask}
cxt.curNode.Parent().Children().Push(bt)
cxt.current.Parent().Children().Push(bt)
}
// GetShare 获取share的数据, 存储用的
func (cxt *TaskContext) GetShare(key string) interface{} {
if v, ok := cxt.share[key]; ok {
if v, ok := cxt.hunter.share[key]; ok {
return v
}
return nil
@ -43,20 +46,15 @@ func (cxt *TaskContext) GetShare(key string) interface{} {
// SetShare 设置share的数据, 存储用的
func (cxt *TaskContext) SetShare(key string, value interface{}) {
cxt.share[key] = value
cxt.hunter.share[key] = value
}
// Session Get return session *requests.Session
func (cxt *TaskContext) Session() *requests.Session {
if cxt.session == nil {
cxt.session = requests.NewSession()
if cxt.hunter.Session() == nil {
cxt.hunter.SetSession(requests.NewSession())
}
return cxt.session
}
// SetSession Set session *requests.Session
func (cxt *TaskContext) SetSession(session *requests.Session) {
cxt.session = session
return cxt.hunter.Session()
}
// Workflow Get return Workflow *requests.Workflow. not exists, return nil
@ -69,6 +67,16 @@ func (cxt *TaskContext) SetWorkflow(workflow *requests.Workflow) {
cxt.workflow = workflow
}
// TaskID Get Task ID
func (cxt *TaskContext) TaskID() string {
return cxt.curTaskID
}
// Path curren Task tree path.
func (cxt *TaskContext) Path() string {
return cxt.curPath
}
// Hunt Hunt() = cxt.Workflow().Execute()
func (cxt *TaskContext) Hunt() (*requests.Response, error) {
return cxt.workflow.Execute()

106
hunter.go
View File

@ -1,23 +1,29 @@
package hunter
import (
"strconv"
pqueue "github.com/474420502/focus/priority_queue"
"github.com/474420502/requests"
)
// IGobalBefore 全局任务执行之前
type IGobalBefore interface {
GobalBefore()
GobalBefore(cxt *TaskContext)
}
// IGobalAfter 全局任务执行之后
type IGobalAfter interface {
GobalAfter()
GobalAfter(cxt *TaskContext)
}
// Hunter 任务相关 必须有序
type Hunter struct {
cxt *TaskContext
task ITaskNode
share map[string]interface{}
session *requests.Session
tasks []ITask
createQueue func() *pqueue.PriorityQueue
}
@ -30,13 +36,15 @@ func NewHunter() *Hunter {
func NewPriorityHunter(queueCreator func() *pqueue.PriorityQueue) *Hunter {
hunter := &Hunter{}
hunter.createQueue = queueCreator
hunter.task = &BaseTask{}
hunter.task.SetParent(nil)
hunter.task.SetChildren(hunter.createQueue())
hunter.cxt = NewContext()
hunter.cxt.curNode = hunter.task
hunter.cxt.share = make(map[string]interface{})
// hunter.task = &BaseTask{}
// hunter.task.SetParent(nil)
// hunter.task.SetChildren(hunter.createQueue())
// hunter.cxt = NewContext()
// hunter.cxt.curNode = hunter.task
hunter.share = make(map[string]interface{})
return hunter
}
@ -50,28 +58,86 @@ func NewPriorityMinHunter() *Hunter {
return NewPriorityHunter(CreatePriorityMinQueue)
}
// Session Get session *requests.Session
func (hunter *Hunter) Session() *requests.Session {
return hunter.session
}
// SetSession Set session *requests.Session
func (hunter *Hunter) SetSession(session *requests.Session) {
hunter.session = session
}
// GetShare 获取share的数据, 存储用的
func (hunter *Hunter) GetShare(key string) interface{} {
if v, ok := hunter.share[key]; ok {
return v
}
return nil
}
// SetShare 设置share的数据, 存储用的
func (hunter *Hunter) SetShare(key string, value interface{}) {
hunter.share[key] = value
}
// Execute 执行任务
func (hunter *Hunter) Execute() {
hunter.recursionTasks(hunter.task)
for _, task := range hunter.tasks {
hunter.execute(task)
}
}
func (hunter *Hunter) recursionTasks(itask ITaskNode) {
// Execute 执行任务
func (hunter *Hunter) execute(task ITask) {
cxt := NewContext()
for children := itask.Children(); children != nil && children.Size() > 0; {
btask := &BaseTask{}
// btask.SetTask(task)
btask.SetParent(nil)
btask.SetChildren(hunter.createQueue())
cxt.parent = btask
cxt.hunter = hunter
cxt.AddTask(task)
hunter.recursionTasks(cxt)
}
func (hunter *Hunter) recursionTasks(cxt *TaskContext) {
autoid := 0
for children := cxt.parent.Children(); children != nil && children.Size() > 0; {
if itask, ok := children.Pop(); ok {
tasknode := itask.(ITaskNode)
ncxt := NewContext()
tasknode := itask.(ITaskNode)
task := tasknode.Task()
if before, ok := task.(IBefore); ok {
before.Before(hunter.cxt)
ncxt.curPath = cxt.parent.Path()
if itid, ok := task.(IIdentity); ok {
ncxt.curTaskID = itid.GetID()
} else {
ncxt.curTaskID = strconv.Itoa(autoid)
autoid++
}
tasknode.Task().Execute(hunter.cxt)
if before, ok := task.(IBefore); ok {
before.Before(cxt)
}
tasknode.Task().Execute(cxt)
if after, ok := task.(IAfter); ok {
after.After(hunter.cxt)
after.After(cxt)
}
hunter.recursionTasks(tasknode)
tasknode.SetPath(cxt.parent.Path() + "." + ncxt.curTaskID)
ncxt.parent = cxt.current
ncxt.current = tasknode
hunter.recursionTasks(ncxt)
}
}
@ -84,7 +150,7 @@ func (hunter *Hunter) Stop() {
// AddTask 执行任务
func (hunter *Hunter) AddTask(task ITask) {
hunter.cxt.AddTask(task)
hunter.tasks = append(hunter.tasks, task)
}
// Execute 执行

View File

@ -23,7 +23,7 @@ func TestCasePreUrl(t *testing.T) {
hunter.Execute()
data := make(map[string]interface{})
content := hunter.cxt.GetShare("test").(string)
content := hunter.GetShare("test").(string)
err := json.Unmarshal([]byte(content), &data)
if err != nil {
t.Error(err)
@ -55,7 +55,7 @@ func TestCasePostForm(t *testing.T) {
hunter.Execute()
data := make(map[string]interface{})
content := hunter.cxt.GetShare("test").(string)
content := hunter.GetShare("test").(string)
err := json.Unmarshal([]byte(content), &data)
if err != nil {
t.Error(err)
@ -88,7 +88,7 @@ func TestCaseWebSub(t *testing.T) {
hunter.Execute()
data := make(map[string]interface{})
content := hunter.cxt.GetShare("test").(string)
content := hunter.GetShare("test").(string)
err := json.Unmarshal([]byte(content), &data)
if err != nil {
t.Error(err)

1
id_com.go Normal file
View File

@ -0,0 +1 @@
package hunter

19
task.go
View File

@ -24,6 +24,11 @@ type ITask interface {
Execute(ctx *TaskContext)
}
// IIdentity 身份id接口
type IIdentity interface {
GetID() string
}
// ITaskNode 任务节点
type ITaskNode interface {
Parent() ITaskNode
@ -34,12 +39,16 @@ type ITaskNode interface {
Task() ITask // ITaskNode
SetTask(itask ITask)
SetPath(path string)
Path() string
}
// BaseTask 任务,必须包含子任务. 执行了第一个
type BaseTask struct {
parent ITaskNode
children *pqueue.PriorityQueue // ITask类型
path string // id 联合体, 禁用.命名
task ITask
}
@ -73,6 +82,16 @@ func (task *BaseTask) SetTask(itask ITask) {
task.task = itask
}
// Path 路径 例如: web.subweb.subsubweb
func (task *BaseTask) Path() string {
return task.path
}
// SetPath 路径 例如: web.subweb.subsubweb
func (task *BaseTask) SetPath(path string) {
task.path = path
}
// // Task 孩子节点
// func (task *BaseTask) Task() ITask {
// return *task