You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
141 lines
3.5 KiB
Go
141 lines
3.5 KiB
Go
/*
|
|
* Copyright 2025 CloudWeGo Authors
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
package agents
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"fmt"
|
|
"log"
|
|
"runtime/debug"
|
|
|
|
"github.com/cloudwego/eino-ext/components/tool/commandline"
|
|
"github.com/cloudwego/eino/adk"
|
|
"github.com/cloudwego/eino/adk/prebuilt/planexecute"
|
|
|
|
"github.com/cloudwego/eino-examples/adk/multiagent/integration-excel-agent/generic"
|
|
"github.com/cloudwego/eino-examples/adk/multiagent/integration-excel-agent/params"
|
|
"github.com/cloudwego/eino-examples/adk/multiagent/integration-excel-agent/utils"
|
|
)
|
|
|
|
func NewWrite2PlanMDWrapper(a adk.Agent, op commandline.Operator) adk.Agent {
|
|
return &write2PlanMDWrapper{a: a, op: op}
|
|
}
|
|
|
|
type write2PlanMDWrapper struct {
|
|
a adk.Agent
|
|
op commandline.Operator
|
|
}
|
|
|
|
func (r *write2PlanMDWrapper) Name(ctx context.Context) string {
|
|
return r.a.Name(ctx)
|
|
}
|
|
|
|
func (r *write2PlanMDWrapper) Description(ctx context.Context) string {
|
|
return r.a.Description(ctx)
|
|
}
|
|
|
|
func (r *write2PlanMDWrapper) Run(ctx context.Context, input *adk.AgentInput, options ...adk.AgentRunOption) *adk.AsyncIterator[*adk.AgentEvent] {
|
|
iter := r.a.Run(ctx, input, options...)
|
|
nIter, gen := adk.NewAsyncIteratorPair[*adk.AgentEvent]()
|
|
|
|
go func() {
|
|
defer func() {
|
|
if e := recover(); e != nil {
|
|
log.Printf("[write2PlanMDWrapper] exec panic recover:%+v, stack: %s", e, string(debug.Stack()))
|
|
}
|
|
gen.Close()
|
|
}()
|
|
|
|
for {
|
|
e, ok := iter.Next()
|
|
if !ok {
|
|
break
|
|
}
|
|
if e.Action != nil && e.Action.Exit {
|
|
err := write2PlanMD(ctx, r.op)
|
|
gen.Send(e)
|
|
if err != nil {
|
|
log.Print("write plan failed", err)
|
|
return
|
|
}
|
|
return
|
|
}
|
|
gen.Send(e)
|
|
}
|
|
|
|
err := write2PlanMD(ctx, r.op)
|
|
if err != nil {
|
|
log.Print("write plan failed", err)
|
|
return
|
|
}
|
|
}()
|
|
|
|
return nIter
|
|
}
|
|
|
|
func write2PlanMD(ctx context.Context, op commandline.Operator) error {
|
|
var executedSteps []planexecute.ExecutedStep
|
|
var plan *generic.Plan
|
|
p, ok := utils.GetSessionValue[*generic.Plan](ctx, planexecute.PlanSessionKey)
|
|
if ok {
|
|
plan = p
|
|
}
|
|
es, ok := utils.GetSessionValue[[]planexecute.ExecutedStep](ctx, planexecute.ExecutedStepsSessionKey)
|
|
if ok {
|
|
executedSteps = es
|
|
}
|
|
wd, ok := params.GetTypedContextParams[string](ctx, params.WorkDirSessionKey)
|
|
if !ok {
|
|
return fmt.Errorf("work dir not found")
|
|
}
|
|
var plans []*generic.FullPlan
|
|
for i, step := range executedSteps {
|
|
var desc string
|
|
s := &generic.Step{}
|
|
err := json.Unmarshal([]byte(step.Step), s)
|
|
if err == nil {
|
|
desc = s.Desc
|
|
}
|
|
plans = append(plans, &generic.FullPlan{
|
|
TaskID: i + 1,
|
|
Status: generic.PlanStatusDone,
|
|
Desc: desc,
|
|
ExecResult: &generic.SubmitResult{
|
|
IsSuccess: utils.PtrOf(true),
|
|
Result: step.Result,
|
|
Files: nil, // todo
|
|
},
|
|
})
|
|
}
|
|
if plan != nil {
|
|
for i, step := range plan.Steps {
|
|
plans = append(plans, &generic.FullPlan{
|
|
TaskID: i + len(executedSteps) + 1,
|
|
Status: generic.PlanStatusTodo,
|
|
Desc: step.Desc,
|
|
})
|
|
}
|
|
}
|
|
err := generic.Write2PlanMD(ctx, op, wd, plans)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
return nil
|
|
}
|