mcp-claude-duo/mcp-partner/tools/talk.js
StillHammer 66e5c677ea v3.0 - Conversation-based messaging system
Features:
- Direct conversations (1-to-1) auto-created and permanent
- Group conversations with leave/archive support
- Real-time messaging via long-polling
- Offline notifications via CLAUDE.md
- Auto-registration on MCP startup

Architecture:
- Broker: Express HTTP server + SQLite
- MCP Partner: Modular tools (one file per tool)
- Full documentation and API reference
2026-01-25 02:57:24 +07:00

91 lines
2.3 KiB
JavaScript

import { brokerFetch, myId, ensureRegistered } from "../shared.js";
export const definition = {
name: "talk",
description: "Envoie un message dans une conversation. Crée automatiquement une conv directe si besoin.",
inputSchema: {
type: "object",
properties: {
message: {
type: "string",
description: "Le message à envoyer",
},
to: {
type: "string",
description: "L'ID du destinataire (pour conv directe)",
},
conversation: {
type: "string",
description: "L'ID de la conversation (pour conv existante)",
},
},
required: ["message"],
},
};
export async function handler(args) {
try {
await ensureRegistered();
if (!args.to && !args.conversation) {
// Essayer de trouver un partenaire unique
const { partners } = await brokerFetch("/partners");
const others = partners?.filter((p) => p.id !== myId);
if (!others?.length) {
return {
content: [{ type: "text", text: "Aucun partenaire enregistré. Précise `to` ou `conversation`." }],
isError: true,
};
}
if (others.length === 1) {
args.to = others[0].id;
} else {
return {
content: [
{
type: "text",
text: `Plusieurs partenaires: ${others.map((p) => p.id).join(", ")}. Précise \`to\` ou \`conversation\`.`,
},
],
isError: true,
};
}
}
const response = await brokerFetch("/talk", {
method: "POST",
body: JSON.stringify({
fromId: myId,
to: args.to,
conversationId: args.conversation,
content: args.message,
}),
});
if (response.error) {
return {
content: [{ type: "text", text: `Erreur: ${response.error}\n${response.message || ""}` }],
isError: true,
};
}
const status = response.notified > 0
? `${response.notified} notifié(s) en temps réel`
: `${response.queued} en file d'attente`;
return {
content: [
{
type: "text",
text: `Message envoyé dans ${response.conversationId}\n${status}`,
},
],
};
} catch (error) {
return {
content: [{ type: "text", text: `Erreur: ${error.message}` }],
isError: true,
};
}
}