How to Build a customer support Agent Using LangChain in TypeScript for retail banking
A customer support agent for retail banking handles routine questions, guides customers through product information, and routes sensitive issues to the right human team. It matters because most bank support volume is repetitive, but every response still has compliance, audit, and data handling implications.
Architecture
Build this agent with a small set of components that keep it safe and useful in a regulated environment:
- •
Chat model layer
- •Use a hosted or private LLM behind LangChain’s
ChatOpenAIor equivalent. - •Keep temperature low for deterministic support responses.
- •Use a hosted or private LLM behind LangChain’s
- •
Policy and system prompt
- •Encode banking rules: no financial advice, no account access without auth, no PII leakage.
- •Force the agent to ask clarifying questions when intent is ambiguous.
- •
Retrieval layer
- •Use
VectorStoreRetrieverover approved bank knowledge: fees, card disputes, branch hours, loan FAQs. - •Separate public product content from internal runbooks.
- •Use
- •
Tool layer
- •Add narrow tools for safe actions like branch lookup, FAQ search, ticket creation, and case escalation.
- •Do not expose raw account actions unless you have authenticated session context and explicit authorization.
- •
Conversation memory
- •Store short-term context only.
- •Avoid persisting sensitive customer data unless your retention policy allows it.
- •
Audit logging
- •Log prompts, tool calls, model outputs, and final decisions with redaction.
- •Keep trace IDs so compliance can reconstruct what happened.
Implementation
1) Install dependencies and define the support tools
For retail banking, start with a small tool surface. The agent should answer FAQs and escalate when it hits anything involving account-specific data or regulated decisions.
npm install langchain @langchain/openai zod
import { z } from "zod";
import { DynamicStructuredTool } from "@langchain/core/tools";
export const branchLookupTool = new DynamicStructuredTool({
name: "branch_lookup",
description: "Find branch hours and locations from approved bank directory data.",
schema: z.object({
city: z.string().min(2),
}),
func: async ({ city }) => {
return JSON.stringify({
city,
branches: [
{ name: "Central Branch", hours: "Mon-Fri 9am-5pm" },
{ name: "North Branch", hours: "Mon-Sat 10am-4pm" },
],
});
},
});
export const createCaseTool = new DynamicStructuredTool({
name: "create_case",
description: "Create a customer support case for escalation to a human agent.",
schema: z.object({
category: z.enum(["card_dispute", "loan_query", "fraud", "general_support"]),
summary: z.string().min(10),
}),
func: async ({ category, summary }) => {
return JSON.stringify({
caseId: `CASE-${Date.now()}`,
category,
status: "queued_for_human_review",
summary,
});
},
});
2) Build the agent with a strict banking prompt
Use ChatOpenAI, ChatPromptTemplate, and createToolCallingAgent. The prompt should constrain behavior hard enough that the model cannot wander into advice or unsupported actions.
import { ChatOpenAI } from "@langchain/openai";
import { ChatPromptTemplate, MessagesPlaceholder } from "@langchain/core/prompts";
import { AgentExecutor, createToolCallingAgent } from "langchain/agents";
import { branchLookupTool, createCaseTool } from "./tools";
const llm = new ChatOpenAI({
modelName: "gpt-4o-mini",
temperature: 0,
});
const prompt = ChatPromptTemplate.fromMessages([
[
"system",
`You are a retail banking customer support agent.
Rules:
- Answer only using approved bank knowledge or tools.
- Never request full card numbers, passwords, OTPs, or PINs.
- Never provide financial advice or make eligibility decisions.
- If the user asks about account-specific data, fraud, disputes, or anything sensitive, escalate to a human.
- Be concise and professional.`,
],
["human", "{input}"],
new MessagesPlaceholder("agent_scratchpad"),
]);
const tools = [branchLookupTool, createCaseTool];
const agent = await createToolCallingAgent({
llm,
tools,
prompt,
});
export const executor = new AgentExecutor({
agent,
tools,
});
3) Add an API handler with redaction and audit logging
In production banking systems, you need traceability. Log what was asked and which tool was used, but redact obvious sensitive values before storage.
function redact(input: string) {
return input
.replace(/\b\d{13,19}\b/g, "[REDACTED_CARD]")
.replace(/\b\d{3}-\d{2}-\d{4}\b/g, "[REDACTED_ID]")
.replace(/\b\d{6}\b/g, "[REDACTED_OTP]");
}
export async function handleSupportMessage(userId: string, message: string) {
const sanitized = redact(message);
console.log(
JSON.stringify({
event: "bank_support_request",
userId,
message: sanitized,
timestamp: new Date().toISOString(),
})
);
const result = await executor.invoke({
input: sanitized,
});
console.log(
JSON.stringify({
event: "bank_support_response",
userId,
output: redact(String(result.output)),
timestamp: new Date().toISOString(),
})
);
return result.output;
}
4) Route unsafe requests to escalation
Do not let the model “try its best” on sensitive cases. If the user asks for balance checks, card blocks tied to identity verification, fraud claims, or loan decisions, send them to a human queue.
const unsafePatterns = [
/balance/i,
/card number/i,
/otp|one-time password/i,
];
export async function safeSupportHandler(userId: string, message: string) {
if (unsafePatterns.some((pattern) => pattern.test(message))) {
return executor.invoke({
input:
"Create an escalation case for this customer request. Do not answer directly.",
});
}
return handleSupportMessage(userId, message);
}
Production Considerations
- •
Data residency
- •Keep prompts and vector stores in-region if your bank operates under local residency rules.
- •Do not send customer chat logs across borders unless legal review has approved it.
- •
Compliance controls
- •Maintain prompt templates under change control.
- •Review system messages with legal/compliance teams because they are effectively policy code.
- •
Monitoring
Keep learning
- •The complete AI Agents Roadmap — my full 8-step breakdown
- •Free: The AI Agent Starter Kit — PDF checklist + starter code
- •Work with me — I build AI for banks and insurance companies
By Cyprian Aarons, AI Consultant at Topiax.
Want the complete 8-step roadmap?
Grab the free AI Agent Starter Kit — architecture templates, compliance checklists, and a 7-email deep-dive course.
Get the Starter Kit