I tried retrieving Amazon Connect Customer AI agent self-service conversations using the ListMessages API

I tried retrieving Amazon Connect Customer AI agent self-service conversations using the ListMessages API

Here is how to retrieve conversation history with AI agents in Amazon Connect using a Contact ID. You can use the `ListMessages` API to programmatically extract messages between customers and AI agents, which can be utilized for external system integration and analysis of response accuracy.
2026.09.09

This page has been translated by machine translation. View original

Introduction

When using Amazon Connect Customer AI agents to handle self-service inquiries, you may want to review the conversation content between customers and AI agents after a call ends.

For example, use cases include the following:

  • Reviewing the AI agent's responses
  • Integrating inquiry content and response results with external systems
  • Analyzing the AI agent's response accuracy

Information about Amazon Connect Customer AI agents can be viewed from the ListMessages API, ListSpans API, CloudWatch Logs, Automated Interaction Log, Contact Lens, and others depending on the use case.

This time, we will use the ListMessages API, which can retrieve conversation messages within an AI agent session.

We executed the DescribeContact API from AWS CloudShell using a Contact ID as the starting point, extracted the Assistant ID and Session ID from the retrieved Session ARN, and retrieved the conversation using the ListMessages API.

https://docs.aws.amazon.com/connect/latest/APIReference/API_amazon-q-connect_ListMessages.html

Conclusion First

The flow for retrieving conversations with an AI agent from a Contact ID is as follows:

Contact ID

DescribeContact

Contact.WisdomInfo.SessionArn

Extract Assistant ID and Session ID

ListMessages

Retrieve messages between customer and AI agent

Extract the Assistant ID and Session ID from Contact.WisdomInfo.SessionArn included in the DescribeContact response, and specify them in aws qconnect list-messages.

In this verification, the following commands were executed from AWS CloudShell.

export AWS_REGION="ap-northeast-1"
export INSTANCE_ID="<connect-instance-id>"
export CONTACT_ID="<contact-id>"

SESSION_ARN=$(aws connect describe-contact \
  --instance-id "$INSTANCE_ID" \
  --contact-id "$CONTACT_ID" \
  --region "$AWS_REGION" \
  --query 'Contact.WisdomInfo.SessionArn' \
  --output text)

if [ -z "$SESSION_ARN" ] ||
   [ "$SESSION_ARN" = "None" ] ||
   [ "$SESSION_ARN" = "null" ]; then
  echo "ERROR: Failed to retrieve the AI agent Session ARN." >&2
  exit 1
fi

ASSISTANT_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $(NF-1)}')
SESSION_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $NF}')

echo "CONTACT_ID=$CONTACT_ID"
echo "ASSISTANT_ID=$ASSISTANT_ID"
echo "SESSION_ID=$SESSION_ID"

aws qconnect list-messages \
  --assistant-id "$ASSISTANT_ID" \
  --session-id "$SESSION_ID" \
  --filter TEXT_ONLY \
  --region "$AWS_REGION" \
  --output json |
jq -r '
  .messages
  | sort_by(.timestamp)
  | .[]
  | select(.value.text.value? != null)
  | "\(.participant): \(.value.text.value | gsub("\\s+"; " "))"
'

In this verification, we executed this command after the call ended and were able to confirm messages between the customer and AI agent in the format of CUSTOMER and BOT.

Conclusion First

The ListMessages API does not allow you to specify a Contact ID directly. To execute it, you need the AI agent's Assistant ID and Session ID.

Therefore, first execute the DescribeContact API by specifying the Contact ID and retrieve Contact.WisdomInfo.SessionArn from the response. Since the Session ARN contains the Assistant ID and Session ID at the end, extract each of them and specify them in the ListMessages API.

In this verification, we retrieved the conversation from AWS CloudShell using the following steps:

  1. Execute the DescribeContact API specifying the Contact ID
  2. Retrieve Contact.WisdomInfo.SessionArn
  3. Extract the Assistant ID and Session ID from the Session ARN
  4. Execute the ListMessages API specifying the extracted IDs
  5. Format the retrieved messages chronologically using jq

