← Back to list

Build your own Chatbot with GenAI on Amazon Bedrock

Create your own chatbot and take advantage of Generative AI models on Amazon Bedrock. You’ll thank yourself later!

José Carlos Carvalheira · 2025-11-30 19:08 · 15 claps · 12.1 min read
#genia #chatbots #chatgpt #aws #generative-ai-use-cases
Open on Medium ↗
Wiki topics: LLM · Large Language Models AI · AI · General ☁️ · DevOps & Cloud

Build your own Chatbot with GenAI on Amazon Bedrock

Create your own chatbot and take advantage of Generative AI models on Amazon Bedrock. You’ll thank yourself later!

Hello, my name is José Carlos Carvalheira, and in this article I want to share with you a practical step‑by‑step guide to building your own chatbot using large language models (LLMs). The focus will be on Amazon Bedrock, a platform that makes it easy to access generative AI models without having to train everything from scratch, or even sign up for multiple platforms just to use pre‑trained models!

My goal is to show you that with just a few lines of Python code, you can build a functional chatbot and start exploring the power of LLMs in real applications. (…and at a low cost , stay tuned, I’ll explain more in the conclusion of this post.)

It’s important to highlight that each model provider, such as Amazon, Meta, OpenAI, Anthropic, and others, has its own particularities when it comes to coding and integration. That’s why in this post we’ll focus specifically on Amazon, using the text model “amazon.titan-text-express-v1”.

Even if you try to use another model from Amazon itself, the same code will rarely work as‑is, since each model also comes with its own parameters, specificities, and use cases.

Shall we get started?

Dividing this post into 7 steps for complete understanding by the end of the reading:

  1. Amazon Bedrock and the Chosen Model for the Chatbot
  2. Setting Up the Environment
  3. Downloading and Validating Your Code
  4. Code explanation
  5. Running your personal chatbot
  6. Understand how the pricing model works
  7. Conclusion

1) Amazon Bedrock and the Chosen Model for the Chatbot

Amazon Bedrock is an AWS service that allows developers to build generative AI applications without the need to train models from scratch or manage complex infrastructure.

It stands out by offering a simple and practical way to access generative AI models without configuring servers, training advanced models, or dealing with heavy infrastructure. With Bedrock, you can experiment with different models from providers such as Amazon, Meta, Anthropic, and Cohere through a single API, making the integration process much faster and more accessible. In addition, the service leverages the robustness and security of AWS infrastructure, ensuring scalability and reliability for real-world applications.

This combination of simplicity, variety, and security makes Bedrock an excellent choice for anyone looking to explore the power of LLMs in chatbot projects, text analysis, or any other AI application.

For our project, we will use the “Titan Text G1 — Express v1” model, which is text-based and will serve as the “engine” of our chatbot.

Below you can see the AWS console displaying the model selected for this project.

img01. Amazon Bedrock — Model Catalog screen

img01. Amazon Bedrock — Model Catalog screen

When you click on the selected model, some information will be displayed. One of them is the Model ID, which will be used directly in our Python code.

img02. Amazon Bedrock — Titan Text G1 — Express Model screen

img02. Amazon Bedrock — Titan Text G1 — Express Model screen

You can also find information on how to use the model through the link “amazon.titan-text-express-v1”, as this page provides references to all the coding standards expected by the model.

Take a look at this example, where we are following exactly the standards required by the amazon.titan-text-express-v1 model. There’s no need to worry about understanding what the code below does; just notice that we need to follow a documented standard for each type of model.

img03. Amazon Bedrock docs — Request parameters of Amazon Titan Text Express Model

img03. Amazon Bedrock docs — Request parameters of Amazon Titan Text Express Model

2) Setting Up the Environment

2.1) Creating and Configuring a Programmatic User

Here I’ll just create a new IAM user and attach the AmazonBedrockFullAccess policy to it.

I’ll simplify this process since it’s not the core concept of this post, but keep in mind that permission granularity is a fundamental pillar of security in AWS.

img04. IAM User and associated Policy

img04. IAM User and associated Policy

Don’t forget that you’ll need the AWS CLI installed to enable the configuration of your user “Profile” on your machine (Download here).

It is important to remember to write down or download the credentials that will be provided at the end of the programmatic user creation.

After installation, run the commands below. The first command is to verify that the installation was completed successfully by indicating the installed version of the AWS CLI, and the second command is to configure your access to AWS through your machine, responding to the information requested during the configuration process.

