Clarify Agentbox names and invariants
Co-authored-by: codegirl007 <codegirl-007@users.noreply.github.com>
This commit is contained in:
co-authored by
codegirl007
parent
4d2fb4a733
commit
e702497996
@@ -67,7 +67,7 @@ func run(ctx context.Context, args []string) error {
|
||||
fmt.Fprintf(os.Stderr, "Run artifacts: %s\n", traceStore.Directory())
|
||||
return err
|
||||
}
|
||||
fmt.Printf("Replay written to:\n%s\n", traceStore.Directory())
|
||||
fmt.Printf("Run artifacts written to:\n%s\n", traceStore.Directory())
|
||||
return nil
|
||||
}
|
||||
|
||||
|
||||
@@ -76,6 +76,8 @@ func greenCentroidX(screenshot []byte) (float64, error) {
|
||||
for y := bounds.Min.Y; y < bounds.Max.Y; y++ {
|
||||
for x := bounds.Min.X; x < bounds.Max.X; x++ {
|
||||
red, green, blue, _ := renderedImage.At(x, y).RGBA()
|
||||
// Match the mover's #00ff66 square. Requiring 1,000 matching pixels
|
||||
// prevents a small green UI detail from passing verification.
|
||||
if green > 0xc000 && red < 0x4000 && blue < 0x8000 {
|
||||
xCoordinateSum += uint64(x)
|
||||
greenPixelCount++
|
||||
|
||||
@@ -87,12 +87,14 @@ func modelPrompt(task string, history []Step, observation Observation) (string,
|
||||
return "", err
|
||||
}
|
||||
return "You control an interactive Linux application from screenshots. " +
|
||||
"Choose exactly one safe input action, or mark done when the task is complete. " +
|
||||
"Choose exactly one allowed input action, or mark done when the task is complete. " +
|
||||
"Use logical key names such as RIGHT, ENTER, or ESCAPE. Keep waits under 5000 ms.\n" +
|
||||
string(data), nil
|
||||
}
|
||||
|
||||
func decisionSchema() map[string]any {
|
||||
// Strict structured output requires every action property to be present,
|
||||
// even when a particular action ignores most of them.
|
||||
actionProperties := map[string]any{
|
||||
"type": map[string]any{
|
||||
"type": "string",
|
||||
|
||||
@@ -13,7 +13,7 @@ import (
|
||||
type manifest struct {
|
||||
Command string `json:"command"`
|
||||
Args []string `json:"args"`
|
||||
Env map[string]string `json:"env"`
|
||||
EnvironmentVariables map[string]string `json:"env"`
|
||||
WindowTitle string `json:"window_title"`
|
||||
}
|
||||
|
||||
@@ -60,7 +60,7 @@ func Resolve(path string) (environment.Command, error) {
|
||||
return environment.Command{
|
||||
Path: commandPath,
|
||||
Args: config.Args,
|
||||
Env: config.Env,
|
||||
EnvironmentVariables: config.EnvironmentVariables,
|
||||
WindowTitle: config.WindowTitle,
|
||||
}, nil
|
||||
}
|
||||
|
||||
@@ -17,7 +17,7 @@ func (environmentBackend *Environment) Launch(
|
||||
ctx context.Context,
|
||||
application environment.Command,
|
||||
) error {
|
||||
fmt.Fprintln(environmentBackend.config.Output, "Uploading build...")
|
||||
fmt.Fprintln(environmentBackend.config.Output, "Staging application...")
|
||||
executable, err := os.Open(application.Path)
|
||||
if err != nil {
|
||||
return fmt.Errorf("open application: %w", err)
|
||||
@@ -47,7 +47,7 @@ func (environmentBackend *Environment) Launch(
|
||||
|
||||
fmt.Fprintln(environmentBackend.config.Output, "Launching application...")
|
||||
dockerArguments := []string{"exec", "-d"}
|
||||
for variableName, variableValue := range application.Env {
|
||||
for variableName, variableValue := range application.EnvironmentVariables {
|
||||
dockerArguments = append(
|
||||
dockerArguments,
|
||||
"-e",
|
||||
|
||||
@@ -69,6 +69,8 @@ func (environmentBackend *Environment) Start(ctx context.Context) error {
|
||||
); err != nil {
|
||||
return fmt.Errorf("start environment: %w", err)
|
||||
}
|
||||
// entrypoint.sh creates this file only after both Xvfb and Openbox accept
|
||||
// requests. It is the readiness handshake between host and container.
|
||||
if err := waitFor(ctx, 10*time.Second, func() bool {
|
||||
_, readyErr := environmentBackend.runDocker(
|
||||
ctx,
|
||||
|
||||
@@ -10,7 +10,7 @@ import (
|
||||
type Command struct {
|
||||
Path string
|
||||
Args []string
|
||||
Env map[string]string
|
||||
EnvironmentVariables map[string]string
|
||||
WindowTitle string
|
||||
}
|
||||
|
||||
@@ -36,7 +36,8 @@ type InputAction struct {
|
||||
DurationMS int `json:"duration_ms,omitempty"`
|
||||
}
|
||||
|
||||
// LogEntry is a snapshot of one application output stream.
|
||||
// LogEntry is a cumulative snapshot of one application output stream. Time is
|
||||
// when Agentbox captured the snapshot, not when the application emitted it.
|
||||
type LogEntry struct {
|
||||
Stream string `json:"stream"`
|
||||
Message string `json:"message"`
|
||||
|
||||
@@ -117,7 +117,7 @@ func Run(ctx context.Context) (runErr error) {
|
||||
return fmt.Errorf("build environment image: %w", err)
|
||||
}
|
||||
|
||||
fmt.Println("Creating isolated graphical environment...")
|
||||
fmt.Println("Creating restricted graphical environment...")
|
||||
_, err = r.docker(ctx,
|
||||
"create",
|
||||
"--name", r.containerName,
|
||||
@@ -327,6 +327,8 @@ func squareCentroid(path string) (point, error) {
|
||||
for y := bounds.Min.Y; y < bounds.Max.Y; y++ {
|
||||
for x := bounds.Min.X; x < bounds.Max.X; x++ {
|
||||
red, green, blue, _ := img.At(x, y).RGBA()
|
||||
// Match the demo square's #00ff66 color with enough tolerance for
|
||||
// image conversion while rejecting the black background.
|
||||
if green > 0xc000 && red < 0x4000 && blue < 0x8000 {
|
||||
sumX += uint64(x)
|
||||
sumY += uint64(y)
|
||||
|
||||
@@ -45,7 +45,7 @@ func Run(ctx context.Context, config Config) (runErr error) {
|
||||
if err := config.Environment.Launch(ctx, config.Command); err != nil {
|
||||
return err
|
||||
}
|
||||
fmt.Fprintln(config.Output, "Agent attached.")
|
||||
fmt.Fprintln(config.Output, "Agent loop started.")
|
||||
|
||||
var stepHistory []agent.Step
|
||||
var actionHistory []environment.InputAction
|
||||
|
||||
@@ -0,0 +1,4 @@
|
||||
// Package trace stores durable run records. steps.jsonl contains complete
|
||||
// observations and decisions, actions.jsonl is an action-only view, and PNG
|
||||
// screenshots remain separate files referenced by relative paths.
|
||||
package trace
|
||||
@@ -25,6 +25,8 @@ func List(projectRoot string) ([]Run, error) {
|
||||
continue
|
||||
}
|
||||
run, err := Read(projectRoot, entry.Name())
|
||||
// Old or malformed trace directories are intentionally hidden rather
|
||||
// than making the entire run listing fail.
|
||||
if err == nil && run.SchemaVersion == SchemaVersion {
|
||||
runs = append(runs, run)
|
||||
}
|
||||
@@ -87,6 +89,7 @@ func ReadSteps(projectRoot, runID string) ([]StepRecord, error) {
|
||||
}
|
||||
|
||||
func validateRunID(runID string) error {
|
||||
// Run IDs become path components, so reject separators and traversal.
|
||||
if filepath.Base(runID) != runID {
|
||||
return errors.New("invalid run ID")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user