The following are the commands executed this time.

export AWS_REGION="ap-northeast-1"
export INSTANCE_ID="<connect-instance-id>"
export CONTACT_ID="<contact-id>"

SESSION_ARN=$(aws connect describe-contact \
  --instance-id "$INSTANCE_ID" \
  --contact-id "$CONTACT_ID" \
  --region "$AWS_REGION" \
  --query 'Contact.WisdomInfo.SessionArn' \
  --output text)

if [ -z "$SESSION_ARN" ] ||
   [ "$SESSION_ARN" = "None" ] ||
   [ "$SESSION_ARN" = "null" ]; then
  echo "ERROR: Failed to retrieve the AI agent Session ARN." >&2
  exit 1
fi

ASSISTANT_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $(NF-1)}')
SESSION_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $NF}')

echo "CONTACT_ID=$CONTACT_ID"
echo "ASSISTANT_ID=$ASSISTANT_ID"
echo "SESSION_ID=$SESSION_ID"

aws qconnect list-messages \
  --assistant-id "$ASSISTANT_ID" \
  --session-id "$SESSION_ID" \
  --filter TEXT_ONLY \
  --region "$AWS_REGION" \
  --output json |
jq -r '
  .messages
  | sort_by(.timestamp)
  | .[]
  | select(.value.text.value? != null)
  | "\(.participant): \(.value.text.value | gsub("\\s+"; " "))"
'

When we executed this command after the call ended, customer utterances were retrieved as CUSTOMER and AI agent responses were retrieved as BOT.

Prerequisites

This was verified in the following environment:

  • Region: ap-northeast-1
  • Amazon Connect Customer instance: already created
  • Self-service AI agent: already created
  • Voice flow using AI agent: already created
  • Execution environment: AWS CloudShell

Resource IDs, message IDs, account IDs, and phone numbers in the article have been changed to example values.

Also, the AWS CloudShell environment used has both the aws command and jq command available. How to verify without using jq is explained in the latter half.

Flow for Retrieving Conversations from a Contact ID

To execute the ListMessages API, an Assistant ID and Session ID are required.

This time, we executed the DescribeContact API by specifying a Contact ID and retrieved these IDs from Contact.WisdomInfo.SessionArn in the response.

The DescribeContact API is an API that retrieves information about a specified contact. The response includes WisdomInfo as information related to the AI agent, and the Session ARN is stored within it.

{
  "Contact": {
    "WisdomInfo": {
      "SessionArn": "arn:aws:wisdom:ap-northeast-1:111111111111:session/aaaaaaaa-bbbb-4ccc-8ddd-eeeeeeeeeeee/ffffffff-1111-4222-8333-444444444444"
    }
  }
}

In this verification, the Session ARN had the following format:

arn:aws:wisdom:<region>:<account-id>:session/<assistant-id>/<session-id>

For this reason, we split the ARN by / and extract the Assistant ID and Session ID from the end.

arn:aws:wisdom:<region>:<account-id>:session/<assistant-id>/<session-id>
                                                        ↑             ↑
                                                Assistant ID       Session ID

Details of the DescribeContact API are described in the following documentation.

https://docs.aws.amazon.com/ja_jp/connect/latest/APIReference/API_DescribeContact.html

Details of WisdomInfo are described in the following documentation.

https://docs.aws.amazon.com/ja_jp/connect/latest/APIReference/API_WisdomInfo.html

Extracting IDs from the Session ARN

Use the following commands to extract the Assistant ID and Session ID from the end of the Session ARN.

ASSISTANT_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $(NF-1)}')
SESSION_ID=$(echo "$SESSION_ARN" | awk -F/ '{print $NF}')

awk -F/ treats / as a delimiter, and NF is used to get the number of elements.

  • $(NF-1): The second-to-last element
  • $NF: The last element

In the Session ARN format confirmed this time, the second-to-last element corresponds to the Assistant ID, and the last element corresponds to the Session ID.

When the Session ARN Cannot Be Retrieved

Since SessionArn is not a required field of WisdomInfo, it may not be retrievable depending on the target Contact.

