Thank you for your interest in contributing to the iOS Simulator MCP server! This guide outlines our contribution process and project philosophy.
This project is intentionally simple and follows these core principles:
- Single file architecture: All logic is contained in
src/index.tsto simplify bundling and maintenance - Minimal dependencies: We keep dependencies minimal to ensure fast installs and small footprint on user machines
- Standard tooling: We use
npm(universally available) andtsc(simple, already available) for building
- New tools should be driven by real use cases, not hypothetical situations
- We are not trying to include every possible tool - additional tools can pollute context windows and confuse AI agents
- The original use case: Give AI editors the ability to interact with iOS simulators like a user, similar to playwright-mcp for browsers
- This enables autonomous agent loops where AI can validate its own work in the iOS simulator
- No significant architecture changes without prior discussion
- Major changes must be discussed with the author beforehand via GitHub issues or DMs
- Changes should address real pain points that cannot be solved by existing implementation or configuration
Before contributing, ensure you have:
- macOS (iOS simulators only work on macOS)
- Node.js installed
- Xcode and iOS simulators installed
- Facebook IDB tool installed (installation guide)
- An MCP client (like Cursor) for testing
For additional context and references, see CONTEXT.md which contains helpful links for MCP development, iOS simulator commands, and security considerations.
-
Fork and clone the repository
git clone https://github.com/your-username/ios-simulator-mcp.git cd ios-simulator-mcp -
Install dependencies
npm install
-
Build the project
npm run build
-
Test during development
# Watch mode for development npm run watch # Test with MCP inspector npm run dev
To maintain maximum compatibility with the MCP ecosystem, we align our dependencies with those used by @modelcontextprotocol/sdk. This ensures seamless integration and reduces potential conflicts.
@modelcontextprotocol/sdk: Always use the latest stable versionzod: Match the version used by@modelcontextprotocol/sdk(currently^3.23.8)typescript: Match the version used by@modelcontextprotocol/sdk(currently^5.5.4)@types/node: Match the version used by@modelcontextprotocol/sdk(currently^22.0.2)
Before upgrading dependencies, check what versions the MCP SDK uses:
# Check MCP SDK dependencies
npm info @modelcontextprotocol/sdk dependencies
# Check MCP SDK dev dependencies
npm info @modelcontextprotocol/sdk devDependencies
# Compare with current project dependencies
npm ls --depth=0-
Check MCP SDK versions first:
npm info @modelcontextprotocol/sdk dependencies devDependencies
-
Update package.json to match:
- Update
zodto match MCP SDK version - Update
typescriptto match MCP SDK version - Update
@types/nodeto match MCP SDK version - Keep
@modelcontextprotocol/sdkat latest stable
- Update
-
Install and test:
npm install npm run build npm run dev # Test with MCP inspector -
Verify compatibility:
- Test all existing functionality
- Run through the test cases in QA.md
- Ensure no new TypeScript errors
- Compatibility: Ensures our tools work seamlessly with MCP clients
- Stability: Reduces version conflicts and unexpected behavior
- Consistency: Maintains a predictable development environment
- Future-proofing: Easier to adopt new MCP SDK features and fixes
Only deviate from MCP SDK dependency versions when:
- A security vulnerability requires a newer version
- A critical bug fix is only available in a newer version
- The MCP SDK explicitly supports newer versions
In such cases, document the deviation and reasoning in the pull request.
- Follow the existing TypeScript patterns in the codebase
- Use the existing error handling patterns with
toError()anderrorWithTroubleshooting() - Maintain the single-file architecture - all logic stays in
src/index.ts
Before adding a new tool, ask yourself:
- Is this driven by a real use case? Provide specific examples of when this tool would be needed
- Can existing tools solve this problem? Check if current functionality can address the need
- Will this add significant value without cluttering the context? Consider the trade-off between utility and complexity
If adding a new tool:
- Follow the existing pattern with
isToolFiltered()check - Use proper Zod schemas for input validation
- Include comprehensive error handling with troubleshooting links
- Use the
--separator when passing user input to commands (security best practice) - Add the tool to the README.md documentation
When submitting pull requests:
- Check dependency alignment with MCP SDK before submitting
- Include dependency changes in a separate commit when possible
- Document any deviations from MCP SDK versions with clear reasoning
- Test thoroughly after dependency updates to ensure compatibility
- Always use the
--separator when passing user-provided arguments to shell commands - Validate all inputs using Zod schemas
- Use
execFileAsyncwithshell: falseto prevent command injection - Follow the existing patterns for UDID validation and path handling
For more security context, see the command injection resources in CONTEXT.md.
Due to the nature of this project, manual testing is required for all changes:
- Requires a real macOS device
- Needs a running iOS simulator
- Requires an MCP client with a real LLM
- Limited development budget (hobby project without sponsorship)
-
Build your changes
npm run build
-
Configure your MCP client (e.g., Cursor) to use your local build:
{ "mcpServers": { "ios-simulator": { "command": "node", "args": ["/full/path/to/your/ios-simulator-mcp/build/index.js"] } } } -
Start an iOS simulator
xcrun simctl list devices xcrun simctl boot "iPhone 15" # or your preferred device
-
Test thoroughly in your MCP client
- Test all affected functionality
- Test error conditions
- Verify the tool works as expected with AI agents
- Consider running the test cases in QA.md to ensure existing functionality still works
Include in your pull request:
- Step-by-step testing instructions
- Screenshots or video of the functionality working
- Description of the real use case that drove this change
- Confirmation that existing functionality still works
-
Create a feature branch
git checkout -b feature/your-feature-name
-
Make your changes following the guidelines above
-
Test thoroughly using the manual testing process
-
Update documentation if needed:
- Add new tools to README.md
- Update any relevant documentation
-
Submit a pull request with:
- Clear description of the change and motivation
- Step-by-step testing instructions
- Screenshots/video of manual testing
- Confirmation of real use case
- Releases are managed through the GitHub releases page
- The pipeline uses standard
npm publishcommands - Version bumping and release timing are handled by the maintainer
For significant changes or questions:
- Open a GitHub issue for discussion
- Reach out via DMs for architectural discussions
- Provide context about your specific use case
- Be respectful and constructive in all interactions
- Focus on real use cases and practical solutions
- Respect the project's philosophy of intentional simplicity
- Provide thorough testing and documentation for contributions
Thank you for helping make iOS Simulator MCP better! 🚀