aws --version
aws configure

The last field can be left blank, just by pressing Enter.

img05. AWS CLI — install validation

img05. AWS CLI — install validation

img06. AWS CLI — Configuration

img06. AWS CLI — Configuration

Now run a test command to check if your access is correct.

aws bedrock list-foundation-models

You will see that you can view the list of models provided by Amazon Bedrock.

img07. AWS CLI — Validating the credentials access

img07. AWS CLI — Validating the credentials access

After this test, you will be ready to proceed

2.2) Creating and Activating the Virtual Environment

2.2.1) Windows Environment Let's start to configure the windows environment.

2.2.1.1) Start downloading the Python3 and installing it

2.2.1.2) Run the command below in the folder where you want to create your project.

py -m venv .venv
.venv\Scripts\activate

img08. Python — Environment configuration

img08. Python — Environment configuration

Note that after running the second command, the text “(.venv)” will appear in front of your prompt.

You will also see it inside your project folder when browsing through Microsoft Visual Studio Code.

img09. Microsoft Visual Studio Code — .venv created

img09. Microsoft Visual Studio Code — .venv created

Now run the command below to install the latest version of Boto3 (AWS SDK for Python). For this, we will use pip3.

 pip3 install boto3

img10. AWS Boto3 SDK instalation

img10. AWS Boto3 SDK instalation

Validate the installation of Boto3 using the command below.

pip show boto3

img11. AWS Boto3 SDK — Install Validation

img11. AWS Boto3 SDK — Install Validation

2.2.2) Linux/MacOS Run the command below in the folder where you want to create your project.

$ python3 -m venv .venv
$ source .venv/bin/activate

img12. Python — Environment configuration

img12. Python — Environment configuration

Note that after running the second command, the text “(.venv)” will appear in front of your prompt.

You will also see it inside your project folder when browsing through Microsoft Visual Studio Code.

img13. Microsoft Visual Studio Code — .venv created

img13. Microsoft Visual Studio Code — .venv created

Now run the command below to install the latest version of Boto3 (AWS SDK for Python). For this, we will use pip3.

$ pip3 install boto3

img14. AWS Boto3 SDK instalation

img14. AWS Boto3 SDK instalation

Validate the installation of Boto3 using the command below.

$ pip show boto3 

img15. AWS Boto3 SDK — install validation

img15. AWS Boto3 SDK — install validation

3) Downloading and Validating Your Code

3.1) Before starting, open Microsoft Visual Studio Code, go to the Extensions view, and install the Python extension.

img16. Microsoft Visual Studio Code Extentions — Python Environments

img16. Microsoft Visual Studio Code Extentions — Python Environments

3.2) Using Microsoft Visual Studio Code, create a folder named src/ so that our code does not need to be placed in the project root. Then, inside this folder, create a file called “chatbot.py”.

img17. Microsoft Visual Studio Code Extentions — New src folder

img17. Microsoft Visual Studio Code Extentions — New src folder

3.3) Go to our GitHub repository and download the base code, which will be used throughout this post. (chatbot code)

3.4) Copy the content from the GitHub repository into the “chatbot.py” file and save it.

3.5) Only if necessary, don’t forget to add “.venv” to the content of the .gitignore file located in the root of your project.

4) Code explanation

4.1) Importing the Libraries

• boto3: Official AWS SDK for Python, used in our case to interact with Amazon Bedrock. • json: Used to handle data in JSON format (model input and output). • os and platform: Used to clear the terminal screen in a way compatible with Windows and Linux/Mac. • ClientError: Used to capture errors when invoking models through the Client object.

import boto3
import json
import os
import platform
from botocore.exceptions import ClientError

4.2) Setting initial variables

Define the bot’s name and the language model that will be used (Amazon Titan).

bot_name = "Bot Assistent"
model_id = "amazon.titan-text-express-v1"

Create the cliente object variable to connect to the Bedrock Runtime service in the us-east-1 region.

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

4.3) Chatbot History

This variable is very important for the smooth functioning of the chatbot, as it maintains the conversation history and context. This array will store all the messages exchanged between the user and the bot.

Important Tip The more messages are exchanged with the bot, the higher the number of input tokens in the conversation, which can quickly increase costs. For this reason, limiting the total number of tokens is important. However, when doing so, older messages in the conversation will no longer be taken into account by the bot.

