Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 10 additions & 6 deletions examples/bedrock/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,21 +6,25 @@ This example demonstrates how to use LaunchDarkly's AI Config with the AWS Bedro

- Python 3.10 or higher
- [Poetry](https://python-poetry.org/) installed
- A LaunchDarkly account with an [AI Config](https://launchdarkly.com/docs/home/ai-configs/create) created
- A [LaunchDarkly](https://launchdarkly.com/) account and SDK key
- AWS credentials configured for Bedrock access

## Setup

1. Create the following config in your LaunchDarkly project. You can use a different key by setting the environment variable in your `.env`.

- [Create an AI Config](https://launchdarkly.com/docs/home/ai-configs/create) with a Bedrock model and a system message. Default key: `sample-completion-config`.

1. Create a `.env` file in this directory with the following variables:

```
LAUNCHDARKLY_SDK_KEY=your-launchdarkly-sdk-key
LAUNCHDARKLY_AI_CONFIG_KEY=sample-ai-config
LAUNCHDARKLY_AI_CONFIG_KEY=sample-completion-config
```

> `LAUNCHDARKLY_AI_CONFIG_KEY` defaults to `sample-ai-config` if not set.
> `LAUNCHDARKLY_AI_CONFIG_KEY` defaults to `sample-completion-config` if not set.

2. Ensure your AWS credentials can be [auto-detected by the `boto3` library](https://boto3.amazonaws.com/v1/documentation/api/latest/guide/credentials.html). You can set them in your `.env` file:
1. Ensure your AWS credentials can be [auto-detected by the `boto3` library](https://boto3.amazonaws.com/v1/documentation/api/latest/guide/credentials.html). You can set them in your `.env` file:

```
AWS_ACCESS_KEY_ID=your-access-key-id
Expand All @@ -30,7 +34,7 @@ This example demonstrates how to use LaunchDarkly's AI Config with the AWS Bedro

Other options include role providers or shared credential files.

3. Install the required dependencies:
1. Install the required dependencies:

```bash
poetry install
Expand All @@ -39,5 +43,5 @@ This example demonstrates how to use LaunchDarkly's AI Config with the AWS Bedro
## Run

```bash
poetry run bedrock-example
poetry run bedrock
```
59 changes: 47 additions & 12 deletions examples/bedrock/bedrock_example.py
Original file line number Diff line number Diff line change
@@ -1,20 +1,45 @@
import os
import logging
from dotenv import load_dotenv
import ldclient
from ldclient import Context
from ldclient.config import Config
from ldai import LDAIClient
from ldai.tracker import TokenUsage
from ldai.providers import LDAIMetrics
import boto3

load_dotenv()

logging.basicConfig()
logging.getLogger('ldclient').setLevel(logging.WARNING)

client = boto3.client("bedrock-runtime", region_name=os.getenv('AWS_DEFAULT_REGION', 'us-east-1'))


def get_bedrock_metrics(response):
"""Extract metrics from a Bedrock converse response."""
status_code = response.get("ResponseMetadata", {}).get("HTTPStatusCode", 0)
success = status_code == 200

usage = None
if response.get("usage"):
u = response["usage"]
usage = TokenUsage(
total=u.get("totalTokens", 0),
input=u.get("inputTokens", 0),
output=u.get("outputTokens", 0),
)

duration_ms = response.get("metrics", {}).get("latencyMs")

return LDAIMetrics(success=success, usage=usage, duration_ms=duration_ms)

# Set sdk_key to your LaunchDarkly SDK key.
sdk_key = os.getenv('LAUNCHDARKLY_SDK_KEY')

# Set config_key to the AI Config key you want to evaluate.
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-ai-config')
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-completion-config')

def main():
if not sdk_key:
Expand Down Expand Up @@ -69,25 +94,35 @@ def main():
chat_messages = [{'role': msg.role, 'content': [{'text': msg.content}]} for msg in config_value.messages if msg.role != 'system']
system_messages = [{'text': msg.content} for msg in config_value.messages if msg.role == 'system']

# Add the user input to the conversation
USER_INPUT = "What can you help me with?"
print("User Input:\n", USER_INPUT)
chat_messages.append({'role': 'user', 'content': [{'text': USER_INPUT}]})
SAMPLE_QUESTION = "What can you help me with?"
chat_messages.append({'role': 'user', 'content': [{'text': SAMPLE_QUESTION}]})

converse = tracker.track_bedrock_converse_metrics(
client.converse(
print(f'\nSending sample question to {config_value.model.name}: "{SAMPLE_QUESTION}"')
print("Waiting for response...")

converse = tracker.track_metrics_of(
get_bedrock_metrics,
lambda: client.converse(
modelId=config_value.model.name,
messages=chat_messages,
system=system_messages,
)
),
)

# Append the AI response to the conversation history
chat_messages.append(converse["output"]["message"])
print("AI Response:\n", converse["output"]["message"]["content"][0]["text"])

# Continue the conversation by adding user input to the messages list and invoking the LLM again.
print("Success.")
print(f"\nModel response:\n{converse['output']['message']['content'][0]['text']}")

summary = tracker.get_summary()
print("\nDone! The AI config was evaluated and the following metrics were tracked:")
print(f" Duration: {summary.duration_ms}ms")
print(f" Success: {summary.success}")
if summary.usage:
print(f" Input tokens: {summary.usage.input}")
print(f" Output tokens: {summary.usage.output}")
print(f" Total tokens: {summary.usage.total}")
if summary.tool_calls:
print(f" Tool calls: {', '.join(summary.tool_calls)}")

# Flush pending events and close the client.
ldclient.get().flush()
Expand Down
4 changes: 2 additions & 2 deletions examples/bedrock/pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,12 @@ readme = "README.md"
packages = [{include = "bedrock_example.py"}]

[tool.poetry.scripts]
bedrock-example = "bedrock_example:main"
bedrock = "bedrock_example:main"

[tool.poetry.dependencies]
python = "^3.10"
python-dotenv = ">=1.0.0"
launchdarkly-server-sdk-ai = "^0.18.0"
launchdarkly-server-sdk-ai = ">=0.19.0"
boto3 = ">=0.2.0"

[build-system]
Expand Down
14 changes: 8 additions & 6 deletions examples/chat_observability/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,29 +13,31 @@ View your data in the LaunchDarkly dashboard under **Observability** tabs.

- Python 3.10 or higher
- [Poetry](https://python-poetry.org/) installed
- A LaunchDarkly account with an [AI Config](https://launchdarkly.com/docs/home/ai-configs/create) created
- A [LaunchDarkly](https://launchdarkly.com/) account and SDK key
- An API key for your AI provider (e.g., OpenAI)

## Setup

1. Create the following config in your LaunchDarkly project. You can use a different key by setting the environment variable in your `.env`.

- [Create an AI Config](https://launchdarkly.com/docs/home/ai-configs/create) with a model and a system message. Default key: `sample-completion-config`.

1. Create a `.env` file in this directory with the following variables:

```
LAUNCHDARKLY_SDK_KEY=your-launchdarkly-sdk-key
LAUNCHDARKLY_AI_CONFIG_KEY=sample-ai-config
LAUNCHDARKLY_AI_CONFIG_KEY=sample-completion-config
OPENAI_API_KEY=your-openai-api-key
```

> `LAUNCHDARKLY_AI_CONFIG_KEY` defaults to `sample-ai-config` if not set.

Optionally, set service identification:

```
SERVICE_NAME=my-ai-service
SERVICE_VERSION=1.0.0
```

2. Install the required dependencies:
1. Install the required dependencies:

```bash
poetry install
Expand All @@ -44,5 +46,5 @@ View your data in the LaunchDarkly dashboard under **Observability** tabs.
## Run

```bash
poetry run chat-observability-example
poetry run chat
```
38 changes: 21 additions & 17 deletions examples/chat_observability/chat_observability_example.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import os
import logging
from dotenv import load_dotenv
import asyncio
import logging
import ldclient
from ldclient import Context
from ldclient.config import Config
Expand All @@ -10,13 +10,15 @@

load_dotenv()

logging.basicConfig()
logging.getLogger('ldclient').setLevel(logging.WARNING)
logging.getLogger('httpx').setLevel(logging.WARNING)

# Set sdk_key to your LaunchDarkly SDK key.
sdk_key = os.getenv('LAUNCHDARKLY_SDK_KEY')

# Set config_key to the AI Config key you want to evaluate.
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-ai-config')
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-completion-config')

# Service configuration for observability
service_name = os.getenv('SERVICE_NAME', 'hello-python-ai-observability')
Expand Down Expand Up @@ -85,27 +87,29 @@ async def async_main():
print(f"*** Failed to create chat for key: {ai_config_key}")
return

user_input_1 = "What is feature flagging in 2 sentences?"
print("User Input:", user_input_1)

response_1 = await chat.invoke(user_input_1)
print("Chat Response:", response_1.message.content)
sample_question_1 = "What is feature flagging in 2 sentences?"
print(f'\nSending sample question: "{sample_question_1}"')
print("Waiting for response...")

response_1 = await chat.run(sample_question_1)
print(f"\nModel response:\n{response_1.content}")

user_input_2 = "Give me a specific use case example."
print("\nUser Input:", user_input_2)
sample_question_2 = "Give me a specific use case example."
print(f'\nSending follow-up question: "{sample_question_2}"')
print("Waiting for response...")

response_2 = await chat.invoke(user_input_2)
print("Chat Response:", response_2.message.content)
response_2 = await chat.run(sample_question_2)
print(f"\nModel response:\n{response_2.content}")

# Judge evaluations run asynchronously. Await them (e.g. with asyncio.gather) so they
# Judge evaluations run asynchronously. Await them so they
# complete before the process or request ends—even if you don't need to log or use
# the results.
if response_1.evaluations:
await asyncio.gather(*response_1.evaluations)
if response_2.evaluations:
await asyncio.gather(*response_2.evaluations)
if response_1.evaluations is not None:
await response_1.evaluations
if response_2.evaluations is not None:
await response_2.evaluations

print("\nSuccess.")
print("\nDone! The AI config was evaluated with observability enabled.")

except Exception as err:
print("Error:", err)
Expand Down
8 changes: 4 additions & 4 deletions examples/chat_observability/pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,15 @@ readme = "README.md"
packages = [{include = "chat_observability_example.py"}]

[tool.poetry.scripts]
chat-observability-example = "chat_observability_example:main"
chat = "chat_observability_example:main"

[tool.poetry.dependencies]
python = "^3.10"
python-dotenv = ">=1.0.0"
launchdarkly-server-sdk-ai = "^0.18.0"
launchdarkly-server-sdk-ai = ">=0.19.0"
launchdarkly-observability = ">=0.1.0"
launchdarkly-server-sdk-ai-openai = ">=0.4.0"
launchdarkly-server-sdk-ai-langchain = ">=0.5.0"
launchdarkly-server-sdk-ai-openai = ">=0.5.0"
launchdarkly-server-sdk-ai-langchain = ">=0.6.0"
openai = ">=0.2.0"

[build-system]
Expand Down
14 changes: 8 additions & 6 deletions examples/gemini/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,22 +6,24 @@ This example demonstrates how to use LaunchDarkly's AI Config with the Google Ge

- Python 3.10 or higher
- [Poetry](https://python-poetry.org/) installed
- A LaunchDarkly account with an [AI Config](https://launchdarkly.com/docs/home/ai-configs/create) created
- A [LaunchDarkly](https://launchdarkly.com/) account and SDK key
- A [Google API key](https://aistudio.google.com/apikey)

## Setup

1. Create the following config in your LaunchDarkly project. You can use a different key by setting the environment variable in your `.env`.

- [Create an AI Config](https://launchdarkly.com/docs/home/ai-configs/create) with a Gemini model (e.g. `gemini-2.0-flash`) and a system message. Default key: `sample-completion-config`.

1. Create a `.env` file in this directory with the following variables:

```
LAUNCHDARKLY_SDK_KEY=your-launchdarkly-sdk-key
LAUNCHDARKLY_AI_CONFIG_KEY=sample-ai-config
LAUNCHDARKLY_AI_CONFIG_KEY=sample-completion-config
GOOGLE_API_KEY=your-google-api-key
```

> `LAUNCHDARKLY_AI_CONFIG_KEY` defaults to `sample-ai-config` if not set.

2. Install the required dependencies:
1. Install the required dependencies:

```bash
poetry install
Expand All @@ -30,5 +32,5 @@ This example demonstrates how to use LaunchDarkly's AI Config with the Google Ge
## Run

```bash
poetry run gemini-example
poetry run gemini
```
31 changes: 22 additions & 9 deletions examples/gemini/gemini_example.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import os
import logging
from dotenv import load_dotenv
import ldclient
from ldclient import Context
Expand All @@ -11,11 +12,14 @@

load_dotenv()

logging.basicConfig()
logging.getLogger('ldclient').setLevel(logging.WARNING)

# Set sdk_key to your LaunchDarkly SDK key.
sdk_key = os.getenv('LAUNCHDARKLY_SDK_KEY')

# Set config_key to the AI Config key you want to evaluate.
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-ai-config')
ai_config_key = os.getenv('LAUNCHDARKLY_AI_CONFIG_KEY', 'sample-completion-config')

# Set Google API key
google_api_key = os.getenv('GOOGLE_API_KEY')
Expand Down Expand Up @@ -143,12 +147,13 @@ def main():
# Convert LaunchDarkly messages to Google AI format using the helper function
system_instruction, messages = map_to_google_ai_messages(config_value.messages or [])

# Add the user input to the conversation
USER_INPUT = "What can you help me with?"
print("User Input:\n", USER_INPUT)
user_message = types.Content(role="user", parts=[types.Part(text=USER_INPUT)])
SAMPLE_QUESTION = "What can you help me with?"
user_message = types.Content(role="user", parts=[types.Part(text=SAMPLE_QUESTION)])
messages.append(user_message)

print(f'\nSending sample question to {config_value.model.name}: "{SAMPLE_QUESTION}"')
print("Waiting for response...")

completion = track_genai_metrics(tracker, lambda: client.models.generate_content(
model=config_value.model.name,
contents=messages,
Expand All @@ -158,13 +163,21 @@ def main():
))
ai_response = completion.text

# Add the AI response to the conversation history
ai_message = types.Content(role="model", parts=[types.Part(text=ai_response)])
messages.append(ai_message)
print("AI Response:\n", ai_response)

# Continue the conversation by adding user input to the messages list and invoking the LLM again.
print("Success.")
print(f"\nModel response:\n{ai_response}")

summary = tracker.get_summary()
print("\nDone! The AI config was evaluated and the following metrics were tracked:")
print(f" Duration: {summary.duration_ms}ms")
print(f" Success: {summary.success}")
if summary.usage:
print(f" Input tokens: {summary.usage.input}")
print(f" Output tokens: {summary.usage.output}")
print(f" Total tokens: {summary.usage.total}")
if summary.tool_calls:
print(f" Tool calls: {', '.join(summary.tool_calls)}")

# Flush pending events and close the client.
ldclient.get().flush()
Expand Down
Loading
Loading