Lesson 23 / 31
Tasks, Messages, Parts and Artifacts
Learn the core objects and the task lifecycle.
A task is a unit of delegated work
The client sends a message (a role of user or agent plus one or more parts: text, files or structured data). The remote agent may reply directly, or create a task with an id: a stateful unit of work whose status moves through a lifecycle such as submitted → working → (input-required) → completed, or failed, canceled or rejected (the spec lists a few more states, such as auth-required). Results are returned as artifacts (documents, files, structured outputs), made of parts, and intermediate status updates can be streamed. A context id groups related tasks into one conversation. Tasks are the reason A2A suits long-running and interactive work. Terminal states are final: a completed task cannot be reopened, so follow-up work starts a new task in the same context.
A task lifecycle as a state machine, run
I ran this with plain Python 3 (standard library only). This is a simplified model for learning, not the full A2A state list. A normal task goes submitted, working, input-required (the agent needs more information), working again and completed. Trying to move a completed task back to working is rejected.
ALLOWED = {
"submitted": {"working", "rejected"},
"working": {"input-required", "completed", "failed", "canceled"},
"input-required": {"working", "canceled"},
"completed": set(), "failed": set(), "canceled": set(), "rejected": set(),
}
class Task:
def __init__(self):
self.state, self.history = "submitted", ["submitted"]
def move(self, new):
if new not in ALLOWED[self.state]:
raise ValueError(f"illegal transition {self.state} -> {new}")
self.state = new; self.history.append(new)
t = Task()
for step in ("working", "input-required", "working", "completed"):
t.move(step)
print(" -> ".join(t.history))
try:
t.move("working")
except ValueError as e:
print("blocked:", e)
Output:
submitted -> working -> input-required -> working -> completed blocked: illegal transition completed -> working
Message, task and artifact shapes (illustrative)
Field names follow the general A2A structure; check the current specification for exact names. Not run here.
{
"message": { "role": "user",
"parts": [ { "kind": "text", "text": "Please propose a refund for invoice INV-204" } ] },
"task": { "id": "t-91", "contextId": "c-7",
"status": { "state": "input-required",
"message": { "role": "agent", "parts": [ { "kind": "text", "text": "Which order line is damaged?" } ] } } }
}Quick check: What does the input-required state mean?
- The remote agent needs more information from the client or user
- The task failed permanently
- The task was deleted
- The card is invalid
Answer
The remote agent needs more information from the client or user — The task pauses until the requested input arrives.