Tasks are the work assignments in CrewAI. Each task has a description, expected output, and an assigned agent. This guide shows you how to create effective tasks.
Coming from Software Engineering? CrewAI tasks are like Jira tickets for AI agents — a description of what to do, acceptance criteria (expected output), an assignee (agent), and dependencies (context from other tasks). If you've ever written a good user story with clear acceptance criteria, you already know how to define effective CrewAI tasks. The skill of writing unambiguous specifications transfers directly.
What is a Task?
A task defines:
- What needs to be done
- Who should do it
- What the output should look like
- Dependencies on other tasks
Basic Task Creation
# script_id: day_054_tasks_definition/basic_task_creation
from crewai import Agent, Task
# First, create an agent
researcher = Agent(
role="Research Analyst",
goal="Find accurate, up-to-date information",
backstory="You are an expert researcher with years of experience."
)
# Create a task for this agent
research_task = Task(
description="""Research the current state of electric vehicles in 2024.
Focus on:
- Market leaders and their market share
- Latest technological advancements
- Price trends
- Consumer adoption rates
Provide detailed, factual information with sources where possible.""",
expected_output="""A comprehensive research report containing:
- Executive summary
- Market analysis
- Technology overview
- Key statistics
- Future outlook""",
agent=researcher
)
Task Properties
Required Properties
# script_id: day_054_tasks_definition/required_properties
task = Task(
# What the agent should do (required)
description="Detailed instructions for the task...",
# What the output should look like (required)
expected_output="Description of desired output format...",
# Which agent handles this (required)
agent=my_agent
)
Optional Properties
# script_id: day_054_tasks_definition/optional_properties
task = Task(
description="...",
expected_output="...",
agent=my_agent,
# Dependencies - tasks that must complete first
context=[previous_task1, previous_task2],
# Output file - save result to file
output_file="output/research_report.md",
# Async execution - run in parallel
async_execution=True,
# Human input - require human approval
human_input=True,
# Callback - function to run after completion
callback=my_callback_function
)
Task Dependencies with Context
Chain tasks together using context:
# script_id: day_054_tasks_definition/task_dependencies_context
from crewai import Agent, Task, Crew, Process
# Agents
researcher = Agent(role="Researcher", goal="Research topics", backstory="Expert researcher")
writer = Agent(role="Writer", goal="Write content", backstory="Expert writer")
editor = Agent(role="Editor", goal="Edit content", backstory="Expert editor")
# Task 1: Research (no dependencies)
research_task = Task(
description="Research artificial intelligence trends in 2024",
expected_output="Detailed research notes with key findings",
agent=researcher
)
# Task 2: Write (depends on research)
writing_task = Task(
description="Write a blog post based on the research provided",
expected_output="A 1000-word blog post",
agent=writer,
context=[research_task] # Gets output from research_task
)
# Task 3: Edit (depends on writing)
editing_task = Task(
description="Edit the blog post for clarity and grammar",
expected_output="A polished, publication-ready blog post",
agent=editor,
context=[writing_task] # Gets output from writing_task
)
# The crew will execute in order based on dependencies
crew = Crew(
agents=[researcher, writer, editor],
tasks=[research_task, writing_task, editing_task],
process=Process.sequential
)
Multiple Context Sources
A task can receive context from multiple previous tasks:
# script_id: day_054_tasks_definition/multiple_context_sources
# Research from multiple angles
market_research = Task(
description="Research market trends",
expected_output="Market analysis report",
agent=market_researcher
)
tech_research = Task(
description="Research technology developments",
expected_output="Technology analysis report",
agent=tech_researcher
)
competitor_research = Task(
description="Research competitor activities",
expected_output="Competitor analysis report",
agent=competitor_researcher
)
# Synthesis task receives all three
synthesis_task = Task(
description="""Synthesize all research into a comprehensive report.
Combine insights from market, technology, and competitor analyses.""",
expected_output="Unified strategic report",
agent=strategist,
context=[market_research, tech_research, competitor_research] # All three!
)
Task Output Types
Text Output (Default)
# script_id: day_054_tasks_definition/text_output
task = Task(
description="Write a summary",
expected_output="A 200-word summary",
agent=writer
)
# Output is a string
File Output
# script_id: day_054_tasks_definition/file_output
task = Task(
description="Generate a report",
expected_output="Detailed report in markdown format",
agent=analyst,
output_file="reports/analysis.md" # Saved to file
)
Structured Output with Pydantic
# script_id: day_054_tasks_definition/structured_output_pydantic
from pydantic import BaseModel
from typing import List
class ResearchReport(BaseModel):
title: str
summary: str
key_findings: List[str]
recommendations: List[str]
task = Task(
description="Research and report on AI trends",
expected_output="Structured research report",
agent=researcher,
output_pydantic=ResearchReport # Structured output!
)
# Access result
result = task.output
print(result.title) # Typed access
print(result.key_findings)
# > **Note:** CrewAI 0.70+ may have changed this API. Check the [CrewAI docs](https://docs.crewai.com) for the latest syntax.
Writing Effective Task Descriptions
Be Specific
# script_id: day_054_tasks_definition/specific_descriptions
# Bad: Vague
task = Task(
description="Research AI",
expected_output="Report",
agent=researcher
)
# Good: Specific
task = Task(
description="""Research artificial intelligence applications in healthcare.
Focus areas:
1. Diagnostic imaging (X-rays, MRIs, CT scans)
2. Drug discovery and development
3. Patient monitoring systems
4. Administrative automation
For each area, identify:
- Current state of adoption
- Key players and products
- Success stories and case studies
- Challenges and limitations
Use recent sources (2023-2024) and cite them.""",
expected_output="""A structured research report with:
- Executive summary (100 words)
- Section for each focus area (300 words each)
- Data tables where applicable
- List of sources""",
agent=researcher
)
Include Success Criteria
# script_id: day_054_tasks_definition/success_criteria
task = Task(
description="""Write product descriptions for our new laptop.
Requirements:
- Length: 150-200 words
- Tone: Professional but approachable
- Include: Key specs, benefits, use cases
- Target audience: Business professionals
Success criteria:
- All technical specs mentioned
- At least 3 unique benefits highlighted
- Clear call-to-action included
- No jargon that average user won't understand""",
expected_output="Product description meeting all criteria above",
agent=copywriter
)
Human Input Tasks
Require human approval before proceeding:
# script_id: day_054_tasks_definition/human_input_task
critical_task = Task(
description="Draft an email to all customers about the service outage",
expected_output="Professional apology email",
agent=communications_agent,
human_input=True # Pauses for human review
)
# When executed, crew will pause and show output for approval
Callback Functions
Run custom code when a task completes:
# script_id: day_054_tasks_definition/callback_functions
def on_task_complete(output):
"""Called when task finishes."""
print(f"Task completed!")
print(f"Output length: {len(output)} characters")
# Log to database, send notification, etc.
def validate_output(output):
"""Validate and potentially modify output."""
if len(output) < 100:
raise ValueError("Output too short!")
return output
task = Task(
description="Generate a detailed report",
expected_output="Comprehensive report",
agent=analyst,
callback=on_task_complete
)
Task Templates
Create reusable task templates:
# script_id: day_054_tasks_definition/task_templates
def create_research_task(topic: str, agent: Agent) -> Task:
"""Template for research tasks."""
return Task(
description=f"""Conduct thorough research on: {topic}
Research should include:
- Current state and trends
- Key players and stakeholders
- Recent developments (last 12 months)
- Future outlook
Use reliable sources and cite them.""",
expected_output=f"Comprehensive research report on {topic}",
agent=agent
)
def create_writing_task(topic: str, word_count: int, agent: Agent, context: list = None) -> Task:
"""Template for writing tasks."""
return Task(
description=f"""Write engaging content about: {topic}
Requirements:
- Word count: approximately {word_count} words
- Tone: Professional and engaging
- Include introduction, body, and conclusion
- Use subheadings for readability""",
expected_output=f"A {word_count}-word article about {topic}",
agent=agent,
context=context or []
)
# Usage
research = create_research_task("renewable energy", researcher)
article = create_writing_task("renewable energy trends", 1000, writer, [research])
Best Practices
1. Clear Expected Output
# script_id: day_054_tasks_definition/clear_expected_output
# Bad
expected_output="A report"
# Good
expected_output="""A structured report containing:
- Executive summary (2-3 sentences)
- Key findings (bullet points)
- Detailed analysis (3-4 paragraphs)
- Recommendations (numbered list)
- Appendix with data sources"""
2. Appropriate Task Granularity
# script_id: day_054_tasks_definition/task_granularity
# Bad: Too big
task = Task(
description="Research, write, edit, and publish an article"
)
# Good: Broken into appropriate pieces
research_task = Task(description="Research the topic...")
writing_task = Task(description="Write the first draft...", context=[research_task])
editing_task = Task(description="Edit and polish...", context=[writing_task])
3. Match Tasks to Agent Strengths
# script_id: day_054_tasks_definition/match_tasks_to_agents
# Good: Task matches agent's role
researcher = Agent(role="Research Specialist", ...)
research_task = Task(description="Research market trends", agent=researcher)
# Bad: Mismatched
researcher = Agent(role="Research Specialist", ...)
coding_task = Task(description="Write Python code", agent=researcher)
Summary
Quick Reference
# script_id: day_054_tasks_definition/quick_reference
# Basic task
task = Task(
description="What to do",
expected_output="What to produce",
agent=my_agent
)
# With dependencies
task = Task(
description="...",
expected_output="...",
agent=my_agent,
context=[task1, task2]
)
# With output file
task = Task(
description="...",
expected_output="...",
agent=my_agent,
output_file="output.md"
)
# With human approval
task = Task(
description="...",
expected_output="...",
agent=my_agent,
human_input=True
)
What's Next?
Now let's learn about Sequential and Parallel Processes - controlling how tasks execute in CrewAI!