history = []

4.4) Request Configuration

This function aims to ensure that the parameters expected by the model are correctly passed during its execution.

def get_request_config():
    return json.dumps({
            "inputText": "\n".join(history),
            "textGenerationConfig": {
                "maxTokenCount": 4096,
                "stopSequences": [],
                "temperature": 0,
                "topP": 1
            }
    })

• inputText: combines the entire history into a single string, so the model has conversation context. • maxTokenCount: sets the maximum number of tokens in the response. • stopSequences: used to define keywords that can end the bot’s response. • temperature: controls the creativity of the response (0 = deterministic; higher values = more creative). • topP: controls the diversity of the response; in other words, it limits or not the vocabulary, making it more predictable or more creative.

4.5) History Appending function

This function simply appends the parameter value to the History Array, ensuring that the entire conversation remains persistent.

def addHistory(text:str):
    history.append(text)

4.6) Prompt Cleaning

This function clears the terminal screen, adapting the command to be compatible with both Windows and Linux/Mac.

if platform.system() == "Windows":
    os.system('cls')
else:
    os.system('clear')

4.7) Chatbot Initial Interface

Displays an initial message to the user.

print("######################################")
print("###        CHATBOT ACTIVATED       ###")
print("######################################")
print("IS THERE A TOPIC YOU'RE CURIOUS ABOUT?")

4.8) Interface Loop

4.8.1) Inside the interface loop, each time the user asks a question, an interaction begins and the user’s message is immediately stored in the message history.

while True:
    user_input = input("\nUser: ")
    addHistory("User: " + user_input)

4.8.2) If the user wants to end the conversation with the chatbot without abruptly stopping the application, they can do so by sending the message “exit” or “bye”.

if user_input.lower() == "exit" or user_input.lower() == "bye":
    print(bot_name + ": Bye bye!")        
    break

4.8.3) If the user simply presses ENTER without sending any message to the model, the interface is optimized to avoid an unnecessary call to Bedrock, and a default message is displayed.

if user_input.strip() == "":
    print(bot_name + ": I don't understand you!")

4.8.4) The point in the loop where the code runs the Titan model on Bedrock, passing the parameters required by the model.

modelInvoke = client.invoke_model(
    body=get_request_config(), 
    modelId=model_id, 
    accept="application/json", 
    contentType="application/json")

4.8.5) Decode the JSON response sent by the model and extract the text to display on the screen.

responseCall = json.loads(modelInvoke.get('body').read())
outputBodyText = responseCall.get('results')[0].get('outputText').strip()

Hold on… here I will explain why this is being done this way.

The Titan model we are using, when returning its response in JSON format, follows a documented standard. In this case, see below the image that shows the format we are expecting.

img18. Amazon Bedrock docs — Response parameters of Amazon Titan Text Express Model

img18. Amazon Bedrock docs — Response parameters of Amazon Titan Text Express Model

Invoke Model Response FINISHED — The response was fully generated. LENGTH — The response was truncated because of the response length you set. STOP_CRITERIA_MET — The response was truncated because the stop criteria was reached. RAG_QUERY_WHEN_RAG_DISABLED — The feature is disabled and cannot complete the query. CONTENT_FILTERED — The contents were filtered or removed by the content filter applied.

4.8.6) Adding the response to the history and printing the output as a Bot.

addHistory(outputBodyText)
print("\n" + bot_name + ": " + outputBodyText.replace("Bot",""))

5) Running your personal chatbot

5.1) To run your new code using the Microsoft Visual Studio terminal, make sure the virtual environment is activated. If it is already activated, simply skip this step, otherwise, run the following command in your project folder:

## Windows Command ##
.venv\Scripts\activate

## Linux/MacOS Command ##
$ source .venv/bin/activate

5.2) Using the Visual Studio terminal or your operating system’s Command Prompt, run the following command in the same project folder to start your chatbot:

## Windows Command ##
python src/chatbot.py

## Linux/MacOS Command ##
$ python3 src/chatbot.py

img19. Chatbot — Starting

img19. Chatbot — Starting

Evolving the questions for the chatbot, notice that the chatbot is able to keep an active conversation, including topics previously asked.

img20. Chatbot — Chatting with the Bot

img20. Chatbot — Chatting with the Bot

