vxcontrol/pentagi · warning
failed to put terminal log (write file cmd): %w
Error message
failed to put terminal log (write file cmd): %w
What it means
After writeFileToContainer succeeds, WriteFile emits an ANSI-styled 'File successfully saved' entry to the flow's terminal log via tlp.PutMsg (TermlogTypeStdin). If that logging write fails — DB down, context canceled, terminal-log storage error — the whole operation is reported as failed with this wrapper even though the file was already written to the container.
Source
Thrown at backend/pkg/tools/terminal.go:441
return buffer.String(), nil
}
func (t *terminal) WriteFile(ctx context.Context, flowID int64, content string, path string) (string, error) {
if path == "" {
return "", fmt.Errorf("path is required and cannot be empty")
}
if err := t.writeFileToContainer(ctx, flowID, path, content); err != nil {
return "", err
}
// Format success message with styling
successMsg := fmt.Sprintf("File successfully saved to %s", path)
styledMsg := fmt.Sprintf("%s%s%s%s", ansiColorSystemMsg, successMsg, ansiColorReset, ansiLineTerminator)
_, err := t.tlp.PutMsg(ctx, database.TermlogTypeStdin, styledMsg, t.containerID, t.taskID, t.subtaskID)
if err != nil {
return "", fmt.Errorf("failed to put terminal log (write file cmd): %w", err)
}
return fmt.Sprintf("Successfully wrote %d bytes to %s", len(content), path), nil
}
// writeFileToContainer copies content into the flow's container at path,
// overwriting it. It performs no terminal-log writes; WriteFile and EditFile
// each log their own, differently-worded, success message.
func (t *terminal) writeFileToContainer(ctx context.Context, flowID int64, path, content string) error {
containerName := PrimaryTerminalName(t.tenantPrefix, flowID)
isRunning, err := t.dockerClient.IsContainerRunning(ctx, t.containerLID)
if err != nil {
return fmt.Errorf("container runtime check failed: %w", err)
}
if !isRunning {
return fmt.Errorf("target container is not operational")
}View on GitHub (pinned to ea665308ba)
Solutions
- Check database connectivity and logs (PostgreSQL up, pool not exhausted) — this is a logging-side failure, not a Docker one
- Retry the WriteFile call; the file write is idempotent (same content overwrites)
- Decouple logging from the result path: log the PutMsg error (non-fatal) instead of failing a write that already succeeded
- Verify ctx deadlines upstream aren't expiring between the Docker put and the log insert
Example fix
// before
_, err := t.tlp.PutMsg(ctx, database.TermlogTypeStdin, styledMsg, t.containerID, t.taskID, t.subtaskID)
if err != nil {
return "", fmt.Errorf("failed to put terminal log (write file cmd): %w", err)
}
// after
if _, err := t.tlp.PutMsg(ctx, database.TermlogTypeStdin, styledMsg, t.containerID, t.taskID, t.subtaskID); err != nil {
logger.WarnContext(ctx, "termlog write failed for file save", "path", path, "err", err)
} Defensive patterns
Strategy: try-catch
Validate before calling
// Pre-call: ensure the termlog store is reachable
if err := db.PingContext(ctx); err != nil {
return fmt.Errorf("terminal log store unavailable: %w", err)
} Try / catch
if _, err := tlp.PutMsg(ctx, database.TermlogTypeStdin, styledMsg, containerID, taskID, subtaskID); err != nil {
logger.WarnContext(ctx, "termlog write failed; file already saved", "path", path, "err", err)
// do not fail the whole write for a logging error
} Prevention
- Treat terminal-log persistence as best-effort, not as the write's success criterion
- Give the log insert a short independent timeout so ctx cancellation upstream doesn't poison it
- Monitor DB pool saturation during heavy flow activity
- Add a fallback buffer/retry queue for failed termlog writes
When it happens
Trigger: The file content was successfully put into the container, but the subsequent PutMsg to the termlog store returned an error: PostgreSQL unreachable/rolled back, ctx deadline exceeded during the log insert, or the terminal-log record for the container/task/subtask is in a bad state.
Common situations: Database failover or connection-pool exhaustion during heavy flow activity; request context canceled by an upstream HTTP/GraphQL timeout right after the Docker write completed; migration/schema drift on the termlog table.
Related errors
- failed to put terminal log (stdout): %w
- failed to put terminal log (read file cmd): %w
- failed to put terminal log (read file content): %w
- failed to create flow agent log: %w
- failed to create flow msg log: %w
AI-assisted analysis of vxcontrol/pentagi@ea665308ba (2026-09-01).
Data as JSON: /api/errors/5dcc31c4aeda6e97.
Report an issue: GitHub.