Le Confidant MCP
An MCP server that allows AI assistants to read quantitative statistics from WhatsApp chat exports, such as message counts, reply times, and average lengths, while also providing public tools for link creation and text formatting.
Endpoint and access
No sign-in to connect and list tools. Individual tools may still need a vendor account, credentials, or permissions; check the documented prerequisites.
https://leconfidant.ai/api/mcpWhat you can do with it
- Read statistics from a connected WhatsApp analysis
- Create a wa.me link
- Format WhatsApp text
- Normalize phone numbers
Source and maintenance
Protocol and capabilities
- Server
- le-confidant 0.4.0
- MCP protocol
- 2025-06-18
- Tools
- 7 advertised
- Resources
- 1 advertised
- Resource templates
- 0 advertised
- Prompts
- Not advertised
{
"tools": {
"listChanged": true
},
"resources": {
"listChanged": true
}
}Server-provided instructions
Untrusted server output shown for inspection. It is not Koskamo guidance and is excluded from knowledge search.
Tools
7 advertised
generate_whatsapp_link — Create a WhatsApp click-to-chat link
Create a wa.me URL with an optional prefilled message for copying or sharing. Requires a valid phone number; does not verify WhatsApp registration. Inputs are processed by this server to return the result; this tool does not store or log phone numbers or text. It does not access an account or send messages.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"phone"
],
"properties": {
"phone": {
"type": "string",
"maxLength": 80,
"minLength": 1,
"description": "International phone number beginning with +, or a national number with defaultCountry."
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"message": {
"type": "string",
"maxLength": 4000
},
"defaultCountry": {
"type": "string",
"maxLength": 2,
"minLength": 2
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"e164",
"url",
"messageSent"
],
"properties": {
"url": {
"type": "string",
"format": "uri"
},
"e164": {
"type": "string"
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"messageSent": {
"type": "boolean",
"const": false
}
},
"additionalProperties": false
}{
"title": "Create a WhatsApp click-to-chat link",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}format_whatsapp_text — Format text for WhatsApp
Convert the user's Markdown source to text ready to paste into WhatsApp. Before calling, copy the supplied source unchanged into text: do not Markdown-escape it or pre-convert it. Example: source **Meeting tomorrow** must be passed as **Meeting tomorrow**; the tool returns *Meeting tomorrow*. Preserve backslashes the user actually supplied, but never insert extra ones. After calling, display structuredContent.formattedText verbatim in a plain-text fenced code block, without escaping or reformatting it. Supports # headings, bold, italics, strikethrough, lists and links. Preserves URL destinations, literal text and fenced/inline code. Unsupported blocks remain literal; does not render HTML, summarize or translate. Inputs are processed by this server to return the result; this tool does not store or log phone numbers or text. It does not access an account or send messages.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"text"
],
"properties": {
"text": {
"type": "string",
"maxLength": 12000,
"minLength": 1,
"description": "The user's original Markdown source, up to 12,000 UTF-16 code units. Copy it unchanged: do not render it, pre-convert formatting, or add backslashes before Markdown punctuation. For **Meeting tomorrow**, pass exactly **Meeting tomorrow** as the decoded text value. Preserve backslashes only when present in the user's source; normal JSON string encoding must not change the decoded text."
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"formattedText",
"messageSent"
],
"properties": {
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"messageSent": {
"type": "boolean",
"const": false
},
"formattedText": {
"type": "string",
"description": "Finished WhatsApp text, ready to copy. Display this value verbatim in a plain-text fenced code block; do not add backslash escapes, change emphasis markers, or format it again. Choose a fence that does not conflict with code already in the returned text."
}
},
"additionalProperties": false
}{
"title": "Format text for WhatsApp",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}normalize_whatsapp_numbers — Normalize phone numbers for WhatsApp
Validate up to 100 phone numbers and return E.164 numbers and wa.me links with per-row status and duplicate positions. National numbers require defaultCountry. Never guess a country from language. Does not check WhatsApp registration or contact people. Inputs are processed by this server to return the result; this tool does not store or log phone numbers or text. It does not access an account or send messages.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"numbers"
],
"properties": {
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"numbers": {
"type": "array",
"items": {
"type": "string",
"maxLength": 80,
"minLength": 1
},
"maxItems": 100,
"minItems": 1
},
"defaultCountry": {
"type": "string",
"maxLength": 2,
"minLength": 2,
"description": "Country for national numbers; never inferred from locale."
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"rows",
"validCount",
"uniqueValidCount",
"invalidCount",
"registrationChecked"
],
"properties": {
"rows": {
"type": "array",
"items": {
"anyOf": [
{
"type": "object",
"required": [
"index",
"valid",
"error"
],
"properties": {
"error": {
"type": "string",
"const": "invalid_number"
},
"index": {
"type": "integer",
"minimum": 0
},
"valid": {
"type": "boolean",
"const": false
}
},
"additionalProperties": false
},
{
"type": "object",
"required": [
"index",
"valid",
"e164",
"waLink"
],
"properties": {
"e164": {
"type": "string"
},
"index": {
"type": "integer",
"minimum": 0
},
"valid": {
"type": "boolean",
"const": true
},
"waLink": {
"type": "string",
"format": "uri"
},
"duplicateOf": {
"type": "integer",
"minimum": 0
}
},
"additionalProperties": false
}
]
},
"maxItems": 100
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"validCount": {
"type": "integer",
"maximum": 100,
"minimum": 0
},
"invalidCount": {
"type": "integer",
"maximum": 100,
"minimum": 0
},
"uniqueValidCount": {
"type": "integer",
"maximum": 100,
"minimum": 0
},
"registrationChecked": {
"type": "boolean",
"const": false
}
},
"additionalProperties": false
}{
"title": "Normalize phone numbers for WhatsApp",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}demo_whatsapp_wrapped — Show a fictional WhatsApp Wrapped recap
Show a synthetic WhatsApp recap without an account, upload or private conversation access. Use only for a demo or example, never to answer questions about the user's real conversation. All numbers are fictional and fixed; no relationship diagnosis. Returns a text and structured recap, without image export.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"properties": {
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"source",
"title",
"scope",
"participants",
"totalMessages",
"activeDays",
"topEmojis",
"limitations",
"learnMore"
],
"properties": {
"scope": {
"type": "string",
"const": "whole_conversation"
},
"title": {
"type": "string"
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"source": {
"type": "object",
"required": [
"fictional",
"synthetic",
"privateDataAccessed"
],
"properties": {
"fictional": {
"type": "boolean",
"const": true
},
"synthetic": {
"type": "boolean",
"const": true
},
"privateDataAccessed": {
"type": "boolean",
"const": false
}
},
"additionalProperties": false
},
"learnMore": {
"type": "object",
"required": [
"title",
"url"
],
"properties": {
"url": {
"type": "string",
"format": "uri"
},
"title": {
"type": "string"
}
},
"additionalProperties": false
},
"topEmojis": {
"type": "array",
"items": {
"type": "object",
"required": [
"emoji",
"count"
],
"properties": {
"count": {
"type": "integer",
"minimum": 0
},
"emoji": {
"type": "string"
}
},
"additionalProperties": false
},
"maxItems": 3
},
"activeDays": {
"type": "integer",
"minimum": 0
},
"limitations": {
"type": "array",
"items": {
"type": "string"
},
"maxItems": 4
},
"participants": {
"type": "array",
"items": {
"type": "object",
"required": [
"label",
"messages",
"share"
],
"properties": {
"label": {
"enum": [
"A",
"B"
],
"type": "string"
},
"share": {
"type": "number",
"maximum": 1,
"minimum": 0
},
"messages": {
"type": "integer",
"minimum": 0
}
},
"additionalProperties": false
},
"maxItems": 2,
"minItems": 2
},
"totalMessages": {
"type": "integer",
"minimum": 0
}
},
"additionalProperties": false
}{
"title": "Show a fictional WhatsApp Wrapped recap",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}style_whatsapp_text — Restyle text with decorative letters
Rewrite the user's text in one decorative Unicode style to paste into WhatsApp. Styles: bold, italic, monospace, bubble, gothic, double (double-struck), strikethrough, upside-down. Call it once the user has picked a style from this list. These are lookalike characters, not real fonts: accented letters and digits usually stay plain, and screen readers can read the result badly. After calling, display structuredContent.styledText verbatim in a plain-text fenced code block. Inputs are processed by this server to return the result; this tool does not store or log phone numbers or text. It does not access an account or send messages.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"text",
"style"
],
"properties": {
"text": {
"type": "string",
"maxLength": 4000,
"minLength": 1,
"description": "The user's text, copied unchanged."
},
"style": {
"enum": [
"bold",
"italic",
"monospace",
"bubble",
"gothic",
"double",
"strikethrough",
"upside-down"
],
"type": "string",
"description": "The style the user chose."
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"style",
"styledText",
"messageSent"
],
"properties": {
"style": {
"enum": [
"bold",
"italic",
"monospace",
"bubble",
"gothic",
"double",
"strikethrough",
"upside-down"
],
"type": "string"
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"styledText": {
"type": "string",
"description": "Finished text, ready to copy. Display this value verbatim in a plain-text fenced code block; do not normalize, translate or format it again."
},
"messageSent": {
"type": "boolean",
"const": false
}
},
"additionalProperties": false
}{
"title": "Restyle text with decorative letters",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}get_conversation_snapshot — Read whole-session statistics
Use only to retrieve or explain WHOLE-SESSION numerical statistics from the user's explicitly authorized WhatsApp export analysis. DO NOT call for date-window, month-to-month, trend or period-comparison requests, even to check available data. For example, 'Compare September and November in my own connected WhatsApp analysis' needs NO tool call: explain that period comparison is unavailable. This tool returns only stored whole-session totals and cannot answer that request. For supported requests, returns neutral A/B labels, counts/shares, starts, reply timing/sample sizes, mean message length, definitions, limitations and expiry from the OAuth-selected session. No raw messages, names, excerpts, paid insights or new analysis. Set locale to the user's supported language.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"properties": {
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
}
},
"additionalProperties": false
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"kind",
"source",
"expiresAt",
"snapshot",
"definitions",
"limitations"
],
"properties": {
"kind": {
"type": "string",
"const": "free_snapshot"
},
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
},
"source": {
"type": "object",
"required": [
"fictional",
"analysis",
"participantsArePseudonyms"
],
"properties": {
"analysis": {
"type": "string",
"const": "stored_free_quantitative"
},
"fictional": {
"type": "boolean"
},
"participantsArePseudonyms": {
"type": "boolean",
"const": true
}
},
"additionalProperties": false
},
"snapshot": {
"type": "object",
"required": [
"totalMessages",
"participants"
],
"properties": {
"participants": {
"type": "array",
"items": {
"type": "object",
"required": [
"label",
"messages",
"messageSharePercent",
"observedStarts",
"replyPairs",
"meanReplyMinutes",
"medianReplyMinutes",
"p25ReplyMinutes",
"p75ReplyMinutes",
"meanMessageCharacters"
],
"properties": {
"label": {
"enum": [
"A",
"B"
],
"type": "string"
},
"messages": {
"type": "integer",
"minimum": 0
},
"replyPairs": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
},
"observedStarts": {
"anyOf": [
{
"type": "number",
"minimum": 0
},
{
"type": "null"
}
]
},
"p25ReplyMinutes": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
},
"p75ReplyMinutes": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
},
"meanReplyMinutes": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
},
"medianReplyMinutes": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
},
"messageSharePercent": {
"anyOf": [
{
"type": "number",
"maximum": 100,
"minimum": 0
},
{
"type": "null"
}
]
},
"meanMessageCharacters": {
"$ref": "#/properties/snapshot/properties/participants/items/properties/observedStarts"
}
},
"additionalProperties": false
},
"maxItems": 2,
"minItems": 2
},
"totalMessages": {
"type": "integer",
"minimum": 0
}
},
"additionalProperties": false
},
"expiresAt": {
"type": "string",
"format": "date-time"
},
"definitions": {
"type": "object",
"required": [
"messages",
"replies",
"initiation",
"labels"
],
"properties": {
"labels": {
"type": "string"
},
"replies": {
"type": "string"
},
"messages": {
"type": "string"
},
"initiation": {
"type": "string"
}
},
"additionalProperties": false
},
"limitations": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
}{
"title": "Read whole-session statistics",
"readOnlyHint": true,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": false
}disconnect_conversation — Disconnect your selected conversation
Use only when the user explicitly asks to disconnect or revoke this connection. Permanently revoke its current OAuth grant immediately; the revoked credential cannot be restored. Fresh explicit consent creates a new grant while the original session is eligible. Stops future reads without deleting the source session or results already in this conversation. Other connections can be revoked on the website. This tool changes access and is destructive access revocation; it does not retrieve statistics or answer period comparisons.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"properties": {
"locale": {
"enum": [
"en",
"es",
"pt-br",
"de",
"fr",
"it"
],
"type": "string",
"default": "en"
}
},
"additionalProperties": false
}{
"title": "Disconnect your selected conversation",
"readOnlyHint": false,
"openWorldHint": false,
"idempotentHint": true,
"destructiveHint": true
}Prompts
Not advertised
Resources
1 advertised
conversation-results-card — Le Confidant results
ui://le-confidant/results-v3.html30-day availability
Aggregated from read-only remote checks; this is not a tool-execution or security guarantee.
- Successful checks
- 1 of 1 (100%)
- Average latency
- 745 ms
- 95th percentile latency
- 745 ms
Maintenance history
Public check and source-refresh events. Editorial and ownership records remain private.
- · probe · passed · 745 ms · metadata changed · 7 tool(s), 1 resource(s), 0 resource template(s)
Connect from your client
Each snippet registers the same endpoint; pick the client you use.
Claude Code
claude mcp add --transport http le-confidant-mcp https://leconfidant.ai/api/mcpCodex
codex mcp add le-confidant-mcp --url https://leconfidant.ai/api/mcpCursor
{
"mcpServers": {
"le-confidant-mcp": {
"url": "https://leconfidant.ai/api/mcp"
}
}
}Cline
{
"mcpServers": {
"le-confidant-mcp": {
"type": "streamableHttp",
"url": "https://leconfidant.ai/api/mcp",
"disabled": false
}
}
}VS Code
{
"servers": {
"le-confidant-mcp": {
"type": "http",
"url": "https://leconfidant.ai/api/mcp"
}
}
}Gemini CLI
gemini mcp add --transport http le-confidant-mcp https://leconfidant.ai/api/mcpClaude Desktop
{
"mcpServers": {
"le-confidant-mcp": {
"url": "https://leconfidant.ai/api/mcp"
}
}
}Windsurf
{
"mcpServers": {
"le-confidant-mcp": {
"serverUrl": "https://leconfidant.ai/api/mcp"
}
}
}Let your agent find its tools
Find servers like Le Confidant MCP from your agent. Add Koskamo once to search the index for endpoints, access requirements, and client setup. Public discovery needs no key.
Other productivity and knowledge servers
Do you run Le Confidant MCP?
Prove ownership with a DNS record, a well-known file, or your Official MCP Registry entry, and your edits publish immediately. Proofs are re-checked weekly; admins can still hide or remove a listing.