@lizzythelizard/whatsapp-mcp 0.1.5 → 0.1.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +6 -2
- package/dist/index.js.map +1 -1
- package/dist/syncManager.d.ts +29 -0
- package/dist/syncManager.d.ts.map +1 -0
- package/dist/syncManager.js +79 -0
- package/dist/syncManager.js.map +1 -0
- package/dist/tools/chatTools.d.ts +5 -0
- package/dist/tools/chatTools.d.ts.map +1 -0
- package/dist/tools/chatTools.js +34 -0
- package/dist/tools/chatTools.js.map +1 -0
- package/dist/tools/common.d.ts +49 -0
- package/dist/tools/common.d.ts.map +1 -0
- package/dist/tools/common.js +18 -0
- package/dist/tools/common.js.map +1 -0
- package/dist/tools/contactTools.d.ts +4 -0
- package/dist/tools/contactTools.d.ts.map +1 -0
- package/dist/tools/contactTools.js +5 -0
- package/dist/tools/contactTools.js.map +1 -0
- package/dist/tools/messageTools.d.ts +5 -0
- package/dist/tools/messageTools.d.ts.map +1 -0
- package/dist/tools/messageTools.js +21 -0
- package/dist/tools/messageTools.js.map +1 -0
- package/dist/tools.d.ts +1 -4
- package/dist/tools.d.ts.map +1 -1
- package/dist/tools.js +60 -69
- package/dist/tools.js.map +1 -1
- package/package.json +60 -59
package/dist/index.js
CHANGED
|
@@ -5,7 +5,9 @@ import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
|
5
5
|
import { createStore } from './store.js';
|
|
6
6
|
import { createHandler } from './sync.js';
|
|
7
7
|
import { promises as fsp } from 'fs';
|
|
8
|
-
import {
|
|
8
|
+
import { registerContactResources } from './tools/contactTools.js';
|
|
9
|
+
import { registerChatTools } from './tools/chatTools.js';
|
|
10
|
+
import { registerMessageTools } from './tools/messageTools.js';
|
|
9
11
|
const dataDir = process.env.DATA_DIR ?? './data';
|
|
10
12
|
async function readDataFromFile() {
|
|
11
13
|
const canAccess = await fsp.access(dataDir).then(() => true).catch(() => false);
|
|
@@ -30,7 +32,9 @@ async function main() {
|
|
|
30
32
|
const inputData = await readDataFromFile();
|
|
31
33
|
const whatsappStore = createStore(writeDataToFile, inputData);
|
|
32
34
|
const whatsappSync = createHandler(whatsappStore);
|
|
33
|
-
|
|
35
|
+
registerContactResources(server, whatsappStore);
|
|
36
|
+
registerChatTools(server, whatsappStore, whatsappSync);
|
|
37
|
+
registerMessageTools(server, whatsappStore, whatsappSync);
|
|
34
38
|
await server.connect(transport);
|
|
35
39
|
console.info('whatsapp-mcp server running on stdio');
|
|
36
40
|
}
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAA;AAChF,OAAO,GAAG,MAAM,iBAAiB,CAAC,OAAO,IAAI,EAAE,MAAM,EAAE,CAAA;AACvD,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AACnE,OAAO,EAAE,WAAW,EAAa,MAAM,YAAY,CAAA;AACnD,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAA;AACzC,OAAO,EAAE,QAAQ,IAAI,GAAG,EAAE,MAAM,IAAI,CAAA;AACpC,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { UserSession } from '@/app/shared/auth/auth';
|
|
2
|
+
import { SyncHandler } from './sync';
|
|
3
|
+
import { Mutex } from 'async-mutex';
|
|
4
|
+
export type RunningSyncStatus = {
|
|
5
|
+
state: 'connecting';
|
|
6
|
+
} | {
|
|
7
|
+
state: 'qr';
|
|
8
|
+
data: string;
|
|
9
|
+
} | {
|
|
10
|
+
state: 'initialsync';
|
|
11
|
+
} | {
|
|
12
|
+
state: 'ready';
|
|
13
|
+
} | {
|
|
14
|
+
state: 'failed';
|
|
15
|
+
data: string;
|
|
16
|
+
};
|
|
17
|
+
interface RunningSync {
|
|
18
|
+
status: RunningSyncStatus;
|
|
19
|
+
timeout: NodeJS.Timeout;
|
|
20
|
+
handler: SyncHandler;
|
|
21
|
+
}
|
|
22
|
+
declare global {
|
|
23
|
+
var runningSyncs: Map<string, RunningSync> | undefined;
|
|
24
|
+
var mutex: Mutex | undefined;
|
|
25
|
+
}
|
|
26
|
+
export declare function getRunningSyncData(user: UserSession): RunningSyncStatus;
|
|
27
|
+
export declare function triggerWhatsappSync(user: UserSession): Promise<void>;
|
|
28
|
+
export {};
|
|
29
|
+
//# sourceMappingURL=syncManager.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"syncManager.d.ts","sourceRoot":"","sources":["../src/syncManager.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAA;AAIpD,OAAO,EAAa,WAAW,EAAE,MAAM,QAAQ,CAAA;AAC/C,OAAO,EAAE,KAAK,EAAE,MAAM,aAAa,CAAA;AAEnC,MAAM,MAAM,iBAAiB,GAAG;IAAE,KAAK,EAAE,YAAY,CAAA;CAAE,GACnD;IAAE,KAAK,EAAE,IAAI,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,GAC7B;IAAE,KAAK,EAAE,aAAa,CAAA;CAAE,GACxB;IAAE,KAAK,EAAE,OAAO,CAAA;CAAE,GAClB;IAAE,KAAK,EAAE,QAAQ,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAAA;AAErC,UAAU,WAAW;IACnB,MAAM,EAAE,iBAAiB,CAAA;IACzB,OAAO,EAAE,MAAM,CAAC,OAAO,CAAA;IACvB,OAAO,EAAE,WAAW,CAAA;CACrB;AAED,OAAO,CAAC,MAAM,CAAC;IACb,IAAI,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,WAAW,CAAC,GAAG,SAAS,CAAA;IACtD,IAAI,KAAK,EAAE,KAAK,GAAG,SAAS,CAAA;CAC7B;AAED,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,WAAW,GAAG,iBAAiB,CAEvE;AAED,wBAAsB,mBAAmB,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CAwB1E"}
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
'use server';
|
|
2
|
+
import { logger } from '@/app/shared/logger';
|
|
3
|
+
import { transactional } from '@/app/shared/_external/db/access';
|
|
4
|
+
import { logEvent } from '@/app/shared/_data/Event';
|
|
5
|
+
import { startSync } from './sync';
|
|
6
|
+
import { Mutex } from 'async-mutex';
|
|
7
|
+
export function getRunningSyncData(user) {
|
|
8
|
+
return getSync(user).status;
|
|
9
|
+
}
|
|
10
|
+
export async function triggerWhatsappSync(user) {
|
|
11
|
+
globalThis.mutex ??= new Mutex();
|
|
12
|
+
await globalThis.mutex.runExclusive(async () => {
|
|
13
|
+
globalThis.runningSyncs ??= new Map();
|
|
14
|
+
const existing = globalThis.runningSyncs.get(user.email);
|
|
15
|
+
if (existing) {
|
|
16
|
+
clearTimeout(existing.timeout);
|
|
17
|
+
existing.timeout = setTimeout(() => { existing.handler.close(); }, 5 * 1000);
|
|
18
|
+
return;
|
|
19
|
+
}
|
|
20
|
+
logger.debug(`Start whatsapp sync for ${user.email}`);
|
|
21
|
+
const handler = await startSync(user.email);
|
|
22
|
+
handler.onQrCode((qr) => { qrCallback(user, qr); });
|
|
23
|
+
handler.onAuth(() => { authCallback(user); });
|
|
24
|
+
handler.onReady(() => { readyCallback(user); });
|
|
25
|
+
handler.onFinished((error) => { finishedCallback(user, error); });
|
|
26
|
+
handler.start();
|
|
27
|
+
const runningSync = {
|
|
28
|
+
status: { state: 'connecting' },
|
|
29
|
+
timeout: setTimeout(() => { closeSync(user); }, 5 * 1000),
|
|
30
|
+
handler,
|
|
31
|
+
};
|
|
32
|
+
globalThis.runningSyncs.set(user.email, runningSync);
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
function qrCallback(user, qr) {
|
|
36
|
+
const message = `WhatsApp authentication requires QR code for user ${user.email}`;
|
|
37
|
+
logger.info(message);
|
|
38
|
+
void transactional(async (c) => { await logEvent(c, 'INFO', message); });
|
|
39
|
+
const runningSync = getSync(user);
|
|
40
|
+
runningSync.status = { state: 'qr', data: qr };
|
|
41
|
+
}
|
|
42
|
+
function authCallback(user) {
|
|
43
|
+
const message = `WhatsApp authentication successful for user ${user.email}`;
|
|
44
|
+
logger.info(message);
|
|
45
|
+
void transactional(async (c) => { await logEvent(c, 'INFO', message); });
|
|
46
|
+
const runningSync = getSync(user);
|
|
47
|
+
runningSync.status = { state: 'initialsync' };
|
|
48
|
+
}
|
|
49
|
+
function readyCallback(user) {
|
|
50
|
+
logger.debug(`WhatsApp is ready for user ${user.email}`);
|
|
51
|
+
const runningSync = getSync(user);
|
|
52
|
+
runningSync.status = { state: 'ready' };
|
|
53
|
+
}
|
|
54
|
+
function finishedCallback(user, error) {
|
|
55
|
+
if (!error) {
|
|
56
|
+
logger.debug('Closing WhatsApp sync handler after successful completion');
|
|
57
|
+
globalThis.runningSyncs?.delete(user.email);
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
60
|
+
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
|
|
61
|
+
const message = `WhatsApp sync failed for user ${user.email}: ${errorMessage}`;
|
|
62
|
+
logger.error(message, error);
|
|
63
|
+
void transactional(async (c) => { await logEvent(c, 'ERROR', message); });
|
|
64
|
+
const runningSync = getSync(user);
|
|
65
|
+
runningSync.status = { state: 'failed', data: message };
|
|
66
|
+
}
|
|
67
|
+
function closeSync(user) {
|
|
68
|
+
logger.info('WhatsApp sync timeout reached, closing sync handler');
|
|
69
|
+
const runningSync = getSync(user);
|
|
70
|
+
globalThis.runningSyncs?.delete(user.email);
|
|
71
|
+
runningSync.handler.close();
|
|
72
|
+
}
|
|
73
|
+
function getSync(user) {
|
|
74
|
+
const runningSync = globalThis.runningSyncs?.get(user.email);
|
|
75
|
+
if (!runningSync)
|
|
76
|
+
throw new Error(`No running WhatsApp sync found for user ${user.email}`);
|
|
77
|
+
return runningSync;
|
|
78
|
+
}
|
|
79
|
+
//# sourceMappingURL=syncManager.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"syncManager.js","sourceRoot":"","sources":["../src/syncManager.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import { type WhatsAppStore } from '../store.js';
|
|
3
|
+
import { WhatsAppHandler } from '../sync.js';
|
|
4
|
+
export declare function registerChatTools(server: McpServer, store: WhatsAppStore, sync: WhatsAppHandler): void;
|
|
5
|
+
//# sourceMappingURL=chatTools.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chatTools.d.ts","sourceRoot":"","sources":["../../src/tools/chatTools.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AACnE,OAAO,EAAE,KAAK,aAAa,EAAE,MAAM,aAAa,CAAA;AAChD,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAA;AAI5C,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,SAAS,EAAE,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,eAAe,QAkC/F"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import z from 'zod';
|
|
2
|
+
import { JidSchema, registerEntityResources, toCallResult, toCallError } from './common.js';
|
|
3
|
+
export function registerChatTools(server, store, sync) {
|
|
4
|
+
registerEntityResources(server, 'chats', 'chat', () => store.getChats(), id => store.getChat(id), c => `chats://app/${c.id}`, c => c.name ?? c.id);
|
|
5
|
+
server.registerTool('set_chat_archived', { description: 'Set a WhatsApp chat as archived or unarchived.', inputSchema: ArchiveChatSchema }, async (args) => {
|
|
6
|
+
try {
|
|
7
|
+
await sync.setArchived(args.jid, args.archived);
|
|
8
|
+
return toCallResult(`Chat ${args.jid} archived status set to ${String(args.archived)}`);
|
|
9
|
+
}
|
|
10
|
+
catch (error) {
|
|
11
|
+
return toCallError(error);
|
|
12
|
+
}
|
|
13
|
+
});
|
|
14
|
+
server.registerTool('set_chat_read', { description: 'Set a WhatsApp chat as read or unread.', inputSchema: ReadChatSchema }, async (args) => {
|
|
15
|
+
try {
|
|
16
|
+
await sync.setRead(args.jid, args.read);
|
|
17
|
+
return toCallResult(`Chat ${args.jid} read status set to ${String(args.read)}`);
|
|
18
|
+
}
|
|
19
|
+
catch (error) {
|
|
20
|
+
return toCallError(error);
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
const ArchiveChatSchema = z.object({
|
|
25
|
+
jid: JidSchema,
|
|
26
|
+
archived: z.boolean()
|
|
27
|
+
.describe('Whether the chat should be archived (true) or unarchived (false).'),
|
|
28
|
+
});
|
|
29
|
+
const ReadChatSchema = z.object({
|
|
30
|
+
jid: JidSchema,
|
|
31
|
+
read: z.boolean()
|
|
32
|
+
.describe('Whether the chat should be marked as read (true) or unread (false).'),
|
|
33
|
+
});
|
|
34
|
+
//# sourceMappingURL=chatTools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chatTools.js","sourceRoot":"","sources":["../../src/tools/chatTools.ts"],"names":[],"mappings":"AAGA,OAAO,CAAC,MAAM,KAAK,CAAA;AACnB,OAAO,EAAE,SAAS,EAAE,uBAAuB,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,aAAa,CAAA;AAE3F,MAAM,UAAU,iBAAiB,CAAC,MAAiB,EAAE,KAAoB,EAAE,IAAqB;IAC9F,uBAAuB,CACrB,MAAM,EAAE,OAAO,EAAE,MAAM,EACvB,GAAG,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,EAAE,CAAC,EAC/C,CAAC,CAAC,EAAE,CAAC,eAAe,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,EAAE,CAChD,CAAA;IAED,MAAM,CAAC,YAAY,CACjB,mBAAmB,EACnB,EAAE,WAAW,EAAE,gDAAgD,EAAE,WAAW,EAAE,iBAAiB,EAAE,EACjG,KAAK,EAAE,IAAI,EAAE,EAAE;QACb,IAAI,CAAC;YACH,MAAM,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAA;YAC/C,OAAO,YAAY,CAAC,QAAQ,IAAI,CAAC,GAAG,2BAA2B,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAA;QACzF,CAAC;QACD,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,WAAW,CAAC,KAAc,CAAC,CAAA;QACpC,CAAC;IACH,CAAC,CACF,CAAA;IAED,MAAM,CAAC,YAAY,CACjB,eAAe,EACf,EAAE,WAAW,EAAE,wCAAwC,EAAE,WAAW,EAAE,cAAc,EAAE,EACtF,KAAK,EAAE,IAAI,EAAE,EAAE;QACb,IAAI,CAAC;YACH,MAAM,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,IAAI,CAAC,CAAA;YACvC,OAAO,YAAY,CAAC,QAAQ,IAAI,CAAC,GAAG,uBAAuB,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAA;QACjF,CAAC;QACD,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,WAAW,CAAC,KAAc,CAAC,CAAA;QACpC,CAAC;IACH,CAAC,CACF,CAAA;AACH,CAAC;AAED,MAAM,iBAAiB,GAAG,CAAC,CAAC,MAAM,CAAC;IACjC,GAAG,EAAE,SAAS;IACd,QAAQ,EAAE,CAAC,CAAC,OAAO,EAAE;SAClB,QAAQ,CAAC,mEAAmE,CAAC;CACjF,CAAC,CAAA;AAEF,MAAM,cAAc,GAAG,CAAC,CAAC,MAAM,CAAC;IAC9B,GAAG,EAAE,SAAS;IACd,IAAI,EAAE,CAAC,CAAC,OAAO,EAAE;SACd,QAAQ,CAAC,qEAAqE,CAAC;CACnF,CAAC,CAAA"}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import { type CallToolResult, type ListResourcesResult, type ReadResourceResult } from '@modelcontextprotocol/sdk/types.js';
|
|
3
|
+
import z from 'zod';
|
|
4
|
+
export declare const toReadResource: (contents: ReadResourceResult["contents"]) => {
|
|
5
|
+
contents: ({
|
|
6
|
+
uri: string;
|
|
7
|
+
text: string;
|
|
8
|
+
mimeType?: string | undefined;
|
|
9
|
+
_meta?: {
|
|
10
|
+
[x: string]: unknown;
|
|
11
|
+
} | undefined;
|
|
12
|
+
} | {
|
|
13
|
+
uri: string;
|
|
14
|
+
blob: string;
|
|
15
|
+
mimeType?: string | undefined;
|
|
16
|
+
_meta?: {
|
|
17
|
+
[x: string]: unknown;
|
|
18
|
+
} | undefined;
|
|
19
|
+
})[];
|
|
20
|
+
};
|
|
21
|
+
export declare const toListResource: (resources: ListResourcesResult["resources"]) => {
|
|
22
|
+
resources: {
|
|
23
|
+
uri: string;
|
|
24
|
+
name: string;
|
|
25
|
+
description?: string | undefined;
|
|
26
|
+
mimeType?: string | undefined;
|
|
27
|
+
size?: number | undefined;
|
|
28
|
+
annotations?: {
|
|
29
|
+
audience?: ("user" | "assistant")[] | undefined;
|
|
30
|
+
priority?: number | undefined;
|
|
31
|
+
lastModified?: string | undefined;
|
|
32
|
+
} | undefined;
|
|
33
|
+
_meta?: {
|
|
34
|
+
[x: string]: unknown;
|
|
35
|
+
} | undefined;
|
|
36
|
+
icons?: {
|
|
37
|
+
src: string;
|
|
38
|
+
mimeType?: string | undefined;
|
|
39
|
+
sizes?: string[] | undefined;
|
|
40
|
+
theme?: "light" | "dark" | undefined;
|
|
41
|
+
}[] | undefined;
|
|
42
|
+
title?: string | undefined;
|
|
43
|
+
}[];
|
|
44
|
+
};
|
|
45
|
+
export declare const toCallResult: (text: string) => CallToolResult;
|
|
46
|
+
export declare const toCallError: (error: Error) => CallToolResult;
|
|
47
|
+
export declare function registerEntityResources<T>(server: McpServer, pluralType: string, singularType: string, getAll: () => T[], get: (id: string) => T | undefined, toUri: (entity: T) => string, toName: (entity: T) => string): void;
|
|
48
|
+
export declare const JidSchema: z.ZodUnion<readonly [z.ZodString, z.ZodString]>;
|
|
49
|
+
//# sourceMappingURL=common.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.d.ts","sourceRoot":"","sources":["../../src/tools/common.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAoB,MAAM,yCAAyC,CAAA;AACrF,OAAO,EAAE,KAAK,cAAc,EAAE,KAAK,mBAAmB,EAAE,KAAK,kBAAkB,EAAE,MAAM,oCAAoC,CAAA;AAC3H,OAAO,CAAC,MAAM,KAAK,CAAA;AAEnB,eAAO,MAAM,cAAc,GAAI,UAAU,kBAAkB,CAAC,UAAU,CAAC;;;;;;;;;;;;;;;;CAAmB,CAAA;AAC1F,eAAO,MAAM,cAAc,GAAI,WAAW,mBAAmB,CAAC,WAAW,CAAC;;;;;;;;;;;;;;;;;;;;;;;CAAoB,CAAA;AAC9F,eAAO,MAAM,YAAY,GAAI,MAAM,MAAM,KAAG,cAAyE,CAAA;AACrH,eAAO,MAAM,WAAW,GAAI,OAAO,KAAK,KAAG,cAAmG,CAAA;AAE9I,wBAAgB,uBAAuB,CAAC,CAAC,EACvC,MAAM,EAAE,SAAS,EACjB,UAAU,EAAE,MAAM,EAClB,YAAY,EAAE,MAAM,EACpB,MAAM,EAAE,MAAM,CAAC,EAAE,EACjB,GAAG,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,CAAC,GAAG,SAAS,EAClC,KAAK,EAAE,CAAC,MAAM,EAAE,CAAC,KAAK,MAAM,EAC5B,MAAM,EAAE,CAAC,MAAM,EAAE,CAAC,KAAK,MAAM,QAoB9B;AAED,eAAO,MAAM,SAAS,iDAG6H,CAAA"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ResourceTemplate } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import z from 'zod';
|
|
3
|
+
export const toReadResource = (contents) => ({ contents });
|
|
4
|
+
export const toListResource = (resources) => ({ resources });
|
|
5
|
+
export const toCallResult = (text) => ({ content: [{ type: 'text', text }], isError: false });
|
|
6
|
+
export const toCallError = (error) => ({ content: [{ type: 'text', text: `Error: ${error.message}` }], isError: true });
|
|
7
|
+
export function registerEntityResources(server, pluralType, singularType, getAll, get, toUri, toName) {
|
|
8
|
+
const toResource = (entity) => entity ? [{ uri: toUri(entity), mimeType: 'application/json', text: JSON.stringify(entity) }] : [];
|
|
9
|
+
server.registerResource(pluralType, `${pluralType}://app`, { title: `All WhatsApp ${pluralType}`, description: `List WhatsApp ${pluralType}`, mimeType: 'application/json' }, () => toReadResource(getAll().flatMap(toResource)));
|
|
10
|
+
server.registerResource(singularType, new ResourceTemplate(`${pluralType}://app/{${singularType}Id}`, {
|
|
11
|
+
list: () => toListResource(getAll().map(e => ({ uri: toUri(e), name: toName(e) }))),
|
|
12
|
+
}), { title: `A single WhatsApp ${singularType}`, description: `Details of a single WhatsApp ${singularType}`, mimeType: 'application/json' }, (_, params) => toReadResource(toResource(get(params[`${singularType}Id`]))));
|
|
13
|
+
}
|
|
14
|
+
export const JidSchema = z.union([
|
|
15
|
+
z.string().min(1, 'JID is required').endsWith('@s.whatsapp.net', 'JID not a valid WhatsApp JID)'),
|
|
16
|
+
z.string().min(1, 'JID is required').endsWith('@g.us', 'JID not a valid WhatsApp JID)'),
|
|
17
|
+
]).describe('The JID of the recipient or chat. For example 41791234567@s.whatsapp.net for an individual or 1234567890-1234567890@g.us for a group');
|
|
18
|
+
//# sourceMappingURL=common.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"common.js","sourceRoot":"","sources":["../../src/tools/common.ts"],"names":[],"mappings":"AAAA,OAAO,EAAa,gBAAgB,EAAE,MAAM,yCAAyC,CAAA;AAErF,OAAO,CAAC,MAAM,KAAK,CAAA;AAEnB,MAAM,CAAC,MAAM,cAAc,GAAG,CAAC,QAAwC,EAAE,EAAE,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,CAAA;AAC1F,MAAM,CAAC,MAAM,cAAc,GAAG,CAAC,SAA2C,EAAE,EAAE,CAAC,CAAC,EAAE,SAAS,EAAE,CAAC,CAAA;AAC9F,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,IAAY,EAAkB,EAAE,CAAC,CAAC,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,CAAA;AACrH,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,KAAY,EAAkB,EAAE,CAAC,CAAC,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,UAAU,KAAK,CAAC,OAAO,EAAE,EAAE,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC,CAAA;AAE9I,MAAM,UAAU,uBAAuB,CACrC,MAAiB,EACjB,UAAkB,EAClB,YAAoB,EACpB,MAAiB,EACjB,GAAkC,EAClC,KAA4B,EAC5B,MAA6B;IAE7B,MAAM,UAAU,GAAG,CAAC,MAAqB,EAAE,EAAE,CAC3C,MAAM,CAAC,CAAC,CAAC,CAAC,EAAE,GAAG,EAAE,KAAK,CAAC,MAAM,CAAC,EAAE,QAAQ,EAAE,kBAA2B,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAA;IAE7G,MAAM,CAAC,gBAAgB,CACrB,UAAU,EACV,GAAG,UAAU,QAAQ,EACrB,EAAE,KAAK,EAAE,gBAAgB,UAAU,EAAE,EAAE,WAAW,EAAE,iBAAiB,UAAU,EAAE,EAAE,QAAQ,EAAE,kBAAkB,EAAE,EACjH,GAAG,EAAE,CAAC,cAAc,CAAC,MAAM,EAAE,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC,CACnD,CAAA;IAED,MAAM,CAAC,gBAAgB,CACrB,YAAY,EACZ,IAAI,gBAAgB,CAAC,GAAG,UAAU,WAAW,YAAY,KAAK,EAAE;QAC9D,IAAI,EAAE,GAAG,EAAE,CAAC,cAAc,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,GAAG,EAAE,KAAK,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;KACpF,CAAC,EACF,EAAE,KAAK,EAAE,qBAAqB,YAAY,EAAE,EAAE,WAAW,EAAE,gCAAgC,YAAY,EAAE,EAAE,QAAQ,EAAE,kBAAkB,EAAE,EACzI,CAAC,CAAC,EAAE,MAAM,EAAE,EAAE,CAAC,cAAc,CAAC,UAAU,CAAC,GAAG,CAAC,MAAM,CAAC,GAAG,YAAY,IAAI,CAAW,CAAC,CAAC,CAAC,CACtF,CAAA;AACH,CAAC;AAED,MAAM,CAAC,MAAM,SAAS,GAAG,CAAC,CAAC,KAAK,CAAC;IAC/B,CAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,EAAE,iBAAiB,CAAC,CAAC,QAAQ,CAAC,iBAAiB,EAAE,+BAA+B,CAAC;IACjG,CAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,EAAE,iBAAiB,CAAC,CAAC,QAAQ,CAAC,OAAO,EAAE,+BAA+B,CAAC;CACxF,CAAC,CAAC,QAAQ,CAAC,sIAAsI,CAAC,CAAA"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contactTools.d.ts","sourceRoot":"","sources":["../../src/tools/contactTools.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AACnE,OAAO,EAAE,KAAK,aAAa,EAAE,MAAM,aAAa,CAAA;AAGhD,wBAAgB,wBAAwB,CAAC,MAAM,EAAE,SAAS,EAAE,KAAK,EAAE,aAAa,QAM/E"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { registerEntityResources } from './common.js';
|
|
2
|
+
export function registerContactResources(server, store) {
|
|
3
|
+
registerEntityResources(server, 'contacts', 'contact', () => store.getContacts(), id => store.getContact(id), c => `contacts://app/${c.id}`, c => c.name ?? c.id);
|
|
4
|
+
}
|
|
5
|
+
//# sourceMappingURL=contactTools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contactTools.js","sourceRoot":"","sources":["../../src/tools/contactTools.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,uBAAuB,EAAE,MAAM,aAAa,CAAA;AAErD,MAAM,UAAU,wBAAwB,CAAC,MAAiB,EAAE,KAAoB;IAC9E,uBAAuB,CACrB,MAAM,EAAE,UAAU,EAAE,SAAS,EAC7B,GAAG,EAAE,CAAC,KAAK,CAAC,WAAW,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,EAAE,CAAC,EACrD,CAAC,CAAC,EAAE,CAAC,kBAAkB,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,EAAE,CACnD,CAAA;AACH,CAAC"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
2
|
+
import { type WhatsAppStore } from '../store.js';
|
|
3
|
+
import { WhatsAppHandler } from '../sync.js';
|
|
4
|
+
export declare function registerMessageTools(server: McpServer, store: WhatsAppStore, sync: WhatsAppHandler): void;
|
|
5
|
+
//# sourceMappingURL=messageTools.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"messageTools.d.ts","sourceRoot":"","sources":["../../src/tools/messageTools.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AACnE,OAAO,EAAE,KAAK,aAAa,EAAE,MAAM,aAAa,CAAA;AAChD,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAA;AAK5C,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,SAAS,EAAE,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,eAAe,QAoBlG"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import z from 'zod';
|
|
2
|
+
import { JidSchema, registerEntityResources, toCallResult, toCallError } from './common.js';
|
|
3
|
+
export function registerMessageTools(server, store, sync) {
|
|
4
|
+
registerEntityResources(server, 'messages', 'message', () => store.getMessages(), id => store.getMessage(id), m => `messages://app/${m.key.id}`, m => m.key.id);
|
|
5
|
+
server.registerTool('send_message', { description: 'Send a WhatsApp-Message to a given JID.', inputSchema: SendMessageSchema }, async (args) => {
|
|
6
|
+
try {
|
|
7
|
+
const message = await sync.sendMessage(args.jid, args.message);
|
|
8
|
+
return toCallResult(`Message sent to ${message.key.remoteJid ?? 'unknown'}: "${message.message?.conversation ?? 'unknown'}"`);
|
|
9
|
+
}
|
|
10
|
+
catch (error) {
|
|
11
|
+
return toCallError(error);
|
|
12
|
+
}
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
const SendMessageSchema = z.object({
|
|
16
|
+
jid: JidSchema,
|
|
17
|
+
message: z.string()
|
|
18
|
+
.min(1, 'Message body is required')
|
|
19
|
+
.describe('The body of the message to be sent. Can contain unicode characters like emojis.'),
|
|
20
|
+
});
|
|
21
|
+
//# sourceMappingURL=messageTools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"messageTools.js","sourceRoot":"","sources":["../../src/tools/messageTools.ts"],"names":[],"mappings":"AAGA,OAAO,CAAC,MAAM,KAAK,CAAA;AAEnB,OAAO,EAAE,SAAS,EAAE,uBAAuB,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,aAAa,CAAA;AAE3F,MAAM,UAAU,oBAAoB,CAAC,MAAiB,EAAE,KAAoB,EAAE,IAAqB;IACjG,uBAAuB,CACrB,MAAM,EAAE,UAAU,EAAE,SAAS,EAC7B,GAAG,EAAE,CAAC,KAAK,CAAC,WAAW,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,EAAE,CAAC,EACrD,CAAC,CAAC,EAAE,CAAC,kBAAkB,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,EAAE,CACjD,CAAA;IAED,MAAM,CAAC,YAAY,CACjB,cAAc,EACd,EAAE,WAAW,EAAE,yCAAyC,EAAE,WAAW,EAAE,iBAAiB,EAAE,EAC1F,KAAK,EAAE,IAAI,EAAE,EAAE;QACb,IAAI,CAAC;YACH,MAAM,OAAO,GAAc,MAAM,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,OAAO,CAAC,CAAA;YACzE,OAAO,YAAY,CAAC,mBAAmB,OAAO,CAAC,GAAG,CAAC,SAAS,IAAI,SAAS,MAAM,OAAO,CAAC,OAAO,EAAE,YAAY,IAAI,SAAS,GAAG,CAAC,CAAA;QAC/H,CAAC;QACD,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,WAAW,CAAC,KAAc,CAAC,CAAA;QACpC,CAAC;IACH,CAAC,CACF,CAAA;AACH,CAAC;AAED,MAAM,iBAAiB,GAAG,CAAC,CAAC,MAAM,CAAC;IACjC,GAAG,EAAE,SAAS;IACd,OAAO,EAAE,CAAC,CAAC,MAAM,EAAE;SAChB,GAAG,CAAC,CAAC,EAAE,0BAA0B,CAAC;SAClC,QAAQ,CAAC,iFAAiF,CAAC;CAC/F,CAAC,CAAA"}
|
package/dist/tools.d.ts
CHANGED
|
@@ -1,5 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
import { WhatsAppStore } from './store.js';
|
|
3
|
-
import { WhatsAppHandler } from './sync.js';
|
|
4
|
-
export declare function registerWhatsAppTools(server: McpServer, store: WhatsAppStore, sync: WhatsAppHandler): void;
|
|
1
|
+
export {};
|
|
5
2
|
//# sourceMappingURL=tools.d.ts.map
|
package/dist/tools.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":""}
|
package/dist/tools.js
CHANGED
|
@@ -1,74 +1,65 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
export function registerWhatsAppTools(server, store, sync) {
|
|
4
|
-
registerChatsResources(server, store);
|
|
5
|
-
registerContactsResources(server, store);
|
|
6
|
-
registerMessagesResources(server, store);
|
|
7
|
-
registerMessageTools(server, sync);
|
|
8
|
-
registerChatTools(server, sync);
|
|
9
|
-
}
|
|
10
|
-
function registerChatsResources(server, store) {
|
|
11
|
-
server.registerResource('chats', 'chats://app', { title: 'All WhatsApp Chats', description: 'List WhatsApp chats', mimeType: 'application/json' }, () => toReadResource(store.getChats().flatMap(chatToReadResource)));
|
|
12
|
-
server.registerResource('chat', new ResourceTemplate('chats://app/{chatId}', { list: () => toListResource(store.getChats().flatMap(chatToListResource)) }), { title: 'A single WhatsApp Chat', description: 'Details of a single WhatsApp chat', mimeType: 'application/json' }, (_, { chatId }) => toReadResource(chatToReadResource(store.getChat(chatId))));
|
|
13
|
-
}
|
|
14
|
-
const chatToReadResource = (chat) => chat
|
|
15
|
-
? [{ uri: `chats://app/${chat.id}`, mimeType: 'application/json', text: JSON.stringify(chat) }]
|
|
16
|
-
: [];
|
|
17
|
-
const chatToListResource = (chat) => chat
|
|
18
|
-
? [{ uri: `chats://app/${chat.id}`, name: chat.name ?? chat.id }]
|
|
19
|
-
: [];
|
|
20
|
-
function registerContactsResources(server, store) {
|
|
21
|
-
server.registerResource('contacts', 'contacts://app', { title: 'All WhatsApp Contacts', description: 'List WhatsApp contacts', mimeType: 'application/json' }, () => toReadResource(store.getContacts().flatMap(contactToReadResource)));
|
|
22
|
-
server.registerResource('contact', new ResourceTemplate('contacts://app/{contactId}', { list: () => toListResource(store.getContacts().flatMap(contactToListResource)) }), { title: 'A single WhatsApp Contact', description: 'Details of a single WhatsApp contact', mimeType: 'application/json' }, (_, { contactId }) => toReadResource(contactToReadResource(store.getContact(contactId))));
|
|
23
|
-
}
|
|
24
|
-
const contactToReadResource = (contact) => contact
|
|
25
|
-
? [{ uri: `contacts://app/${contact.id}`, mimeType: 'application/json', text: JSON.stringify(contact) }]
|
|
26
|
-
: [];
|
|
27
|
-
const contactToListResource = (contact) => contact
|
|
28
|
-
? [{ uri: `contacts://app/${contact.id}`, name: contact.name ?? contact.id }]
|
|
29
|
-
: [];
|
|
30
|
-
function registerMessagesResources(server, store) {
|
|
31
|
-
server.registerResource('messages', 'messages://app', { title: 'All WhatsApp Messages', description: 'List WhatsApp messages', mimeType: 'application/json' }, () => toReadResource(store.getMessages().flatMap(messageToReadResource)));
|
|
32
|
-
server.registerResource('message', new ResourceTemplate('messages://app/{messageId}', { list: () => toListResource(store.getMessages().flatMap(messageToListResource)) }), { title: 'A single WhatsApp Message', description: 'Details of a single WhatsApp message', mimeType: 'application/json' }, (_, { messageId }) => toReadResource(messageToReadResource(store.getMessage(messageId))));
|
|
33
|
-
}
|
|
34
|
-
const messageToReadResource = (message) => message
|
|
35
|
-
? [{ uri: `messages://app/${message.key.id}`, mimeType: 'application/json', text: JSON.stringify(message) }]
|
|
36
|
-
: [];
|
|
37
|
-
const messageToListResource = (message) => message
|
|
38
|
-
? [{ uri: `messages://app/${message.key.id}`, name: message.key.id }]
|
|
39
|
-
: [];
|
|
40
|
-
const toReadResource = (t) => ({ contents: t });
|
|
41
|
-
const toListResource = (t) => ({ resources: t });
|
|
42
|
-
function registerMessageTools(server, sync) {
|
|
43
|
-
server.registerTool('send_message', { description: 'Send a WhatsApp-Message to a given JID.', inputSchema: SendMessageSchema }, args => sync.sendMessage(args.jid, args.message).then(messageToText).then(toCallResult).catch(toCallError));
|
|
44
|
-
}
|
|
45
|
-
const messageToText = (message) => {
|
|
46
|
-
return `Message sent to ${message.key.remoteJid ?? 'unknown'}: "${message.message?.conversation ?? 'unknown'}"`;
|
|
47
|
-
};
|
|
48
|
-
function registerChatTools(server, sync) {
|
|
49
|
-
server.registerTool('set_chat_archived', { description: 'Set a WhatsApp chat as archived or unarchived.', inputSchema: ArchiveChatSchema }, args => sync.setArchived(args.jid, args.archived).then(() => `Chat ${args.jid} archived status set to ${args.archived.toString()}`).then(toCallResult).catch(toCallError));
|
|
50
|
-
server.registerTool('set_chat_read', { description: 'Set a WhatsApp chat as read or unread.', inputSchema: ReadChatSchema }, args => sync.setRead(args.jid, args.read).then(() => `Chat ${args.jid} read status set to ${args.read.toString()}`).then(toCallResult).catch(toCallError));
|
|
51
|
-
}
|
|
52
|
-
const JidSchema = z.union([
|
|
53
|
-
z.string().min(1, 'JID is required').endsWith('@s.whatsapp.net', 'JID not a valid WhatsApp JID)'),
|
|
54
|
-
z.string().min(1, 'JID is required').endsWith('@g.us', 'JID not a valid WhatsApp JID)'),
|
|
55
|
-
]).describe('The JID of the recipient or chat. For example 41791234567@s.whatsapp.net for an individual or 1234567890-1234567890@g.us for a group');
|
|
1
|
+
export {};
|
|
2
|
+
/*
|
|
56
3
|
const SendMessageSchema = z.object({
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
.min(1, 'Message body is required')
|
|
60
|
-
.describe('The body of the message to be sent. Can contain unicode characters like emojis.'),
|
|
4
|
+
to: z.string().min(1, "Recipient is required"),
|
|
5
|
+
message: z.string().min(1, "Message body is required"),
|
|
61
6
|
});
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
.describe('Whether the chat should be archived (true) or unarchived (false).'),
|
|
7
|
+
|
|
8
|
+
const ListChatsSchema = z.object({
|
|
9
|
+
limit: z.number().int().positive().optional().default(20),
|
|
66
10
|
});
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
11
|
+
|
|
12
|
+
const ReadMessagesSchema = z.object({
|
|
13
|
+
chatId: z.string().min(1, "Chat ID is required"),
|
|
14
|
+
limit: z.number().int().positive().optional().default(50),
|
|
71
15
|
});
|
|
72
|
-
|
|
73
|
-
|
|
16
|
+
|
|
17
|
+
server.registerTool(
|
|
18
|
+
"send_message",
|
|
19
|
+
{
|
|
20
|
+
description: "Send a WhatsApp message to a recipient",
|
|
21
|
+
inputSchema: SendMessageSchema,
|
|
22
|
+
},
|
|
23
|
+
async ({ to, message }) => ({
|
|
24
|
+
content: [
|
|
25
|
+
{
|
|
26
|
+
type: "text" as const,
|
|
27
|
+
text: `Message would be sent to ${to}: "${message}" (not yet implemented)`,
|
|
28
|
+
},
|
|
29
|
+
],
|
|
30
|
+
}),
|
|
31
|
+
);
|
|
32
|
+
|
|
33
|
+
server.registerTool(
|
|
34
|
+
"list_chats",
|
|
35
|
+
{
|
|
36
|
+
description: "List recent WhatsApp chats",
|
|
37
|
+
inputSchema: ListChatsSchema,
|
|
38
|
+
},
|
|
39
|
+
async ({ limit }) => ({
|
|
40
|
+
content: [
|
|
41
|
+
{
|
|
42
|
+
type: "text" as const,
|
|
43
|
+
text: `Listing up to ${limit} chats (not yet implemented)`,
|
|
44
|
+
},
|
|
45
|
+
],
|
|
46
|
+
}),
|
|
47
|
+
);
|
|
48
|
+
|
|
49
|
+
server.registerTool(
|
|
50
|
+
"read_messages",
|
|
51
|
+
{
|
|
52
|
+
description: "Read messages from a WhatsApp chat",
|
|
53
|
+
inputSchema: ReadMessagesSchema,
|
|
54
|
+
},
|
|
55
|
+
async ({ chatId, limit }) => ({
|
|
56
|
+
content: [
|
|
57
|
+
{
|
|
58
|
+
type: "text" as const,
|
|
59
|
+
text: `Reading up to ${limit} messages from ${chatId} (not yet implemented)`,
|
|
60
|
+
},
|
|
61
|
+
],
|
|
62
|
+
}),
|
|
63
|
+
);
|
|
64
|
+
*/
|
|
74
65
|
//# sourceMappingURL=tools.js.map
|
package/dist/tools.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":";AAEA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EA8DE"}
|
package/package.json
CHANGED
|
@@ -1,59 +1,60 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@lizzythelizard/whatsapp-mcp",
|
|
3
|
-
"version": "0.1.
|
|
4
|
-
"description": "MCP server for WhatsApp integration",
|
|
5
|
-
"type": "module",
|
|
6
|
-
"main": "dist/index.js",
|
|
7
|
-
"files": [
|
|
8
|
-
"dist"
|
|
9
|
-
],
|
|
10
|
-
"engines": {
|
|
11
|
-
"node": ">=20"
|
|
12
|
-
},
|
|
13
|
-
"repository": {
|
|
14
|
-
"type": "git",
|
|
15
|
-
"url": "git+https://github.com/lizzyTheLizard/whatsapp-mcp.git"
|
|
16
|
-
},
|
|
17
|
-
"bugs": {
|
|
18
|
-
"url": "https://github.com/lizzyTheLizard/whatsapp-mcp/issues"
|
|
19
|
-
},
|
|
20
|
-
"homepage": "https://github.com/lizzyTheLizard/whatsapp-mcp#readme",
|
|
21
|
-
"publishConfig": {
|
|
22
|
-
"access": "public"
|
|
23
|
-
},
|
|
24
|
-
"bin": {
|
|
25
|
-
"whatsapp-mcp": "dist/index.js"
|
|
26
|
-
},
|
|
27
|
-
"scripts": {
|
|
28
|
-
"build": "tsc",
|
|
29
|
-
"start": "node dist/index.js",
|
|
30
|
-
"dev": "tsx watch src/index.ts",
|
|
31
|
-
"test": "vitest run",
|
|
32
|
-
"test:watch": "vitest",
|
|
33
|
-
"lint": "eslint src/",
|
|
34
|
-
"lint:fix": "eslint src/ --fix",
|
|
35
|
-
"typecheck": "tsc --noEmit"
|
|
36
|
-
},
|
|
37
|
-
"keywords": [
|
|
38
|
-
"mcp",
|
|
39
|
-
"whatsapp",
|
|
40
|
-
"model-context-protocol"
|
|
41
|
-
],
|
|
42
|
-
"license": "MIT",
|
|
43
|
-
"dependencies": {
|
|
44
|
-
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
45
|
-
"@stylistic/eslint-plugin": "^5.10.0",
|
|
46
|
-
"@whiskeysockets/baileys": "^7.0.0-rc13",
|
|
47
|
-
"zod": "^4.4.3"
|
|
48
|
-
},
|
|
49
|
-
"devDependencies": {
|
|
50
|
-
"@eslint/js": "^10.0.1",
|
|
51
|
-
"@types/node": "^26.0.1",
|
|
52
|
-
"@typescript-eslint/eslint-plugin": "^8.62.0",
|
|
53
|
-
"eslint": "^10.5.0",
|
|
54
|
-
"
|
|
55
|
-
"
|
|
56
|
-
"typescript
|
|
57
|
-
"
|
|
58
|
-
|
|
59
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "@lizzythelizard/whatsapp-mcp",
|
|
3
|
+
"version": "0.1.6",
|
|
4
|
+
"description": "MCP server for WhatsApp integration",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "dist/index.js",
|
|
7
|
+
"files": [
|
|
8
|
+
"dist"
|
|
9
|
+
],
|
|
10
|
+
"engines": {
|
|
11
|
+
"node": ">=20"
|
|
12
|
+
},
|
|
13
|
+
"repository": {
|
|
14
|
+
"type": "git",
|
|
15
|
+
"url": "git+https://github.com/lizzyTheLizard/whatsapp-mcp.git"
|
|
16
|
+
},
|
|
17
|
+
"bugs": {
|
|
18
|
+
"url": "https://github.com/lizzyTheLizard/whatsapp-mcp/issues"
|
|
19
|
+
},
|
|
20
|
+
"homepage": "https://github.com/lizzyTheLizard/whatsapp-mcp#readme",
|
|
21
|
+
"publishConfig": {
|
|
22
|
+
"access": "public"
|
|
23
|
+
},
|
|
24
|
+
"bin": {
|
|
25
|
+
"whatsapp-mcp": "dist/index.js"
|
|
26
|
+
},
|
|
27
|
+
"scripts": {
|
|
28
|
+
"build": "tsc",
|
|
29
|
+
"start": "node dist/index.js",
|
|
30
|
+
"dev": "tsx watch src/index.ts",
|
|
31
|
+
"test": "vitest run",
|
|
32
|
+
"test:watch": "vitest",
|
|
33
|
+
"lint": "eslint src/",
|
|
34
|
+
"lint:fix": "eslint src/ --fix",
|
|
35
|
+
"typecheck": "tsc --noEmit"
|
|
36
|
+
},
|
|
37
|
+
"keywords": [
|
|
38
|
+
"mcp",
|
|
39
|
+
"whatsapp",
|
|
40
|
+
"model-context-protocol"
|
|
41
|
+
],
|
|
42
|
+
"license": "MIT",
|
|
43
|
+
"dependencies": {
|
|
44
|
+
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
45
|
+
"@stylistic/eslint-plugin": "^5.10.0",
|
|
46
|
+
"@whiskeysockets/baileys": "^7.0.0-rc13",
|
|
47
|
+
"zod": "^4.4.3"
|
|
48
|
+
},
|
|
49
|
+
"devDependencies": {
|
|
50
|
+
"@eslint/js": "^10.0.1",
|
|
51
|
+
"@types/node": "^26.0.1",
|
|
52
|
+
"@typescript-eslint/eslint-plugin": "^8.62.0",
|
|
53
|
+
"eslint": "^10.5.0",
|
|
54
|
+
"eslint-plugin-import-x": "^4.17.0",
|
|
55
|
+
"tsx": "^4.22.4",
|
|
56
|
+
"typescript": "^6.0.3",
|
|
57
|
+
"typescript-eslint": "^8.62.0",
|
|
58
|
+
"vitest": "^4.1.9"
|
|
59
|
+
}
|
|
60
|
+
}
|