Therefore, the actual processing checks whether the Session ARN is empty.

if [ -z "$SESSION_ARN" ] ||
   [ "$SESSION_ARN" = "None" ] ||
   [ "$SESSION_ARN" = "null" ]; then
  echo "ERROR: Failed to retrieve the AI agent Session ARN." >&2
  exit 1
fi

In this verification, we targeted voice contacts that used an AI agent, so the Session ARN was retrievable.

Executing the ListMessages API from AWS CloudShell

Once the Assistant ID and Session ID are retrieved, execute aws qconnect list-messages.

The AWS CLI command name is qconnect, but the target is the Amazon Connect Customer AI agent session.

aws qconnect list-messages \
  --assistant-id "$ASSISTANT_ID" \
  --session-id "$SESSION_ID" \
  --filter TEXT_ONLY \
  --region "$AWS_REGION" \
  --output json

ListMessages retrieves messages within a session by specifying an Assistant ID and Session ID. In the AWS CLI reference, list-messages is listed as a pagination-supported API.

The following options are used in this command:

Option Description
--assistant-id The AI agent's Assistant ID
--session-id The Session ID from which to retrieve messages
--filter TEXT_ONLY A filter to target text messages
--region The region in which to execute the API
--output json Outputs the response in JSON format

Execution Results

In this environment, the Contact ID, Assistant ID, and Session ID were displayed as follows.

IDs in the article have been changed to example values.

CONTACT_ID=11111111-2222-4333-8444-555555555555
ASSISTANT_ID=aaaaaaaa-bbbb-4ccc-8ddd-eeeeeeeeeeee
SESSION_ID=ffffffff-1111-4222-8333-444444444444

Next, the conversation between the customer and AI agent was displayed.

CUSTOMER: I'd like to check my delivery date and time
BOT: Certainly. I will check your delivery date and time. Could you please provide the last 4 digits of your order number and the phone number you registered at the time of your order?
CUSTOMER: The last 4 digits are 1742 and my phone number is 090xxxxxxxx
BOT: Thank you. I will check that for you.
BOT: Your scheduled delivery date is September 8th, and the delivery time slot is between 4:00 PM and 6:00 PM.
CUSTOMER: I'd like to change just the delivery time slot to 2:00 PM
BOT: Certainly. You'd like to change the delivery time slot to 2:00 PM. Let me check that for you. I will verify whether the 2:00 PM to 4:00 PM time slot on September 8th is available.
BOT: I apologize. The 2:00 PM to 4:00 PM time slot is fully booked. For September 8th, the 12:00 PM to 2:00 PM or the 6:00 PM to 8:00 PM time slots are available. How would you like to proceed?
CUSTOMER: Then please go with 6:00 PM to 8:00 PM
BOT: Certainly. Let me confirm the change details. Current scheduled delivery: September 8th, 4:00 PM to 6:00 PM. After change: September 8th, 6:00 PM to 8:00 PM. Does this look correct?
CUSTOMER: Yes
BOT: Thank you. I will change the delivery date and time.
BOT: The delivery date and time change has been completed. Your delivery will be on September 8th between 6:00 PM and 8:00 PM. The change details have been sent to you via SMS.
CUSTOMER: Yes, thank you very much
BOT: Thank you for using our service. If you have any questions, please feel free to contact us at any time.

In this verification, the following information was retrieved:

  • Customer utterances
  • AI agent responses
  • CUSTOMER and BOT indicating the speaker
  • Chronological order of messages

Although timestamps are omitted in the display, messages are viewed chronologically using sort_by(.timestamp).

Also, we executed the command after the call ended and were able to retrieve up to the final AI agent response.

Checking JSON Without Using jq

If you want to check the ListMessages response as-is without formatting the conversation, you do not need to use jq.

After retrieving the Assistant ID and Session ID, execute the following command:

aws qconnect list-messages \
  --assistant-id "$ASSISTANT_ID" \
  --session-id "$SESSION_ID" \
  --filter TEXT_ONLY \
  --region "$AWS_REGION" \
  --output json

