Signature: A Task Contract
A Signature in DSPy is a specification that defines the inputs and outputs of a language model task, similar to a function signature in programming.
๐ก Think of It Like a Function Signature
In Python, a function signature tells you what goes in and what comes out:
# Python function signature
def add_numbers(a: int, b: int) -> int:
"""Add two numbers and return the result."""
return a + b
Similarly, a DSPy signature defines the contract for an LM task:
# DSPy signature
class QuestionAnswer(dspy.Signature):
"""Answer questions accurately."""
question: str = dspy.InputField() # What goes in
answer: str = dspy.OutputField() # What comes out
Key Insight: You don't write the implementation (the prompt)โDSPy generates it for you based on your signature!
๐งฉ Components of a Signature
Every signature has three essential parts:
Docstring (Task Description)
Describes what the task does. This becomes part of the prompt that DSPy generates.
class Summarize(dspy.Signature):
"""Summarize the given text in 2-3 sentences.""" # โ Docstring
...
Input Fields
Define what data the task receives. Use dspy.InputField().
class Summarize(dspy.Signature):
"""Summarize the given text."""
text: str = dspy.InputField() # โ Input field
...
Output Fields
Define what the task produces. Use dspy.OutputField().
class Summarize(dspy.Signature):
"""Summarize the given text."""
text: str = dspy.InputField()
summary: str = dspy.OutputField() # โ Output field
๐ A Complete Example
Here's a signature for sentiment analysis with all components:
import dspy
class SentimentAnalysis(dspy.Signature):
"""Analyze the sentiment of the given text and classify it."""
# Input: The text to analyze
text: str = dspy.InputField(
desc="The text to analyze for sentiment"
)
# Outputs: Classification and confidence
sentiment: str = dspy.OutputField(
desc="The sentiment: 'positive', 'negative', or 'neutral'"
)
confidence: str = dspy.OutputField(
desc="Confidence level: 'high', 'medium', or 'low'"
)
Using this signature:
# Create a predictor from the signature
analyzer = dspy.Predict(SentimentAnalysis)
# Use it
result = analyzer(text="I absolutely love this product!")
print(f"Sentiment: {result.sentiment}") # positive
print(f"Confidence: {result.confidence}") # high
๐ฎ Why Signatures Work
When you use a signature, DSPy automatically:
Generates a Prompt
DSPy creates an optimized prompt from your docstring, field names, and descriptions.
Formats Your Input
Your input data is properly formatted and inserted into the prompt.
Calls the LM
The formatted prompt is sent to your configured language model.
Parses the Output
The LM's response is parsed and returned as a structured object with your named output fields.
The magic: You focus on what you want, and DSPy handles how to get it!
๐ Two Ways to Define Signatures
DSPy offers two syntax options:
Inline Signatures
# Quick, simple syntax
qa = dspy.Predict("question -> answer")
# With multiple fields
summarize = dspy.Predict(
"document, max_length -> summary"
)
Class-Based Signatures
# Full-featured syntax
class QA(dspy.Signature):
"""Answer questions accurately."""
question: str = dspy.InputField()
answer: str = dspy.OutputField(
desc="concise answer"
)
We'll cover both in detail in the following sections.
๐จ Common Signature Patterns
Here are signatures for common NLP tasks:
# Question Answering
class QA(dspy.Signature):
"""Answer the question based on the context."""
context: str = dspy.InputField()
question: str = dspy.InputField()
answer: str = dspy.OutputField()
# Summarization
class Summarize(dspy.Signature):
"""Create a concise summary."""
document: str = dspy.InputField()
summary: str = dspy.OutputField()
# Classification
class Classify(dspy.Signature):
"""Classify the text into a category."""
text: str = dspy.InputField()
category: str = dspy.OutputField()
# Translation
class Translate(dspy.Signature):
"""Translate text to the target language."""
text: str = dspy.InputField()
target_language: str = dspy.InputField()
translation: str = dspy.OutputField()
# Entity Extraction
class ExtractEntities(dspy.Signature):
"""Extract named entities from text."""
text: str = dspy.InputField()
entities: list[str] = dspy.OutputField()