Custom Workflows SDK
Overview
The Custom Workflows SDK allows you to define and expose specific stages of your LLM workflows as API endpoints. By decorating your functions with @ag.route and @ag.entrypoint, you can create custom routes that integrate with the Agenta for playground interactions, evaluations, and deployments.
Workflows can be deployed to Agenta using the CLI.
Decorators
@ag.route Decorator
The @ag.route decorator is used to expose specific stages of a workflow (e.g., embedding, retrieval, summarization) as independent API endpoints.
Syntax
@ag.route(path, config_schema)
def function_name(parameters):
# Function implementation
Parameters
path(str): The URL path for the route. Must be a valid HTTP path.config_schema(Type[BaseModel]): A Pydantic model defining the configuration schema for the route.
Configuration schemas are defined using Pydantic models. Each field must have a default value.
Example
from pydantic import BaseModel
import agenta as ag
class MyConfig(BaseModel):
prompt: str
@ag.route("/", config_schema=MyConfig)
def generate_text(input_text: str):
config = ag.ConfigManager.get_from_route(schema=MyConfig)
# Function implementation
return output_text
Endpoints Created
When you use the @ag.route decorator, the following endpoints are created:
-
Playground Endpoints:
-
POST /playground/run/{route} -
This endpoint is intended for use within the Agenta playground. It takes as input the configuration parameters.
-
-
Deployed Endpoints:
-
POST /run/{route} -
This endpoint is intended for production or deployed environments. It takes as input the deployment slug.
-
@ag.entrypoint Decorator
The @ag.entrypoint decorator has the same inputs and outputs as @ag.route("/", config_schema).
However it creates the following endpoints:
-
Playground Endpoints:
-
POST /generate -
POST /playground/run
-
-
Deployed Endpoints:
-
POST /generate_deployed -
POST /run
-
Configuration Schema
When using @ag.route or @ag.entrypoint, you define a configuration schema using a Pydantic BaseModel. This schema specifies the configuration parameters that your function accepts and how they are represented in the Agenta playground.
Accepted Types
The following types are accepted in the configuration schema:
- String (
str) - Integer (
int) - Float (
float) - Boolean (
bool) - Enumerations (using
Annotatedwith choices) - Grouped Enumerations
Defining Fields with Constraints and Defaults
Each field in the configuration schema must have a default value. This default value is specified using Field(default=...) from Pydantic. The default value will be shown in the playground when the application is first run.
You can specify constraints such as minimum and maximum values using Field parameters like ge (greater than or equal to), le (less than or equal to), gt (greater than), and lt (less than).
Example with Constraints and Defaults
from pydantic import BaseModel, Field
import agenta as ag
class MyConfig(BaseModel):
temperature: float = Field(default=1.0, ge=0.0, le=2.0)
max_tokens: int = Field(default=500, ge=1, le=1000)
use_cache: bool = Field(default=False)
In this example:
temperatureis a float field with a default value of1.0, and must be between0.0and2.0inclusive.max_tokensis an integer field with a default value of500, and must be between1and1000inclusive.use_cacheis a boolean field with a default value ofFalse.
Defining Choices for Enumerations
For fields that should present a set of choices (like a dropdown menu), use Annotated along with ag.MultipleChoice or ag.GroupedMultipleChoice to specify the choices. The default value is still specified using Field(default=...).
Example with ag.MultipleChoice
from pydantic import BaseModel, Field
from typing import Annotated
import agenta as ag
class MyConfig(BaseModel):
language: Annotated[str, ag.MultipleChoice(choices=["English", "Spanish", "French"])] = Field(default="English")
In this example:
languageis a string field that allows selection among "English", "Spanish", or "French".- The default value is set to "English" via
Field(default="English").
Example with ag.GroupedMultipleChoice
from pydantic import BaseModel, Field
from typing import Annotated
import agenta as ag
supported_models = {
"OpenAI Models": ["gpt-3.5-turbo", "gpt-4"],
"Other Models": ["bloom", "gpt-j"]
}
class MyConfig(BaseModel):
model: Annotated[str, ag.GroupedMultipleChoice(choices=supported_models)] = Field(default="gpt-3.5-turbo")
In this example:
modelis a string field with grouped choices specified insupported_models.- The default value is set to "gpt-3.5-turbo".
UI Representation
The fields in the configuration schema are represented in the Agenta playground as follows:
- String (
str):- Shown as text areas where users can input text.
- Integer (
int) and Float (float):- Shown as sliders.
- The
minimumandmaximumvalues for the sliders are determined by thege,le,gt, andltconstraints specified inField.
- Boolean (
bool):- Shown as checkboxes.
- Enumerations:
- Shown as dropdown menus.
- Choices are defined using
Annotatedwithag.MultipleChoiceorag.GroupedMultipleChoice, and the default is specified viaField.
Complete Example
from pydantic import BaseModel, Field
from typing import Annotated
import agenta as ag
supported_llm_models = {
"Mistral AI": [
"mistral/mistral-tiny",
"mistral/mistral-small",
"mistral/mistral-medium",
"mistral/mistral-large-latest",
],
"OpenAI": [
"gpt-3.5-turbo-1106",
"gpt-3.5-turbo",
"gpt-4",
"gpt-4o",
"gpt-4o-mini",
"gpt-4-1106-preview",
],
}
class MyConfig(BaseModel):
temperature: float = Field(default=1.0, ge=0.0, le=2.0)
model: Annotated[str, ag.GroupedMultipleChoice(choices=supported_llm_models)] = Field(default="gpt-3.5-turbo")
max_tokens: int = Field(default=-1, ge=-1, le=4000)
prompt_system: str = Field(default="System prompt text")
prompt_user: str = Field(default="User prompt text")
top_p: float = Field(default=1.0)
frequence_penalty: float = Field(default=0.0, ge=-2.0, le=2.0)
presence_penalty: float = Field(default=0.0, ge=-2.0, le=2.0)
force_json: bool = Field(default=False)
In this example:
- Various field types are used, including strings, floats, integers, and booleans.
- Constraints are specified using
Fieldparameters likegeandle. - The
modelfield usesAnnotatedwithag.GroupedMultipleChoiceto define grouped choices. - Default values are specified using
Field(default=...).
Importing Supported Models
You can import predefined supported models from Agenta's assets:
from agenta.sdk.assets import supported_llm_models
Configuration Management
ag.ConfigManager.get_from_route()
Retrieves the configuration from the route context and returns a configuration object.
Syntax
config = ag.ConfigManager.get_from_route(schema=MyConfig)
Parameters
schema(Type[BaseModel], optional): A Pydantic model class that defines the structure of the configuration.
Returns
- An instance of the specified
schemapopulated with the configuration data. - If no
schemais provided, returns a dictionary of configuration parameters.
Description
- Checks the route context for configuration information.
- If configuration is present in the context, it uses that; otherwise, it attempts to fetch the configuration from the registry based on the provided application, variant, or environment identifiers.
Example
from pydantic import BaseModel
import agenta as ag
class MyConfig(BaseModel):
prompt: str
@ag.route("/", config_schema=MyConfig)
def generate_text(input_text: str):
config = ag.ConfigManager.get_from_route(schema=MyConfig)
# Use config.prompt in your function
return output_text
Context Managers
routing_context_manager
Manages the routing context for a request, allowing configuration, application, variant, and environment information to be set and accessed within the context.
Syntax
with routing_context_manager(config=config_dict):
# Code block
Parameters
config(Optional[Dict[str, Any]]): Configuration parameters.application(Optional[Dict[str, Any]]): Application information.variant(Optional[Dict[str, Any]]): Variant information.environment(Optional[Dict[str, Any]]): Environment information.