audio-mcp 0.1.0
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/LICENSE +21 -0
- package/README.md +411 -0
- package/dist/audio/capture.d.ts +28 -0
- package/dist/audio/capture.js +2 -0
- package/dist/audio/capture.js.map +1 -0
- package/dist/audio/devices.d.ts +16 -0
- package/dist/audio/devices.js +65 -0
- package/dist/audio/devices.js.map +1 -0
- package/dist/audio/helper-capture.d.ts +36 -0
- package/dist/audio/helper-capture.js +135 -0
- package/dist/audio/helper-capture.js.map +1 -0
- package/dist/audio/helper-path.d.ts +10 -0
- package/dist/audio/helper-path.js +47 -0
- package/dist/audio/helper-path.js.map +1 -0
- package/dist/audio/wav.d.ts +52 -0
- package/dist/audio/wav.js +174 -0
- package/dist/audio/wav.js.map +1 -0
- package/dist/bin/audio-capture-helper +0 -0
- package/dist/config.d.ts +14 -0
- package/dist/config.js +27 -0
- package/dist/config.js.map +1 -0
- package/dist/errors.d.ts +18 -0
- package/dist/errors.js +21 -0
- package/dist/errors.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +10 -0
- package/dist/index.js.map +1 -0
- package/dist/logger.d.ts +14 -0
- package/dist/logger.js +34 -0
- package/dist/logger.js.map +1 -0
- package/dist/paths.d.ts +15 -0
- package/dist/paths.js +36 -0
- package/dist/paths.js.map +1 -0
- package/dist/server.d.ts +1 -0
- package/dist/server.js +112 -0
- package/dist/server.js.map +1 -0
- package/dist/session/manager.d.ts +58 -0
- package/dist/session/manager.js +184 -0
- package/dist/session/manager.js.map +1 -0
- package/dist/session/store.d.ts +35 -0
- package/dist/session/store.js +72 -0
- package/dist/session/store.js.map +1 -0
- package/dist/tools/index.d.ts +16 -0
- package/dist/tools/index.js +180 -0
- package/dist/tools/index.js.map +1 -0
- package/package.json +58 -0
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { AudioMcpError } from "../errors.js";
|
|
3
|
+
import { statSync, existsSync } from "node:fs";
|
|
4
|
+
import { sliceWav } from "../audio/wav.js";
|
|
5
|
+
const WAV_HEADER_SIZE = 44;
|
|
6
|
+
const MAX_CHUNK_SECONDS = 300;
|
|
7
|
+
function toSessionListItem(meta) {
|
|
8
|
+
// For active sessions, report a live snapshot of disk size + duration
|
|
9
|
+
// so agents can poll progress without stopping the session.
|
|
10
|
+
let fileSize = meta.file_size_bytes;
|
|
11
|
+
let durationSeconds = meta.duration_seconds;
|
|
12
|
+
if (meta.is_active && existsSync(meta.path)) {
|
|
13
|
+
fileSize = statSync(meta.path).size;
|
|
14
|
+
const dataBytes = Math.max(0, fileSize - WAV_HEADER_SIZE);
|
|
15
|
+
const bytesPerSec = meta.sample_rate * meta.channels * 2;
|
|
16
|
+
durationSeconds = bytesPerSec > 0 ? dataBytes / bytesPerSec : 0;
|
|
17
|
+
}
|
|
18
|
+
return {
|
|
19
|
+
session_id: meta.session_id,
|
|
20
|
+
label: meta.label,
|
|
21
|
+
capture_mode: meta.capture_mode,
|
|
22
|
+
started_at: meta.started_at,
|
|
23
|
+
stopped_at: meta.stopped_at,
|
|
24
|
+
duration_seconds: durationSeconds,
|
|
25
|
+
file_size_bytes: fileSize,
|
|
26
|
+
channels: meta.channels,
|
|
27
|
+
is_active: meta.is_active,
|
|
28
|
+
};
|
|
29
|
+
}
|
|
30
|
+
export function buildTools(ctx) {
|
|
31
|
+
const startSession = {
|
|
32
|
+
name: "start_session",
|
|
33
|
+
description: "Start a new audio capture session. Captures mic, system output, or both into a single WAV. " +
|
|
34
|
+
"For capture='both' the file is stereo with L=mic and R=system audio. " +
|
|
35
|
+
"Fails with SESSION_ALREADY_ACTIVE if a session is already running.",
|
|
36
|
+
inputSchema: {
|
|
37
|
+
label: z.string().optional().describe("Human-readable name for the session."),
|
|
38
|
+
source: z
|
|
39
|
+
.string()
|
|
40
|
+
.optional()
|
|
41
|
+
.describe("Microphone device uniqueID or substring-matched name. Only used when capture includes 'mic'. Omit for system default."),
|
|
42
|
+
capture: z
|
|
43
|
+
.enum(["mic", "system", "both"])
|
|
44
|
+
.optional()
|
|
45
|
+
.describe("What to capture. 'mic'=microphone only; 'system'=system audio output only (requires Screen Recording permission); 'both'=stereo WAV with L=mic R=system. Defaults to 'both'."),
|
|
46
|
+
},
|
|
47
|
+
handler: async (input) => {
|
|
48
|
+
return ctx.manager.start({
|
|
49
|
+
label: input.label,
|
|
50
|
+
source: input.source,
|
|
51
|
+
capture: input.capture,
|
|
52
|
+
});
|
|
53
|
+
},
|
|
54
|
+
};
|
|
55
|
+
const stopSession = {
|
|
56
|
+
name: "stop_session",
|
|
57
|
+
description: "Stop the active capture session and finalize the WAV file.",
|
|
58
|
+
inputSchema: {
|
|
59
|
+
session_id: z.string().describe("The UUID returned by start_session."),
|
|
60
|
+
},
|
|
61
|
+
handler: async (input) => {
|
|
62
|
+
return ctx.manager.stop(input.session_id);
|
|
63
|
+
},
|
|
64
|
+
};
|
|
65
|
+
const getAudio = {
|
|
66
|
+
name: "get_audio",
|
|
67
|
+
description: "Return a base64-encoded WAV slice of a recorded session. Max 300 seconds per call; " +
|
|
68
|
+
"chunk larger ranges yourself.",
|
|
69
|
+
inputSchema: {
|
|
70
|
+
session_id: z.string(),
|
|
71
|
+
start_second: z
|
|
72
|
+
.number()
|
|
73
|
+
.min(0)
|
|
74
|
+
.optional()
|
|
75
|
+
.describe("Start of the slice, in seconds (default 0)."),
|
|
76
|
+
end_second: z
|
|
77
|
+
.number()
|
|
78
|
+
.min(0)
|
|
79
|
+
.optional()
|
|
80
|
+
.describe("End of the slice, in seconds (default: end of session)."),
|
|
81
|
+
format: z
|
|
82
|
+
.enum(["wav", "opus"])
|
|
83
|
+
.optional()
|
|
84
|
+
.describe("Output format. Only 'wav' is supported in v1."),
|
|
85
|
+
},
|
|
86
|
+
handler: async (input) => {
|
|
87
|
+
if (input.format && input.format === "opus") {
|
|
88
|
+
throw new AudioMcpError("NOT_IMPLEMENTED", "Opus output is planned for v2. Request format: 'wav' instead.");
|
|
89
|
+
}
|
|
90
|
+
const meta = ctx.store.get(input.session_id);
|
|
91
|
+
if (!meta) {
|
|
92
|
+
throw new AudioMcpError("SESSION_NOT_FOUND", `Session not found: ${input.session_id}`);
|
|
93
|
+
}
|
|
94
|
+
// Active sessions are readable — we compute the live duration from
|
|
95
|
+
// the WAV file's current size so agents can poll mid-recording.
|
|
96
|
+
let sessionDuration;
|
|
97
|
+
if (meta.is_active && existsSync(meta.path)) {
|
|
98
|
+
const dataBytes = Math.max(0, statSync(meta.path).size - WAV_HEADER_SIZE);
|
|
99
|
+
const bytesPerSec = meta.sample_rate * meta.channels * 2;
|
|
100
|
+
sessionDuration = bytesPerSec > 0 ? dataBytes / bytesPerSec : 0;
|
|
101
|
+
}
|
|
102
|
+
else {
|
|
103
|
+
sessionDuration = meta.duration_seconds ?? 0;
|
|
104
|
+
}
|
|
105
|
+
const startSec = input.start_second ?? 0;
|
|
106
|
+
const endSec = input.end_second ?? sessionDuration;
|
|
107
|
+
if (endSec <= startSec) {
|
|
108
|
+
throw new AudioMcpError("INVALID_INPUT", `end_second (${endSec}) must be greater than start_second (${startSec}).`);
|
|
109
|
+
}
|
|
110
|
+
if (endSec - startSec > MAX_CHUNK_SECONDS) {
|
|
111
|
+
throw new AudioMcpError("CHUNK_TOO_LARGE", `Requested ${endSec - startSec}s exceeds the 300s chunk limit. ` +
|
|
112
|
+
`Split into multiple calls, e.g. [${startSec}, ${startSec + MAX_CHUNK_SECONDS}] then ` +
|
|
113
|
+
`[${startSec + MAX_CHUNK_SECONDS}, ${endSec}].`);
|
|
114
|
+
}
|
|
115
|
+
const slice = sliceWav(meta.path, startSec, endSec);
|
|
116
|
+
return {
|
|
117
|
+
session_id: input.session_id,
|
|
118
|
+
start_second: startSec,
|
|
119
|
+
end_second: slice.endSecond,
|
|
120
|
+
duration_seconds: slice.durationSeconds,
|
|
121
|
+
format: "wav",
|
|
122
|
+
sample_rate: slice.sampleRate,
|
|
123
|
+
channels: slice.channels,
|
|
124
|
+
audio_base64: slice.audio.toString("base64"),
|
|
125
|
+
size_bytes: slice.byteLength,
|
|
126
|
+
};
|
|
127
|
+
},
|
|
128
|
+
};
|
|
129
|
+
const listSessions = {
|
|
130
|
+
name: "list_sessions",
|
|
131
|
+
description: "List all recorded sessions, newest first.",
|
|
132
|
+
inputSchema: {},
|
|
133
|
+
handler: async () => {
|
|
134
|
+
return { sessions: ctx.store.list().map(toSessionListItem) };
|
|
135
|
+
},
|
|
136
|
+
};
|
|
137
|
+
const getSession = {
|
|
138
|
+
name: "get_session",
|
|
139
|
+
description: "Return metadata for a single session.",
|
|
140
|
+
inputSchema: {
|
|
141
|
+
session_id: z.string(),
|
|
142
|
+
},
|
|
143
|
+
handler: async (input) => {
|
|
144
|
+
const meta = ctx.store.get(input.session_id);
|
|
145
|
+
if (!meta) {
|
|
146
|
+
throw new AudioMcpError("SESSION_NOT_FOUND", `Session not found: ${input.session_id}`);
|
|
147
|
+
}
|
|
148
|
+
return toSessionListItem(meta);
|
|
149
|
+
},
|
|
150
|
+
};
|
|
151
|
+
const listAudioSources = {
|
|
152
|
+
name: "list_audio_sources",
|
|
153
|
+
description: "List available microphone input devices on this machine.",
|
|
154
|
+
inputSchema: {},
|
|
155
|
+
handler: async () => {
|
|
156
|
+
return { sources: await ctx.listInputDevices() };
|
|
157
|
+
},
|
|
158
|
+
};
|
|
159
|
+
const deleteSession = {
|
|
160
|
+
name: "delete_session",
|
|
161
|
+
description: "Permanently delete a session's audio file and metadata. Refuses active sessions.",
|
|
162
|
+
inputSchema: {
|
|
163
|
+
session_id: z.string(),
|
|
164
|
+
},
|
|
165
|
+
handler: async (input) => {
|
|
166
|
+
ctx.store.delete(input.session_id);
|
|
167
|
+
return { session_id: input.session_id, deleted: true };
|
|
168
|
+
},
|
|
169
|
+
};
|
|
170
|
+
return [
|
|
171
|
+
startSession,
|
|
172
|
+
stopSession,
|
|
173
|
+
getAudio,
|
|
174
|
+
listSessions,
|
|
175
|
+
getSession,
|
|
176
|
+
listAudioSources,
|
|
177
|
+
deleteSession,
|
|
178
|
+
];
|
|
179
|
+
}
|
|
180
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/tools/index.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "audio-mcp",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Local MCP server for macOS that captures microphone + system audio into explicit sessions and exposes raw WAV audio (stereo L=mic, R=system) to AI agents.",
|
|
5
|
+
"license": "MIT",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"bin": {
|
|
8
|
+
"audio-mcp": "dist/index.js"
|
|
9
|
+
},
|
|
10
|
+
"main": "dist/index.js",
|
|
11
|
+
"files": [
|
|
12
|
+
"dist",
|
|
13
|
+
"dist/bin",
|
|
14
|
+
"README.md",
|
|
15
|
+
"LICENSE"
|
|
16
|
+
],
|
|
17
|
+
"engines": {
|
|
18
|
+
"node": ">=18"
|
|
19
|
+
},
|
|
20
|
+
"os": [
|
|
21
|
+
"darwin"
|
|
22
|
+
],
|
|
23
|
+
"scripts": {
|
|
24
|
+
"build": "tsc && chmod +x dist/index.js && npm run build:helper",
|
|
25
|
+
"build:ts": "tsc && chmod +x dist/index.js",
|
|
26
|
+
"build:helper": "./scripts/build-helper.sh",
|
|
27
|
+
"dev": "tsc --watch",
|
|
28
|
+
"test": "vitest run",
|
|
29
|
+
"test:swift": "cd swift-helper && swift test",
|
|
30
|
+
"test:watch": "vitest",
|
|
31
|
+
"lint": "eslint 'src/**/*.ts' 'tests/**/*.ts'",
|
|
32
|
+
"format": "prettier --write 'src/**/*.ts' 'tests/**/*.ts'",
|
|
33
|
+
"prepublishOnly": "npm run build && npm test && lipo -info dist/bin/audio-capture-helper"
|
|
34
|
+
},
|
|
35
|
+
"keywords": [
|
|
36
|
+
"mcp",
|
|
37
|
+
"model-context-protocol",
|
|
38
|
+
"audio",
|
|
39
|
+
"recording",
|
|
40
|
+
"macos",
|
|
41
|
+
"claude",
|
|
42
|
+
"cursor"
|
|
43
|
+
],
|
|
44
|
+
"dependencies": {
|
|
45
|
+
"@modelcontextprotocol/sdk": "^1.0.4",
|
|
46
|
+
"wavefile": "^11.0.0",
|
|
47
|
+
"zod": "^3.23.8"
|
|
48
|
+
},
|
|
49
|
+
"devDependencies": {
|
|
50
|
+
"@types/node": "^20.14.10",
|
|
51
|
+
"@typescript-eslint/eslint-plugin": "^7.16.0",
|
|
52
|
+
"@typescript-eslint/parser": "^7.16.0",
|
|
53
|
+
"eslint": "^8.57.0",
|
|
54
|
+
"prettier": "^3.3.2",
|
|
55
|
+
"typescript": "^5.5.3",
|
|
56
|
+
"vitest": "^1.6.0"
|
|
57
|
+
}
|
|
58
|
+
}
|