The building blocks of AI workflows.
Task
in ControlFlow is a structured way to define these objectives and guide the AI’s behavior. Each task represents a “checkpoint” that requires the AI to meet an observable, verifiable goal. In this way, tasks serve as a bridge between the structured world of traditional software and the more fluid, adaptive world of AI.
This task-centric approach allows you to leverage the full power of AI while maintaining precise oversight. Each task becomes a checkpoint where you can validate outputs, ensuring that the AI’s work aligns with your application’s requirements and constraints.
Task
class directly, or using the @task
decorator.
cf.run
function to create and run a task in a single step. This is a common operation and accepts all the same arguments as creating a Task
directly. See Running Tasks for more information.Task
classTask
class:
@task
decorator@task
decorator for creating tasks, especially for tasks that are frequently invoked with different context values. However, this approach is less common and less flexible than using the Task
class directly.
Task property | Inferred from |
---|---|
name | The function’s name |
objective | The function’s docstring and return value (if any) |
result_type | The function’s return annotation |
context | The function’s arguments (keyed by argument name) and return value (keyed as “Additional context”) |
@task
decorator.
objective
is the only required task configuration, as it indicates the task’s purpose and helps agents understand the task they are working on.
str
, int
, bool
, list
, dict
, etc.None
: sometimes a task requires agents to take actions but not return any specific value. In this case, provide clear instructions to agents about what they should do before completing the task.Tuple[int, str]
, List[str]
, Dict[str, int]
, etc.Annotated[str, "a 5 digit zip code"]
["book", "movie", "album"]
would require the agent to choose one of the three values.str
.
Pydantic model example:
result_validator
parameter. This function will be called with the raw result and should return the validated result or raise an exception if the result is not valid.
objective
to describe what the task’s result should be, and use the instructions
to provide more detailed instructions on how to achieve the objective.None
to infer agents from a parent task, the flow, or the global default (in order).
completion_agents
parameter. Note that if your completion agents are not also assigned to the task, they will not be able to mark the task as successful or failed!
completion_tools
parameter.
completion_tools
parameter. This allows you to specify whether you want to provide success and/or failure tools, or even provide custom completion tools.
The completion_tools
parameter accepts a list of strings, where each string represents a tool to be generated. The available options are:
"SUCCEED"
: Generates a tool for marking the task as successful."FAIL"
: Generates a tool for marking the task as failed.completion_tools
is not specified, both "SUCCEED"
and "FAIL"
tools will be generated by default.
You can manually create completion tools and provide them to your agents by calling task.get_success_tool()
and task.get_fail_tool()
.
completion_tools
, agents may be unable to complete the task or become stuck in a failure state. Without caps on LLM turns or calls, this could lead to runaway LLM usage. Make sure to manually manage how agents complete tasks if you are using a custom set of completion tools.Task
are set during task execution, and can be examined as part of your workflow’s logic.
PENDING
status, progress to a RUNNING
status whenever one of their assigned agents begins to work on it, and finally moves to one of a few completed statuses when the task is finished.
Agents use tools to mark tasks as SUCCESSFUL
or FAILED
. Successful tasks will also have a result
property, which contains the task’s final output. This is a value that satisfies the task’s objective and result type configuration. Failed tasks will have an error message as their result.
Method | Description |
---|---|
is_pending() | Returns True if the task is pending. |
is_running() | Returns True if the task is running. |
is_successful() | Returns True if the task is successful. |
is_failed() | Returns True if the task is failed. |
is_skipped() | Returns True if the task is skipped. |
is_complete() | Returns True if the task is complete (either successful, failed, or skipped) |
is_incomplete() | Returns True if the task is incomplete (either pending, running, or not started) |
is_ready() | Returns True if the task is ready to be worked on (i.e. all dependencies are complete but the task is incomplete) |
result
property will contain the task’s final output. This is a value that satisfies the task’s objective and result type configuration.
If a task fails, its result
property will contain an error message describing the failure.