# Build an AI powered customer service voice agent on AWS

A few weeks ago, I found myself in Vegas, trying to update a dinner reservation on a packed Saturday night. Calling the restaurant was useless—there was no chance of getting through. That got me thinking: how quickly could I spin up an AI-powered reservation assistant?

So, I put it to the test. In under an hour, I built a crude proof of concept (PoC) using AWS services. The setup was simple:

* **Amazon Connect** to handle incoming calls
    
* **Amazon Lex** for voice interaction and capturing reservation details
    
* **AWS Lambda** to process and store the reservation
    
* **Amazon DynamoDB** for storing reservations
    
* **Amazon SES** to send confirmation emails
    

This isn’t about cutting-edge AI. It’s about solving real problems—fast. AI isn’t useful unless it’s applied to the right problem, and once you do that, impact follows almost instantly.

Now, let’s dive into how I built it.

## **Architecture**

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1742563599444/6223826e-03b3-47a3-b0c3-9516aa73c87e.jpeg align="center")

## **Setting Up Amazon Connect for Call Routing**

### **Create an Amazon Connect Instance**

1. Go to the **AWS Console** → **Amazon Connect** → **Create an instance**.
    
2. Set up an administrator account and choose a name for the instance.
    
3. Follow the instance creation flow to claim a phone number and use it for incoming calls
    

Now, whenever someone calls this number, we can define what happens next using a **contact flow**.

### **Configure a Contact Flow to Invoke Lex**

A **contact flow** is a set of actions Amazon Connect follows when handling a call. Under bot create a Lex bot. After configuring the bot, create an “intent” to capture user request to make reservations.

Additionally, the call flow I configured a welcome prompt and terminating the call after capturing the required information

## **Creating an Amazon Lex Bot for Reservations**

### **Define the Lex Bot and Intent**

Amazon Lex is AWS’s conversational AI service, handling both text and voice inputs.

1. In **Amazon Lex**, create a new bot called `ReservationBot`.
    
2. Under **Intents**, create a new intent called `MakeReservation`.
    
3. Add sample utterances like:
    
    * *I want to make a reservation*
        
    * *Can I book a table for tonight?*
        
    * *Reserve a table for two at 7 PM*
        

**Add Slots to Capture User Data**

Slots are variables that store user inputs. Add the following slots to `MakeReservation`:

| Slot Name | Type | Prompt Example | Required? |
| --- | --- | --- | --- |
| `firstName` | AMAZON.FirstName | What name should I book under? | Yes |
| `phoneNumber` | AMAZON.PhoneNumber | Can I get your phone number? | Yes |
| `partySize` | AMAZON.Number | How many people are in your party? | Yes |
| `date` | [AMAZON.Date](http://AMAZON.Date) | What date do you need the reservation for? | Yes |
| `time` | AMAZON.Time | What time would you like the reservation? | Yes |
| `confirmation` | AMAZON.YesNo | Should I confirm your reservation? | Yes |

**Configure Fulfillment with AWS Lambda**

Once Lex collects user input, we need to process the reservation and store it in DynamoDB.

1. In Lex, go to the **Fulfillment** section.
    
2. Select **AWS Lambda function** and create a new function.
    
3. Use the following Python code:
    

```python
import boto3
import uuid

dynamodb = boto3.resource("dynamodb")
table = dynamodb.Table("Reservations")

def lambda_handler(event, context):
    slots = event["currentIntent"]["slots"]
    
    reservation_id = str(uuid.uuid4())
    reservation_data = {
        "ReservationID": reservation_id,
        "FirstName": slots["firstName"],
        "PhoneNumber": slots["phoneNumber"],
        "PartySize": slots["partySize"],
        "Date": slots["date"],
        "Time": slots["time"]
    }
    
    table.put_item(Item=reservation_data)
    
    return {
        "dialogAction": {
            "type": "Close",
            "fulfillmentState": "Fulfilled",
            "message": {
                "contentType": "PlainText",
                "content": f"Your reservation is confirmed, {slots['firstName']}! Your confirmation ID is {reservation_id}."
            }
        }
    }
```

This function:  
✅ Extracts user inputs from Lex  
✅ Generates a unique reservation ID  
✅ Stores the reservation in DynamoDB  
✅ Returns a confirmation message

### **Sending Confirmation Emails with Amazon SES**

Once the reservation is stored, we want to send a confirmation email. Modify the Lambda function to include this:

```python
def send_email(to_address, first_name, reservation_id):
    subject = "Your Reservation is Confirmed!"
    body = f"Hello {first_name},\n\nYour reservation is confirmed. Your confirmation ID is {reservation_id}.\n\nThank you!"
    
    response = ses.send_email(
        Source="your-email@example.com",
        Destination={"ToAddresses": [to_address]},
        Message={
            "Subject": {"Data": subject},
            "Body": {"Text": {"Data": body}}
        }
    )
    return response
```

Update the `lambda_handler` function to call `send_email()`:

```python
send_email(slots["phoneNumber"] + "@example.com", slots["firstName"], reservation_id)
```

Now, once a reservation is made, an email confirmation is sent to the customer.

## **Testing the Full Setup**

**Test the Call Flow in Amazon Connect**

* Call the phone number assigned to Amazon Connect.
    
* Try making a reservation by voice.
    
* Ensure the data is stored in DynamoDB and a confirmation email is sent.
    

This setup isn’t complex, and that’s the beauty of it. In under an hour, we built a fully functional AI-powered reservation system using AWS services. The key takeaways:

✅ **Amazon Connect + Lex** makes voice call automation easy.  
✅ **Lambda + DynamoDB** handles backend processing and storage.  
✅ **Amazon SES** automates email confirmations.

This solution can be expanded in many ways—multi-language support, SMS confirmations via SNS, or even integrating with restaurant POS systems. But the core idea remains: AI is most effective when applied to the right problems.