An example output is as follows.

Message IDs and timestamps have been changed for the article.

{
  "messages": [
    {
      "value": {
        "text": {
          "value": "\nThank you for using our service. If you have any questions, please feel free to contact us at any time.\n"
        }
      },
      "messageId": "aaaaaaaa-1111-4222-8333-bbbbbbbbbbbb",
      "participant": "BOT",
      "timestamp": "2026-08-05T23:56:38.745000+00:00"
    },
    {
      "value": {
        "text": {
          "value": "Yes, thank you very much"
        }
      },
      "messageId": "cccccccc-1111-4222-8333-dddddddddddd",
      "participant": "CUSTOMER",
      "timestamp": "2026-08-05T23:56:37.161000+00:00"
    },
    {
      "value": {
        "text": {
          "value": "\nThe delivery date and time change has been completed. Your delivery will be on September 8th between 6:00 PM and 8:00 PM. The change details have been sent to you via SMS.\n"
        }
      },
      "messageId": "eeeeeeee-1111-4222-8333-ffffffffffff",
      "participant": "BOT",
      "timestamp": "2026-08-05T23:56:22.978000+00:00"
    }
  ]
}

In this format, the following information can be confirmed:

  • messageId
  • participant
  • timestamp
  • value.text.value

Line Breaks in Message Body

Looking at the BOT message body, \n is included at the beginning and end of the string.

"value": "\nThe delivery date and time change has been completed.\n"

Because these line break characters are included, when displaying the JSON as-is, BOT: and the message body may appear on separate lines.

If you want to display the conversation body in a readable format, extract the body using jq as shown earlier and replace line breaks and consecutive whitespace with single spaces.

ListMessages Is Not a Transcript of the Entire Call

What is retrieved by ListMessages is the messages within the AI agent session.

Therefore, it is not an API that retrieves a transcript of the entire voice contact including sections where the AI agent is not involved.

You need to select the feature to use depending on the information you want to retrieve.

Information to Retrieve Example Verification Method
Messages between customer and AI agent ListMessages
AI agent processing and tool execution ListSpans
Detailed event logs of AI agent CloudWatch Logs
View self-service history in admin console Automated Interaction Log
Transcript of voice contact Contact Lens

As in this case, when retrieving messages exchanged between a customer and AI agent within an AI agent session via API, ListMessages is appropriate.

On the other hand, when internal AI agent processing, tool execution, or a transcript of the entire voice contact is needed, use a combination of other features.

Things to Verify When Retrieving

Verify the Presence of the Session ARN

Executing ListMessages requires an Assistant ID and Session ID.

This time we retrieved them from Contact.WisdomInfo.SessionArn in DescribeContact, but you need to account for Contacts where SessionArn does not exist.

When implementing, please add error handling for when the Session ARN cannot be retrieved, or processing to treat such contacts as out of scope.

Consider the Timing of Message Retrieval

In this verification, we executed the command after the call ended and were able to retrieve up to the final AI agent response.

However, when automating the retrieval process in production, you need to verify with the flows and environment you use whether all messages can always be retrieved immediately after the inquiry ends.

In preparation for retrieval failures, it would also be worth considering retries after a certain period of time and managing already-retrieved Contact IDs.

Consider Pagination

list-messages is a pagination-supported command.

Since the AWS CLI performs automatic pagination by default, the commands shown in this article will retrieve all messages even when they span multiple pages.

On the other hand, if --no-paginate is specified, only the first page will be retrieved. Also, if the number of items is limited with --max-items, use the returned token in --starting-token as needed to resume retrieval.

When implementing custom retrieval processing using the API or SDK, use the nextToken included in the response to retrieve the next page.

Summary

By retrieving the Session ARN from the Contact ID and specifying the extracted Assistant ID and Session ID in the ListMessages API, we were able to retrieve the conversation between the customer and AI agent.

The target of ListMessages is messages within the AI agent session. When a transcript of the entire call or processing traces are needed, use Contact Lens, ListSpans, CloudWatch Logs, and other features.

Share this article

AWSのお困り事はクラスメソッドへ