Notice that this code can serve as a foundation for the evolution of any type of chatbot, whether using a proprietary platform or messaging tools that support external API calls.

It is important to remember that each model has its own particularities. For example, switching from an Amazon model to a Meta model will not work directly, since each provider has its own specifications.

However… the implementation concept remains essentially the same, structure the history, configure the parameters, and integrate the model call.

6) Understand how the pricing model works

First, keep in mind the costs of running the model we are currently using (see AWS pricing table)

Keep in mind that prices may change, but using the current rates as a reference, for the Amazon Titan Text Express v1 model the pricing is:

• 1,000 input tokens: $0.0002 • 1,000 output tokens: $0.0006

Now let’s address the question: What are tokens?

Tokens are like small pieces of text that generative AI models use to understand and produce language. Instead of reading an entire sentence at once, the AI breaks it down into smaller parts — which can be whole words, fragments of words, or even symbols — and processes them in sequence.

(Each model has its own rule for calculating the total number of tokens. Unfortunately, for Amazon models we don’t yet have a web-based calculator like OpenAI, which clearly demonstrates how tokenization works. You can check it out here, the concept is very similar.)

Let’s put this understanding into practice using our chatbot. With a small customization, I can show how many tokens were returned in the model’s response.

See the example below:

img21. Chatbot — Pricing based on total of Tokens

img21. Chatbot — Pricing based on total of Tokens

Great, now let’s use the response message returned by the model, and based on it we’ll proceed with the calculations.

"Hello! How can I help you today?"

Now, let’s compare this with the execution performed through the AWS Console, using the simulator that allows us to test the models available in Amazon Bedrock.

img22. AWS Cosole Chat — Total Ouput tokens comparison

img22. AWS Cosole Chat — Total Ouput tokens comparison

Notice that the response returned by the model used 13 tokens, the same as generated in our ChatBot!

Now here’s a quick question…

How many output messages like this would be required for AWS to charge me $0.0006? exactly the amount corresponding to 1,000 tokens used.

Answer 1,000 output tokens / 13 response (output) tokens = 76.92. Let’s round it up to 77.

Ok… and how many output messages like this would be required for AWS to charge me $0.01?

Answer First, let’s identify how many tokens correspond to $0.01. (0,01 / 0,0006) * 1000 = 16.666,67 tokens Let’s round it up to 16.667

Now, we divide this amount by the size of the token message. 16.667 / 13 = 1.282,84 Let’s round it up to 1.283

Great, now for us to be charged $1, how many output messages like this would we need to receive for that charge to occur?

Resposta (1,283 tokens * 100 cents, which correspond to 1 Dollar) = 128,300

In summary, With just 1 Dollar, assuming we always received the same response, or another output message with 13 tokens, we could interact with our ChatBot and get 128,300 responses!

Ok… Ok… This example was purely illustrative. In practice, responses are usually longer and never exactly the same, and in this scenario we are only considering the costs of output tokens. The cost related to input tokens (the questions sent to the ChatBot) was not included here.

The important takeaway is that you now know how to calculate the costs of using the model, considering the total number of input and output tokens. In addition, you also understand the importance of testing your model and fine-tuning it according to your needs by properly adjusting the parameters MaxToken, Temperature, and TopP.

7) Conclusion

Throughout this post, we’ve seen that structuring and running the foundation of a chatbot using the Titan model in Amazon Bedrock is not complicated at all.

This code provides a solid foundation for developing and evolving any chatbot project. It can be used either on your own platform or integrated with conversational tools that support external API calls.

Now, let me share what I think most interesting about all this: beyond the satisfaction of having your own ChatBot, you can continue to improve it, test it with other models, and perhaps even save a good amount of money by not needing to hire equivalent services. Right? Or better yet, you might even start making money with it!

If this post inspired you to explore the topic, then I’ve reached my goal.


메타데이터
post_id
3f79b073b217
slug
build-your-own-chatbot-with-genai-on-amazon-bedrock-3f79b073b217
url
https://medium.com/@carvalheira.cloud/build-your-own-chatbot-with-genai-on-amazon-bedrock-3f79b073b217
canonical_url
https://medium.com/@carvalheira.cloud/build-your-own-chatbot-with-genai-on-amazon-bedrock-3f79b073b217
author_url
https://medium.com/@carvalheira.cloud
status
ok
fetched_at
2026-06-23 19:38:28