Tasks¶
Tasks are the A2A protocol's mechanism for asynchronous, long-running operations. They provide a way to submit work to an agent and track its progress without maintaining an open connection.
A2A Protocol Compliance¶
Hector's task implementation is fully compliant with the A2A (Agent-to-Agent) Protocol specification. This ensures interoperability with other A2A-compliant systems.
Core Methods (Section 11.1.2 - MUST implement)¶
✅ message/send - Create tasks (blocking or non-blocking)
✅ tasks/get - Retrieve task status and results
✅ tasks/cancel - Cancel running tasks
Optional Methods (Section 11.1.3 - MAY implement)¶
✅ message/stream - Stream task updates in real-time
✅ tasks/list - List tasks with filtering and pagination
✅ tasks/resubscribe - Resume streaming for existing tasks
REST Endpoints (Section 3.5.3 - HTTP+JSON/REST transport)¶
All task operations are available via REST API:
# Create task
POST /v1/agents/{agent}/message:send
# Get task details
GET /v1/agents/{agent}/tasks/{taskID}
# Cancel task
POST /v1/agents/{agent}/tasks/{taskID}:cancel
# List tasks
GET /v1/agents/{agent}/tasks
Supported Task States (Section 6.3)¶
All A2A-specified task states are supported:
| State | Type | Description |
|---|---|---|
| SUBMITTED | Initial | Task created, waiting to start |
| WORKING | Active | Agent actively processing |
| COMPLETED | Terminal | Success |
| FAILED | Terminal | Error occurred |
| CANCELLED | Terminal | User cancelled |
| INPUT_REQUIRED | Interrupted | Needs user input |
| REJECTED | Terminal | Agent rejected task |
| AUTH_REQUIRED | Special | Needs authentication |
Overview¶
What is a Task?¶
A Task is a unit of work submitted to an agent that can be: - Tracked - Query status and progress at any time - Asynchronous - Submit and disconnect, check back later - Persistent - Survives server restarts (with SQL backend) - Cancellable - Stop running tasks when needed
When to Use Tasks¶
| Use Case | Recommendation |
|---|---|
| Quick queries (<30s) | Use call or chat commands (blocking) |
| Long operations (minutes/hours) | Use tasks (non-blocking) |
| Background processing | Use tasks |
| Need progress tracking | Use tasks |
| Multi-step workflows | Use tasks |
Task Lifecycle¶
SUBMITTED → WORKING → COMPLETED
↓
FAILED
↓
CANCELLED
Task States¶
| State | Description | Terminal |
|---|---|---|
SUBMITTED |
Task created, waiting to start | No |
WORKING |
Task is actively processing | No |
COMPLETED |
Task finished successfully | Yes |
FAILED |
Task encountered an error | Yes |
CANCELLED |
Task was cancelled by user | Yes |
REJECTED |
Task was rejected (e.g., quota exceeded) | Yes |
Terminal states mean the task won't change anymore and can be archived.
Configuration¶
In-Memory Tasks (Default)¶
Tasks work out-of-the-box with no configuration. They're stored in memory and lost on server restart.
agents:
assistant:
llm: gpt-4o
# No task configuration needed - uses in-memory storage
Characteristics: - ✅ Zero configuration - ✅ Fast - ❌ Lost on restart - ❌ Not suitable for production
SQL-Backed Tasks (Production)¶
For production use, configure SQL persistence:
agents:
production-agent:
llm: gpt-4o
task:
backend: sql
worker_pool: 100 # Max concurrent tasks
sql:
driver: sqlite # or: postgres, mysql
database: ./data/tasks.db
max_conns: 10
max_idle: 2
llms:
gpt-4o:
type: openai
model: gpt-4o
api_key: ${OPENAI_API_KEY}
Supported Databases: - SQLite - Simple file-based storage - PostgreSQL - Production-grade, multi-instance - MySQL - Alternative production option
PostgreSQL Example:
task:
backend: sql
sql:
driver: postgres
database: postgres://user:password@localhost:5432/hector_tasks?sslmode=disable
max_conns: 25
max_idle: 5
Usage¶
Server Mode¶
Start a server with task support:
# With in-memory tasks (development)
hector serve --config config.yaml
# Server output shows:
# Hector server listening on :8080
# Registered agents: assistant
# Task service: in-memory
Submitting Tasks¶
Tasks are submitted via the A2A protocol's blocking configuration:
Blocking (default):
# Waits for completion, returns result
curl -X POST http://localhost:8080/v1/agents/assistant/message:send \
-H "Content-Type: application/json" \
-d '{
"message": {"parts": [{"text": "Long running task"}]},
"configuration": {"blocking": true}
}'
Non-blocking (task mode):
# Returns task ID immediately
curl -X POST http://localhost:8080/v1/agents/assistant/message:send \
-H "Content-Type: application/json" \
-d '{
"message": {"parts": [{"text": "Long running task"}]},
"configuration": {"blocking": false}
}'
# Response:
# {
# "task": {
# "id": "task-abc123",
# "context_id": "ctx-xyz",
# "status": {"state": "TASK_STATE_SUBMITTED"}
# }
# }
Checking Task Status¶
Use the task commands to monitor progress:
# Get task details
hector task get assistant task-abc123 --url http://localhost:8080
# Output:
# Task ID: task-abc123
# Status: TASK_STATE_WORKING
# Context ID: ctx-xyz
# Created: 2024-01-15 10:30:00
Cancelling Tasks¶
Stop a running task:
hector task cancel assistant task-abc123 --url http://localhost:8080
# Output:
# ✅ Task cancelled successfully
#
# Task ID: task-abc123
# Status: TASK_STATE_CANCELLED
CLI Commands¶
hector task get¶
Retrieve task details by ID.
Usage:
hector task get <agent> <task-id> [flags]
Flags:
- --url URL - Agent service URL (required for client mode)
- --token TOKEN - Authentication token
- --config FILE - Configuration file (for local mode)
Examples:
# Client mode - query remote service
hector task get assistant task-abc123 --url http://localhost:8080
# Local mode - query from config
hector task get assistant task-abc123 --config config.yaml
# With authentication
hector task get assistant task-abc123 \
--url https://prod:8080 \
--token "eyJ..."
Output:
Task ID: task-abc123
Status: TASK_STATE_COMPLETED
Context ID: ctx-xyz
Created: 2024-01-15 10:30:00
Updated: 2024-01-15 10:35:00
History:
[USER] Long running analysis task
[ASSISTANT] Analysis complete. Found 3 issues...
Artifacts:
- report.pdf (application/pdf, 2.5 MB)
hector task cancel¶
Cancel a running or pending task.
Usage:
hector task cancel <agent> <task-id> [flags]
Flags:
- Same as task get
Examples:
# Cancel task
hector task cancel assistant task-abc123 --url http://localhost:8080
# Cancel with config
hector task cancel assistant task-abc123 --config config.yaml
Modes and Limitations¶
Supported Modes¶
| Mode | Task Get | Task Cancel | Notes |
|---|---|---|---|
| Server Mode | ✅ Via API | ✅ Via API | Full task support |
| Client Mode | ✅ | ✅ | Connect to any A2A service |
| Local Config Mode | ✅ | ✅ | Direct agent access |
| Zero-Config Mode | ❌ | ❌ | Not supported* |
Note: Task commands require explicit agent configuration. In zero-config mode, use call or chat commands instead.
Client Mode¶
Task commands work with any A2A-compliant service:
# Query task from Hector server
hector task get assistant task-123 --url http://hector:8080
# Query task from ANY other A2A service
hector task get some-agent task-456 --url http://other-service:8080
Local Mode¶
When using --config, tasks are queried directly from the configured agent:
# Query task from local configuration
hector task get assistant task-abc123 --config agents.yaml
The agent must have task persistence configured to retrieve historical tasks.
API Reference¶
REST API¶
Get Task:
GET /v1/tasks/task-abc123
Authorization: Bearer <token>
Cancel Task:
POST /v1/tasks/task-abc123:cancel
Authorization: Bearer <token>
List Tasks:
GET /v1/tasks?context_id=ctx-xyz&status=TASK_STATE_WORKING
gRPC API¶
service A2AService {
rpc GetTask(GetTaskRequest) returns (Task);
rpc CancelTask(CancelTaskRequest) returns (Task);
rpc ListTasks(ListTasksRequest) returns (ListTasksResponse);
rpc TaskSubscription(TaskSubscriptionRequest) returns (stream StreamResponse);
}
Task Subscription (Streaming)¶
Subscribe to real-time task updates:
REST (Server-Sent Events):
curl -N http://localhost:8080/v1/tasks/task-abc123:subscribe
gRPC:
stream, err := client.TaskSubscription(ctx, &pb.TaskSubscriptionRequest{
Name: "tasks/task-abc123",
})
for {
resp, err := stream.Recv()
// Handle status updates, artifacts, etc.
}
Production Considerations¶
Database Selection¶
| Database | Use Case | Pros | Cons |
|---|---|---|---|
| SQLite | Single instance, low volume | Simple setup | No multi-instance |
| PostgreSQL | Production, multi-instance | Robust, scalable | Requires setup |
| MySQL | Production, MySQL shops | Well-known | Less common for tasks |
Task Retention¶
Tasks accumulate over time. Implement cleanup:
-- PostgreSQL: Delete completed tasks older than 30 days
DELETE FROM tasks
WHERE state IN ('COMPLETED', 'FAILED', 'CANCELLED')
AND updated_at < NOW() - INTERVAL '30 days';
Worker Pool Sizing¶
Configure based on your workload:
task:
worker_pool: 100 # Max concurrent tasks
Guidelines: - Start with 100 for most workloads - Increase for high concurrency needs - Monitor task queue depth
Monitoring¶
Track task metrics: - Task completion rate - Average task duration - Failed task percentage - Queue depth
Examples¶
Long-Running Analysis¶
config.yaml:
agents:
analyst:
llm: gpt-4o
tools: [search, write_file]
task:
backend: sql
sql:
driver: sqlite
database: ./tasks.db
llms:
gpt-4o:
type: openai
model: gpt-4o
api_key: ${OPENAI_API_KEY}
Submit task:
# Start server
hector serve --config config.yaml &
# Submit non-blocking task via API
TASK_ID=$(curl -s -X POST http://localhost:8080/v1/agents/analyst/message:send \
-H "Content-Type: application/json" \
-d '{
"message": {"parts": [{"text": "Analyze the entire codebase for security issues"}]},
"configuration": {"blocking": false}
}' | jq -r '.task.id')
echo "Task submitted: $TASK_ID"
Monitor progress:
# Check status periodically
watch -n 5 "hector task get analyst $TASK_ID --config config.yaml"
Cancel if needed:
hector task cancel analyst $TASK_ID --config config.yaml
Best Practices¶
1. Use Tasks for Long Operations¶
# ✅ Good: Long-running task
POST /v1/message:send
{"configuration": {"blocking": false}}
# ❌ Bad: Quick query as task (unnecessary overhead)
POST /v1/message:send
{"configuration": {"blocking": false}, "message": {"parts": [{"text": "What is 2+2?"}]}}
2. Configure SQL for Production¶
# ✅ Good: Production setup
task:
backend: sql
sql:
driver: postgres
database: postgres://...
# ❌ Bad: In-memory for production
# (tasks lost on restart)
3. Implement Task Cleanup¶
Set up periodic cleanup to avoid database bloat:
# Cron job to clean old tasks
0 2 * * * psql -c "DELETE FROM tasks WHERE state='COMPLETED' AND updated_at < NOW() - INTERVAL '30 days'"
4. Handle Errors Gracefully¶
# Check task status before assuming success
STATUS=$(hector task get assistant $TASK_ID --config config.yaml | grep Status | awk '{print $2}')
if [ "$STATUS" = "TASK_STATE_FAILED" ]; then
echo "Task failed, check logs"
exit 1
fi
Troubleshooting¶
"task not found"¶
Cause: Task ID doesn't exist or expired (in-memory mode with restart).
Solution: - Verify task ID is correct - Use SQL backend for persistence - Check if server restarted (in-memory tasks are lost)
Tasks stuck in WORKING¶
Cause: Agent crashed or task deadlocked.
Solution: - Cancel stuck task - Check agent logs for errors - Restart agent if needed
hector task cancel assistant stuck-task-id --config config.yaml
Task commands not working¶
Error: unsupported mode for client creation
Cause: Task commands require agent configuration (don't work in pure zero-config).
Solution: Use a configuration file:
# Create minimal config
cat > config.yaml << EOF
agents:
assistant:
llm: gpt
llms:
gpt:
type: openai
model: gpt-4o-mini
api_key: ${OPENAI_API_KEY}
EOF
# Now task commands work
hector task get assistant task-id --config config.yaml
Next Steps¶
- Streaming - Real-time task updates
- Multi-Agent Systems - Coordinate tasks across agents
- Session Persistence - Long-term conversation storage
- API Reference - Complete API documentation
Related Topics¶
- A2A Protocol - Task specification
- CLI Reference - Task command details
- Configuration - Task configuration options