---
title: "Manage Prompt with the SDK"
---

import Image from "@theme/IdealImage";

In this guide, we'll explore all actions performed through the SDK: creating variants, committing changes, deploying changes, and fetching configurations. For a simpler introduction, please refer to the [prompt mangement tutorial](/tutorials/sdk/manage-prompts-with-SDK).

Before starting, we recommend to get acquainted with how versioning works in Agenta. You can find more details on the [concepts page](/concepts/concepts), or read the quick summary below.

:::info Versioning in Agenta

{" "}

<Image
  style={{ display: "block", margin: "16px 0px 16px 0px" }}
  img={require("/images/prompt_management/taxonomy-concepts.png")}
  alt="Taxonomy of concepts in Agenta"
  loading="lazy"
/>
Agenta follows a structure similar to **git** for prompt versioning. Instead of a
single commit history, you can create multiple branches—called **variants**. Each
variant represents a distinct approach or solution you're exploring.

To move from experimentation to deployment, Agenta uses **environments** like
**development**, **staging**, and **production**. You can deploy specific versions of your **variants**
to these **environments**, controlling what gets tested and what goes live.

The workflow of deploying something to production is therefore as follows:

1. (optionally) Create a new **variant** (branch)
2. Commit a change to that **variant**
3. Deploy that **commit** (**variant**/**version**) to an **environment**

:::

## Setup

Before using the SDK, you need to initialize it using the `ag.init()` method.

```python
import os
import agenta as ag


# Initialize the SDK with your API key
os.environ["AGENTA_API_KEY"] = "xxx" # Only needs setting in oss
os.environ["AGENTA_HOST"] = "https://cloud.agenta.ai" # default value no need setting explicitly

ag.init()
```

## Creating a new prompt

Each prompt in agenta is a unique application. Currently creating a prompt is only available in the web UI. To create a new prompt, just click on create a new prompt and select whether it's a chat or completion prompt in the web UI.

## Committing changes

### Creating a New Variant

To create a new variant, use the `VariantManager.create` method.

```python

from agenta import Prompt

# Prompt is a pydantic BaseModel we created for common prompt settings. 
# To add more fields or validations, create your own custom model.
my_prompt = Prompt(
    temperature=0.7,
    model="gpt-3.5-turbo",
    max_tokens=150,
    prompt_system="You are an assistant that provides concise answers",
    prompt_user="Explain {topic} in simple terms",
    top_p=1.0,
    frequency_penalty=0.0,
    presence_penalty=0.0
)

# Create a new variant
variant = ag.VariantManager.create(
    parameters=my_prompt.model_dump(),
    app_slug="my-app-slug",
    # app_id="my-app-id",  # you can also use `app_id`
    variant_slug="my-variant-slug",
)

print("Created variant:")
print(variant)

# Create a new version asynchronously (optional)
# async def create_variant():
#     variant = await ag.VariantManager.acreate(
#         parameters=my_prompt.model_dump(),
#         app_slug="my-app-slug",
#         app_id="my-app-id",  # you can also use `app_id`
#         variant_slug="my-variant-slug",
#     )

#     print("Created variant (async):")
#     print(variant)
```

This command will create a new variant and initialize it with the first commit containing the parameters provided

- **Parameters:**
  - `app_slug`: The slug of your application.
  - `variant_slug`: The slug of the new variant.
  - `parameters`: A dictionary containing the initial configuration parameters.

**Note:** If a variant with the same `slug` and `version` already exists, the SDK will raise an exception.

**Sample Output:**

```python
Created variant:
{
    'parameters': {
        'temperature': 0.7,
        'model': 'gpt-3.5-turbo',
        'max_tokens': 150,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    },
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'new-variant-id',
    'variant_slug': 'my-variant-slug',
    'variant_version': 1,
    'committed_at': 'current-datetime',
    'committed_by': 'my-email-address',
    'committed_by_id': 'my-user-id',
}
```

### Committing Changes to a Variant

To save changes to a variant (creating a new version), use the `VariantManager.commit` method with explicit parameters.

```python
my_prompt2 = Prompt(
    temperature=1.0,
    model="gpt-4",
    max_tokens=150,
    prompt_system="You are an assistant that provides concise answers",
    prompt_user="Explain {topic} in simple terms",
    top_p=1.0,
    frequency_penalty=0.0,
    presence_penalty=0.0
)

# Commit the new version
variant = ag.VariantManager.commit(
    parameters=my_prompt2.model_dump(),
    app_slug="my-app-slug",
    variant_slug="my-variant-slug",
)

print("Committed new version of variant:")
print(variant)

# Commit the new version asynchronously (optional)
# async def commit_variant():
#     variant = await ag.VariantManager.acommit(
#         parameters=my_prompt2.model_dump(),
#         app_slug="my-app-slug",
#         variant_slug="my-variant-slug",
#     )

#     print("Committed new version of variant (async):")
#     print(variant)
```

:::info Immutability
Each commit creates a new version of the variant. Versions are immutable once created.
:::

**Sample Output:**

```python
Committed new version of variant:
{
    'parameters': {
        'temperature': 1.0,
        'model': 'gpt-4',
        'max_tokens': 150,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    }
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'updated-variant-id',
    'variant_slug': 'my-variant-slug',
    'variant_version': 2,
    'committed_at': 'current-datetime',
    'committed_by': 'my-email-address',
    'committed_by_id': 'my-user-id',
}
```

## Deploying to an Environment

To deploy a variant to an environment, use the `DeploymentManager.deploy` method with the variant reference and `environment_slug`: The slug of the environment (`development`, `staging`, or `production`).

```python
# Deploy the variant to the staging environment
deployment = ag.DeploymentManager.deploy(
    app_slug="my-app-slug",
    # app_id="my-app-id",  # you can also use `app_id`
    variant_slug="my-variant-slug",
    variant_version=None,  # Optional: If not provided, deploys the latest version
    environment_slug="staging"
)

print("Deployed variant to environment:")
print(deployment)

# Deploy the variant to the staging environment asynchronously (optional)
# async def deploy_variant():
#     deployment = await ag.DeploymentManager.adeploy(
#         app_slug="my-app-slug",
#         # app_id="my-app-id",  # you can also use `app_id`
#         variant_slug="my-variant-slug",
#         variant_version=None,  # Optional: If not provided, deploys the latest version
#         environment_slug="staging"
#     )

#     print("Deployed variant to environment (async):")
#     print(deployment)
```

:::warning

- Deploying a variant without specifying a `variant_version` deploys the latest version.
- Only predefined environments with slugs `development`, `staging`, and `production` are currently supported.
  :::

**Sample Output:**

```python
Deployed variant to environment:
{
    'parameters': {
        'temperature': 0.7,
        'model': 'gpt-3.5-turbo',
        'max_tokens': 150,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    },
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'new-variant-id',
    'variant_slug': 'my-variant-slug',
    'variant_version': 1,
    'environment_id': 'staging-enviroment-id',
    'environment_slug': 'staging',
    'environment_version': 1,
    'deployed_at': 'current-datetime',
    'deployed_by': 'my-email-address',
    'deployed_by_id': 'my-user-id',
}
```

## Fetching Configurations

You can fetch the configurations from a variant reference (`app_slug`, `variant_slug`, `variant_version`) or an environment reference (`app_slug`, `environment_slug`). The default behavior when fetching is to fetch the latest configuration from the `production` environment. If you don't provide a `_version` parameter but only a `variant_slug` or an `environment_slug`, the SDK will fetch the latest version of the variant from the specified **environment/variant**.

### Default Behavior when fetching

If you don't provide either `variant` or `environment` identifiers, the SDK fetches the latest configuration deployed to the `production` environment.

```python
# Fetch configuration from the latest version in production (default)
config = ag.ConfigManager.get_from_registry(
    app_slug="my-app-slug"
    # app_id="my-app-id",  # you can also use `app_id`
)

print("Fetched configuration from production:")
print(config)
```

### Fetching by Variant Reference

```python
# Fetch configuration by variant
config = ag.ConfigManager.get_from_registry(
    app_slug="my-app-slug",
    # app_id="my-app-id",  # you can also use `app_id`
    variant_slug="my-variant-slug",
    variant_version=2  # Optional: If not provided, fetches the latest version
)

print("Fetched configuration:")
print(config)
```

**Sample Output:**

```python
Fetched configuration:
{
    'temperature': 1.0,
    'model': 'gpt-4',
    'max_tokens': 150,
    'prompt_system': 'You are an assistant that provides concise answers.',
    'prompt_user': 'Explain {topic} in simple terms.',
    'top_p': 1.0,
    'frequency_penalty': 0.0,
    'presence_penalty': 0.0
}
```

### Fetching by Environment Reference

```python
# Fetch the latest configuration from the staging environment
config = ag.ConfigManager.get_from_registry(
    app_slug="my-app",
    environment_slug="staging"
    environment_version=1  # Optional: If not provided, fetches the latest version
)

print("Fetched configuration from staging:")
print(config)
```

**Sample Output:**

```python
Fetched configuration from staging:
{
    'temperature': 0.7,
    'model': 'gpt-3.5-turbo',
    'max_tokens': 150,
    'prompt_system': 'You are an assistant that provides concise answers.',
    'prompt_user': 'Explain {topic} in simple terms.',
    'top_p': 1.0,
    'frequency_penalty': 0.0,
    'presence_penalty': 0.0
}
```

## Deleting a Variant

To delete a variant, use the `VariantManager.delete` method.

```python
# Delete a variant
ag.VariantManager.delete(
    app_slug="my-app",
    # app_id="my-app-id",  # you can also use `app_id`
    variant_slug="obsolete-variant"
)

# Delete a variant asynchronously (optional)
# async def delete_variant():
#     versions = await ag.VariantManager.adelete(
#         app_slug="my-app",
#         # app_id="my-app-id",  # you can also use `app_id`
#         variant_slug="obsolete-variant",
#     )

print("Variant deleted successfully.")
```

:::warning

- Deleting a variant removes all versions of the variant. This action is irreversible.
- Attempting to delete a variant that is deployed to an environment will fail.
  :::

## Listing All Variants

To list all variants of an application, use the `VariantManager.list` method.

```python
# List all variants (syncrhonously)
variants = ag.VariantManager.list(
    app_slug="my-app"
    # app_id="my-app-id",  # you can also use `app_id`
)

print("List of variants:")
for variant in variants:
    print(variant)

# List all variants asynchronously (optional)
# async def list_variants():
#     variants = await ag.VariantManager.alist(
#         app_slug="my-app"
#         # app_id="my-app-id",  # you can also use `app_id`
#     )

#     print("List of variants (async):")
#     for variant in variants:
#         print(variant)
```

**Sample Output:**

```python
List of variants:
{
    'parameters': {
        'temperature': 1.0,
        'model': 'gpt-4',
        'max_tokens': 150,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    }
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'updated-variant-id',
    'variant_slug': 'my-variant-slug',
    'variant_version': 2,
    'committed_at': 'current-datetime',
    'committed_by': 'my-email-address',
    'committed_by_id': 'my-user-id',
}
{
    'parameters': {
        'temperature': 0.5,
        'model': 'gpt-3.5-turbo',
        'max_tokens': 100,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    }
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'another-variant-id',
    'variant_slug': 'another-variant-slug',
    'variant_version': 1,
    'committed_at': 'another-datetime',
    'committed_by': 'another-email-address',
    'committed_by_id': 'another-user-id',
}
```

## Fetching a Variant's history

To list all versions for a variant of an application, use the `VariantManager.list` method.

```python
# List all variant versions/history (synchronously)
versions = ag.VariantManager.history(
    variant_slug="variant-slug",
    app_slug="my-app"
    # app_id="my-app-id",  # you can also use `app_id`
)

print("History of variant:")
for version in versions:
    print(version)

# List all variant versions/history asynchronously (optional)
# async def fetch_variant_history():
#     versions = await ag.VariantManager.ahistory(
#         variant_slug="variant-slug",
#         app_slug="my-app"
#         # app_id="my-app-id",  # you can also use `app_id`
#     )

#     print("History of variant:")
#     for version in versions:
#         print(version)
```

**Sample Output:**

```python
History of variants:
{
    'parameters': {
        'temperature': 1.0,
        'model': 'gpt-4',
        'max_tokens': 150,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    }
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'updated-variant-id',
    'variant_slug': 'my-variant-slug',
    'variant_version': 2,
    'committed_at': 'current-datetime',
    'committed_by': 'my-email-address',
    'committed_by_id': 'my-user-id',
}
{
    'parameters': {
        'temperature': 0.5,
        'model': 'gpt-3.5-turbo',
        'max_tokens': 100,
        'prompt_system': 'You are an assistant that provides concise answers.',
        'prompt_user': 'Explain {topic} in simple terms.',
        'top_p': 1.0,
        'frequency_penalty': 0.0,
        'presence_penalty': 0.0
    }
    'app_id': 'my-app-id',
    'app_slug': 'my-app-slug',
    'variant_id': 'another-variant-id',
    'variant_slug': 'another-variant-slug',
    'variant_version': 1,
    'committed_at': 'another-datetime',
    'committed_by': 'another-email-address',
    'committed_by_id': 'another-user-id',
}
```

## Asynchronous Operations

If your application uses asynchronous programming, you can use the async versions of the methods (see the `a` prefix in the function name).

```python
# Asynchronous fetching of configuration
config = await ag.ConfigManager.aget_from_registry(
    app_slug="my-app",
    # app_id="my-app-id",  # you can also use `app_id`
    variant_slug="my-variant-slug",
    variant_version=2
)

print("Fetched configuration asynchronously:")
print(config)
```
