A Model Context Protocol server that enables LLM applications to interact with macOS through AppleScript.
This server provides a standardized interface for AI applications to control system functions, manage files, handle notifications, and more.
Features
- ?️ Calendar management (events, reminders)
- ? Clipboard operations
- ? Finder integration
- ? System notifications
- ⚙️ System controls (volume, dark mode, apps)
- ? iTerm terminal integration
Planned Features
- ? Mail (list emails, save attachments, summarize, send)
- ? Safari (open in Safari, save page content, get selected page/tab)
- ? Messages (send, get, list)
- ✅ Reminders (create, get)
- ?️ Notes (create, get, list)
Prerequisites
- macOS 10.15 or later
- Node.js 18 or later
Available Categories
Calendar
Command |
Description |
Parameters |
add |
Create calendar event |
title , startDate , endDate |
list |
List today's events |
None |
Clipboard
Command |
Description |
Parameters |
set_clipboard |
Copy to clipboard |
content |
get_clipboard |
Get clipboard contents |
None |
clear_clipboard |
Clear clipboard |
None |
Finder
Command |
Description |
Parameters |
get_selected_files |
Get selected files |
None |
search_files |
Search for files |
query , location (optional) |
quick_look |
Preview file |
path |
Notifications
Command |
Description |
Parameters |
send_notification |
Show notification |
title , message , sound (optional) |
toggle_do_not_disturb |
Toggle DND mode |
None |
System
Command |
Description |
Parameters |
volume |
Set system volume |
level (0-100) |
get_frontmost_app |
Get active app |
None |
launch_app |
Open application |
name |
quit_app |
Close application |
name , force (optional) |
toggle_dark_mode |
Toggle dark mode |
None |
iTerm
Command |
Description |
Parameters |
paste_clipboard |
Paste to iTerm |
None |
run |
Execute command |
command , newWindow (optional) |
Development
Setup
# Install dependencies
npm install
# Build the server
npm run build
# Launch MCP Inspector
# See: https://modelcontextprotocol.io/docs/tools/inspector
npx @modelcontextprotocol/inspector node path/to/server/index.js args...
Adding New Functionality
1. Create Category File
Create src/categories/newcategory.ts
:
import { ScriptCategory } from "../types/index.js";
export const newCategory: ScriptCategory = {
name: "category_name",
description: "Category description",
scripts: [
// Scripts will go here
]
};
2. Add Scripts
{
name: "script_name",
description: "What the script does",
schema: {
type: "object",
properties: {
paramName: {
type: "string",
description: "Parameter description"
}
},
required: ["paramName"]
},
script: (args) => `
tell application "App"
// AppleScript code using ${args.paramName}
end tell
`
}
3. Register Category
Update src/index.ts
:
import { newCategory } from "./categories/newcategory.js";
// ...
server.addCategory(newCategory);
Debugging
Using MCP Inspector
The MCP Inspector provides a web interface for testing and debugging your server:
npm run inspector
Logging
Enable debug logging by setting the environment variable:
DEBUG=applescript-mcp* npm start
Common Issues
- Permission Errors: Check System Preferences > Security & Privacy
- Script Failures: Test scripts directly in Script Editor.app
- Communication Issues: Check stdio streams aren't being redirected
Resources
Contributing
- Fork the repository
- Create a feature branch
- Commit your changes
- Push to the branch
- Create a Pull Request
License
MIT License - see LICENSE for details
[
{
"description": "[System control and information] Set system volume",
"inputSchema": {
"properties": {
"level": {
"maximum": 100,
"minimum": 0,
"type": "number"
}
},
"required": [
"level"
],
"type": "object"
},
"name": "system_volume"
},
{
"description": "[System control and information] Get the name of the frontmost application",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "system_get_frontmost_app"
},
{
"description": "[System control and information] Launch an application",
"inputSchema": {
"properties": {
"name": {
"description": "Application name",
"type": "string"
}
},
"required": [
"name"
],
"type": "object"
},
"name": "system_launch_app"
},
{
"description": "[System control and information] Quit an application",
"inputSchema": {
"properties": {
"force": {
"default": false,
"description": "Force quit if true",
"type": "boolean"
},
"name": {
"description": "Application name",
"type": "string"
}
},
"required": [
"name"
],
"type": "object"
},
"name": "system_quit_app"
},
{
"description": "[System control and information] Toggle system dark mode",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "system_toggle_dark_mode"
},
{
"description": "[System control and information] Get battery level and charging status",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "system_get_battery_status"
},
{
"description": "[Calendar operations] Add a new event to Calendar",
"inputSchema": {
"properties": {
"calendar": {
"default": "Calendar",
"description": "Calendar name (optional)",
"type": "string"
},
"endDate": {
"description": "End date and time (YYYY-MM-DD HH:MM:SS)",
"type": "string"
},
"startDate": {
"description": "Start date and time (YYYY-MM-DD HH:MM:SS)",
"type": "string"
},
"title": {
"description": "Event title",
"type": "string"
}
},
"required": [
"title",
"startDate",
"endDate"
],
"type": "object"
},
"name": "calendar_add"
},
{
"description": "[Calendar operations] List all events for today",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "calendar_list"
},
{
"description": "[Finder and file operations] Get currently selected files in Finder",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "finder_get_selected_files"
},
{
"description": "[Finder and file operations] Search for files by name",
"inputSchema": {
"properties": {
"location": {
"default": "~",
"description": "Search location (default: home folder)",
"type": "string"
},
"query": {
"description": "Search term",
"type": "string"
}
},
"required": [
"query"
],
"type": "object"
},
"name": "finder_search_files"
},
{
"description": "[Finder and file operations] Preview a file using Quick Look",
"inputSchema": {
"properties": {
"path": {
"description": "File path to preview",
"type": "string"
}
},
"required": [
"path"
],
"type": "object"
},
"name": "finder_quick_look_file"
},
{
"description": "[Clipboard management operations] Get current clipboard content",
"inputSchema": {
"properties": {
"type": {
"default": "text",
"description": "Type of clipboard content to get",
"enum": [
"text",
"file_paths"
],
"type": "string"
}
},
"type": "object"
},
"name": "clipboard_get_clipboard"
},
{
"description": "[Clipboard management operations] Set clipboard content",
"inputSchema": {
"properties": {
"content": {
"description": "Content to copy to clipboard",
"type": "string"
}
},
"required": [
"content"
],
"type": "object"
},
"name": "clipboard_set_clipboard"
},
{
"description": "[Clipboard management operations] Clear clipboard content",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "clipboard_clear_clipboard"
},
{
"description": "[Notification management] Toggle Do Not Disturb mode using keyboard shortcut",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "notifications_toggle_do_not_disturb"
},
{
"description": "[Notification management] Send a system notification",
"inputSchema": {
"properties": {
"message": {
"description": "Notification message",
"type": "string"
},
"sound": {
"default": true,
"description": "Play sound with notification",
"type": "boolean"
},
"title": {
"description": "Notification title",
"type": "string"
}
},
"required": [
"title",
"message"
],
"type": "object"
},
"name": "notifications_send_notification"
},
{
"description": "[iTerm terminal operations] Paste clipboard content into iTerm",
"inputSchema": {
"properties": {},
"type": "object"
},
"name": "iterm_paste_clipboard"
},
{
"description": "[iTerm terminal operations] Run a command in iTerm",
"inputSchema": {
"properties": {
"command": {
"description": "Command to run in iTerm",
"type": "string"
},
"newWindow": {
"default": false,
"description": "Whether to open in a new window (default: false)",
"type": "boolean"
}
},
"required": [
"command"
],
"type": "object"
},
"name": "iterm_run"
}
]