Customer-Aware Agent With Gemini 3.5 Flash and Mem0

Customer-Aware Agent With Gemini 3.5 Flash and Mem0

Quick Takeaways

Most AI support agents fail in the most expensive way possible, politely. They answer the ticket, but they make the customer repeat what your company already knows. If you are building an AI agent for customer support, memory should change the workflow, not just the greeting.

A customer-aware support agent is an AI agent that uses durable customer and account memory to decide the next workflow: answer, ask for missing information, escalate, notify a human, or update the support record.

In this walkthrough, we will build a production-mimicking support agent with:

By the end, your agent will do this:

The point of the architecture is simple:

Mem0 stores what the agent needs to remember. Gemini decides what to do with it.

What Makes a Support Agent Customer-Aware?

A customer-aware support agent does three things differently from a generic chatbot:

  1. It retrieves durable customer and account memory before deciding what to do.
  2. It applies policy to that memory, such as SLA rules or escalation thresholds.
  3. It turns the decision into an action through tools, then writes the outcome back to memory.

The important shift is from response generation to support orchestration.

Why Customer Memory Is Not Enough

For production support, that is too narrow. Support decisions usually depend on multiple scopes of context:

Memory scope What it stores Why it matters
Customer memory Tone preference, previous issues, prior promises, sentiment Helps the agent avoid asking the customer to repeat themselves
Account memory Plan, SLA, renewal date, account health, CSM owner Changes routing, priority, and escalation behavior
Ticket memory Current active issue, missing fields, and status Keeps the current workflow coherent
Team/policy context Refund rules, SLA rules, escalation criteria Keeps the agent aligned with support operations

In this demo, we intentionally separate customer memory from account memory. That matters because a user is not always the account. A developer on an Enterprise workspace, an admin on a Pro account, and a finance contact handling invoices may all need different contexts from the same company-level memory.

This is where naive support agents usually break.

1. Store Only User-Level Memory

If you store everything under a single user identity, you lose the distinction between the individual customer, the account they belong to, the current ticket, and the support team’s operating policy.

2. Confuse Policy With Memory

Do not bury SLA rules, refund policy, or escalation logic inside a user’s memory stream. Put policies in a knowledge base, config file, CMS, or document store designed for official support rules. Retrieve them separately and pass them to the model as policy context.

3. Personalize Tone But Not Workflow

In support, the bigger question is whether the agent should ask for more information, answer directly, escalate, create a ticket, notify a human, or update memory.

4. Actions Happened Without Calling Tools

If the agent tells a customer that something was escalated, your application should have a corresponding system action behind it: a ticket created, a handoff generated, a CSM notified, or a memory updated.

Demo: Building a Customer-Aware Agent with Mem0 and Gemini

This demo is designed as a before/after experiment. First, you run the workflow without seeding Mem0. Then, you click Seed Mem0.

System Architecture

The demo has two execution paths. Before seeding, Gemini runs as a baseline support agent with no persistent memory. After seeding, the same message goes through Mem0 retrieval first.

Step 1: Seed Durable Memories in Mem0

The Mem0 Platform API supports adding memories through POST /v3/memories/add/.

In the demo, each server start creates a fresh run namespace:

const DEMO_NAMESPACE = process.env.DEMO_NAMESPACE || "customer-aware-support-demo";
const DEMO_RUN_ID = process.env.DEMO_RUN_ID || createDemoRunId();
const EFFECTIVE_DEMO_NAMESPACE = `${DEMO_NAMESPACE}:run:${DEMO_RUN_ID}`;

Customer memories and account memories are stored under different IDs:

function scopedCustomerId(customerId) {
    return `${EFFECTIVE_DEMO_NAMESPACE}:customer:${customerId}`;
}
function scopedAccountId(accountId) {
    return `${EFFECTIVE_DEMO_NAMESPACE}:account:${accountId}`;
}

Step 2: Retrieve Customer and Account Context

When a user sends a support message, the app only searches Mem0 after the seed step has completed.

const [customerMemory, accountMemory] = mem0SeededForRun
? await Promise.all([
    mem0Search(message, customerUserId),
    mem0Search(message, accountUserId)
])
: [emptyMem0Envelope(),emptyMem0Envelope()];

Step 3: Give Gemini the Support Decision Packet

The server sends Gemini a compact decision packet.

Step 4: Define Gemini Tools

In this demo, We’ll be using Gemini 3.5 flash that calls the following tools through function calling:

Step 5: Execute Tools

The demo creates local operation logs for support actions.

Step 6: Send Function Results Back to Gemini

After executing tools, the app sends the function responses back to Gemini.

Step 7: Write Support Outcome Back to Mem0

The app only writes support outcomes back to Mem0 after the seed step has enabled Mem0 for the current run.

This is what makes the agent compound. A stateless support agent handles a ticket and forgets it.

Running the Demo

The demo app uses a small Node server and browser UI.

  1. Select a customer.
  2. Run the workflow once before seeding. This is the Gemini-only baseline.
  3. Click Seed Mem0.
  4. Run the same message again for the same customer.
  5. Compare the baseline response with the Mem0-aware response.

💡 The complete code is available on the GitHub repository .

Closing Thought

The best support agents are not just better writers, but are the ones who are better operators. They know when to ask for missing information, when to answer directly, when to escalate, when to notify a human, and what context to carry forward.

That requires two layers:

Mem0 handles the first layer. Gemini handles the second.