Skip to content

Commit af222e6

Browse files
Rust: add invoke-agent example in bedrock-agent-runtime (#7479)
* feat: add invoke agent in bedrock-agent-runtime example --------- Co-authored-by: Tejas Ganesh Naik <tejasgn@amazon.com>
1 parent 801dd21 commit af222e6

File tree

9 files changed

+259
-5
lines changed

9 files changed

+259
-5
lines changed

.doc_gen/metadata/bedrock-agent-runtime_metadata.yaml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,14 @@ bedrock-agent-runtime_InvokeAgent:
2525
- description:
2626
snippet_tags:
2727
- bdz.abapv1.invokeagent
28+
Rust:
29+
versions:
30+
- sdk_version: 1
31+
github: rustv1/examples/bedrock-agent-runtime
32+
excerpts:
33+
- description:
34+
snippet_files:
35+
- rustv1/examples/bedrock-agent-runtime/src/bin/invoke-agent.rs
2836
services:
2937
bedrock-agent-runtime: {InvokeAgent}
3038

.github/workflows/lint-rust.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ jobs:
2727
- uses: dtolnay/rust-toolchain@stable
2828
if: steps.changed-files.outputs.any_changed == 'true'
2929
with:
30-
toolchain: "1.83.0"
30+
toolchain: "1.87.0"
3131
components: clippy, rustfmt
3232
- name: Set Environment
3333
if: steps.changed-files.outputs.any_changed == 'true'

rustv1/Dockerfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
# syntax=docker/dockerfile:1
2-
ARG MSRV=1.83.0
2+
ARG MSRV=1.87.0
33
FROM rust:$MSRV
44

55
# Update image
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
# This should be kept in sync with https://github.com/awslabs/aws-sdk-rust#supported-rust-versions-msrv
22
[toolchain]
3-
channel = "1.83.0"
3+
channel = "1.87.0"

rustv1/examples/Cargo.toml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,8 @@ members = [
99
"aurora",
1010
"auto-scaling",
1111
"autoscalingplans",
12-
"batch",
12+
"batch",
13+
"bedrock-agent-runtime",
1314
"bedrock-runtime",
1415
"cloudformation",
1516
"cloudwatch",
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
[package]
2+
name = "bedrock-agent-runtime"
3+
version = "0.1.0"
4+
edition = "2021"
5+
6+
[dependencies]
7+
aws-config = "1.6.3"
8+
aws-sdk-bedrockagentruntime = "1.98.0"
9+
aws-smithy-types = "1.3.2"
10+
mockall = "0.13.1"
11+
tokio = { version = "1.45.1", features = ["full"] }
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
# Amazon Bedrock Agents Runtime code examples for the SDK for Rust
2+
3+
## Overview
4+
5+
Shows how to use the AWS SDK for Rust to work with Amazon Bedrock Agents Runtime.
6+
7+
<!--custom.overview.start-->
8+
<!--custom.overview.end-->
9+
10+
_Amazon Bedrock Agents Runtime offers you the ability to run autonomous agents in your application._
11+
12+
## ⚠ Important
13+
14+
* Running this code might result in charges to your AWS account. For more details, see [AWS Pricing](https://aws.amazon.com/pricing/) and [Free Tier](https://aws.amazon.com/free/).
15+
* Running the tests might result in charges to your AWS account.
16+
* We recommend that you grant your code least privilege. At most, grant only the minimum permissions required to perform the task. For more information, see [Grant least privilege](https://docs.aws.amazon.com/IAM/latest/UserGuide/best-practices.html#grant-least-privilege).
17+
* This code is not tested in every AWS Region. For more information, see [AWS Regional Services](https://aws.amazon.com/about-aws/global-infrastructure/regional-product-services).
18+
19+
<!--custom.important.start-->
20+
<!--custom.important.end-->
21+
22+
## Code examples
23+
24+
### Prerequisites
25+
26+
For prerequisites, see the [README](../../README.md#Prerequisites) in the `rustv1` folder.
27+
28+
29+
<!--custom.prerequisites.start-->
30+
<!--custom.prerequisites.end-->
31+
32+
### Single actions
33+
34+
Code excerpts that show you how to call individual service functions.
35+
36+
- [InvokeAgent](src/bin/invoke-agent.rs)
37+
38+
39+
<!--custom.examples.start-->
40+
<!--custom.examples.end-->
41+
42+
## Run the examples
43+
44+
### Instructions
45+
46+
47+
<!--custom.instructions.start-->
48+
<!--custom.instructions.end-->
49+
50+
51+
52+
### Tests
53+
54+
⚠ Running tests might result in charges to your AWS account.
55+
56+
57+
To find instructions for running these tests, see the [README](../../README.md#Tests)
58+
in the `rustv1` folder.
59+
60+
61+
62+
<!--custom.tests.start-->
63+
<!--custom.tests.end-->
64+
65+
## Additional resources
66+
67+
- [Amazon Bedrock Agents Runtime User Guide](https://docs.aws.amazon.com/bedrock/latest/userguide/agents.html)
68+
- [Amazon Bedrock Agents Runtime API Reference](https://docs.aws.amazon.com/bedrock/latest/APIReference/API_Operations_Agents_for_Amazon_Bedrock_Runtime.html)
69+
- [SDK for JavaScript (v3) Amazon Bedrock Agents Runtime reference](https://crates.io/crates/aws-sdk-bedrockagentruntime)
70+
71+
<!--custom.resources.start-->
72+
<!--custom.resources.end-->
73+
74+
---
75+
76+
Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
77+
78+
SPDX-License-Identifier: Apache-2.0
79+
Lines changed: 155 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,155 @@
1+
// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2+
// SPDX-License-Identifier: Apache-2.0
3+
4+
use aws_config::{BehaviorVersion, SdkConfig};
5+
use aws_sdk_bedrockagentruntime::{
6+
self as bedrockagentruntime,
7+
types::{error::ResponseStreamError, ResponseStream},
8+
};
9+
#[allow(unused_imports)]
10+
use mockall::automock;
11+
12+
const BEDROCK_AGENT_ID: &str = "AJBHXXILZN";
13+
const BEDROCK_AGENT_ALIAS_ID: &str = "AVKP1ITZAA";
14+
const BEDROCK_AGENT_REGION: &str = "us-east-1";
15+
16+
#[cfg(not(test))]
17+
pub use EventReceiverImpl as EventReceiver;
18+
#[cfg(test)]
19+
pub use MockEventReceiverImpl as EventReceiver;
20+
21+
pub struct EventReceiverImpl {
22+
inner: aws_sdk_bedrockagentruntime::primitives::event_stream::EventReceiver<
23+
ResponseStream,
24+
ResponseStreamError,
25+
>,
26+
}
27+
28+
#[cfg_attr(test, automock)]
29+
impl EventReceiverImpl {
30+
#[allow(dead_code)]
31+
pub fn new(
32+
inner: aws_sdk_bedrockagentruntime::primitives::event_stream::EventReceiver<
33+
ResponseStream,
34+
ResponseStreamError,
35+
>,
36+
) -> Self {
37+
Self { inner }
38+
}
39+
40+
pub async fn recv(
41+
&mut self,
42+
) -> Result<
43+
Option<ResponseStream>,
44+
aws_sdk_bedrockagentruntime::error::SdkError<
45+
ResponseStreamError,
46+
aws_smithy_types::event_stream::RawMessage,
47+
>,
48+
> {
49+
self.inner.recv().await
50+
}
51+
}
52+
53+
#[tokio::main]
54+
async fn main() -> Result<(), Box<bedrockagentruntime::Error>> {
55+
let result = invoke_bedrock_agent("I need help.".to_string(), "123".to_string()).await?;
56+
println!("{}", result);
57+
Ok(())
58+
}
59+
60+
async fn invoke_bedrock_agent(
61+
prompt: String,
62+
session_id: String,
63+
) -> Result<String, bedrockagentruntime::Error> {
64+
let sdk_config: SdkConfig = aws_config::defaults(BehaviorVersion::latest())
65+
.region(BEDROCK_AGENT_REGION)
66+
.load()
67+
.await;
68+
let bedrock_client = bedrockagentruntime::Client::new(&sdk_config);
69+
70+
let command_builder = bedrock_client
71+
.invoke_agent()
72+
.agent_id(BEDROCK_AGENT_ID)
73+
.agent_alias_id(BEDROCK_AGENT_ALIAS_ID)
74+
.session_id(session_id)
75+
.input_text(prompt);
76+
77+
let response = command_builder.send().await?;
78+
79+
let response_stream = response.completion;
80+
81+
let event_receiver = EventReceiver::new(response_stream);
82+
83+
process_agent_response_stream(event_receiver).await
84+
}
85+
86+
async fn process_agent_response_stream(
87+
mut event_receiver: EventReceiver,
88+
) -> Result<String, bedrockagentruntime::Error> {
89+
let mut full_agent_text_response = String::new();
90+
91+
while let Some(event_result) = event_receiver.recv().await? {
92+
match event_result {
93+
ResponseStream::Chunk(chunk) => {
94+
if let Some(bytes) = chunk.bytes {
95+
match String::from_utf8(bytes.into_inner()) {
96+
Ok(text_chunk) => {
97+
full_agent_text_response.push_str(&text_chunk);
98+
}
99+
Err(e) => {
100+
eprintln!("UTF-8 decoding error for chunk: {}", e);
101+
}
102+
}
103+
}
104+
}
105+
_ => {
106+
panic!("received an unhandled event type from Bedrock stream",);
107+
}
108+
}
109+
}
110+
Ok(full_agent_text_response)
111+
}
112+
113+
#[cfg(test)]
114+
mod test {
115+
116+
use super::*;
117+
118+
#[tokio::test]
119+
async fn test_process_agent_response_stream() {
120+
let mut mock = MockEventReceiverImpl::default();
121+
mock.expect_recv().times(1).returning(|| {
122+
Ok(Some(
123+
aws_sdk_bedrockagentruntime::types::ResponseStream::Chunk(
124+
aws_sdk_bedrockagentruntime::types::PayloadPart::builder()
125+
.set_bytes(Some(aws_smithy_types::Blob::new(vec![
126+
116, 101, 115, 116, 32, 99, 111, 109, 112, 108, 101, 116, 105, 111, 110,
127+
])))
128+
.build(),
129+
),
130+
))
131+
});
132+
133+
// end the stream
134+
mock.expect_recv().times(1).returning(|| Ok(None));
135+
136+
let response = process_agent_response_stream(mock).await.unwrap();
137+
138+
assert_eq!("test completion", response);
139+
}
140+
141+
#[tokio::test]
142+
#[should_panic(expected = "received an unhandled event type from Bedrock stream")]
143+
async fn test_process_agent_response_stream_error() {
144+
let mut mock = MockEventReceiverImpl::default();
145+
mock.expect_recv().times(1).returning(|| {
146+
Ok(Some(
147+
aws_sdk_bedrockagentruntime::types::ResponseStream::Trace(
148+
aws_sdk_bedrockagentruntime::types::TracePart::builder().build(),
149+
),
150+
))
151+
});
152+
153+
let _ = process_agent_response_stream(mock).await.unwrap();
154+
}
155+
}

rustv1/examples/rust-toolchain.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
# This should be kept in sync with https://github.com/awslabs/aws-sdk-rust#supported-rust-versions-msrv
22
[toolchain]
3-
channel = "1.83.0"
3+
channel = "1.87.0"

0 commit comments

Comments
 (0)