build_run_mac_ws
Build and run macOS applications from Xcode workspaces in a single command, streamlining development workflows.
Instructions
Builds and runs a macOS app from a workspace in one step.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| workspacePath | Yes | Path to the .xcworkspace file (Required) | |
| scheme | Yes | The scheme to use (Required) | |
| configuration | No | Build configuration (Debug, Release, etc.) | |
| derivedDataPath | No | Path where build products and other derived data will go | |
| extraArgs | No | Additional xcodebuild arguments | |
| preferXcodebuild | No | If true, prefers xcodebuild over the experimental incremental build system, useful for when incremental build system fails. |
Implementation Reference
- src/tools/build_macos.ts:137-216 (handler)Core handler logic for building and running macOS app from workspace: builds using xcodebuild, extracts app path from build settings, and launches with 'open' command.async function _handleMacOSBuildAndRunLogic(params: { workspacePath?: string; projectPath?: string; scheme: string; configuration: string; derivedDataPath?: string; arch?: string; extraArgs?: string[]; preferXcodebuild?: boolean; }): Promise<ToolResponse> { log('info', 'Handling macOS build & run logic...'); const _warningMessages: { type: 'text'; text: string }[] = []; const _warningRegex = /\[warning\]: (.*)/g; try { // First, build the app const buildResult = await _handleMacOSBuildLogic(params); // 1. Check if the build itself failed if (buildResult.isError) { return buildResult; // Return build failure directly } const buildWarningMessages = buildResult.content?.filter((c) => c.type === 'text') ?? []; // 2. Build succeeded, now get the app path using the helper const appPathResult = await _getAppPathFromBuildSettings(params); // 3. Check if getting the app path failed if (!appPathResult.success) { log('error', 'Build succeeded, but failed to get app path to launch.'); const response = createTextResponse( `✅ Build succeeded, but failed to get app path to launch: ${appPathResult.error}`, false, // Build succeeded, so not a full error ); if (response.content) { response.content.unshift(...buildWarningMessages); } return response; } const appPath = appPathResult.appPath; // We know this is a valid string now log('info', `App path determined as: ${appPath}`); // 4. Launch the app using the verified path // Launch the app try { await promisify(exec)(`open "${appPath}"`); log('info', `✅ macOS app launched successfully: ${appPath}`); const successResponse: ToolResponse = { content: [ ...buildWarningMessages, { type: 'text', text: `✅ macOS build and run succeeded for scheme ${params.scheme}. App launched: ${appPath}`, }, ], }; return successResponse; } catch (launchError) { const errorMessage = launchError instanceof Error ? launchError.message : String(launchError); log('error', `Build succeeded, but failed to launch app ${appPath}: ${errorMessage}`); const errorResponse = createTextResponse( `✅ Build succeeded, but failed to launch app ${appPath}. Error: ${errorMessage}`, false, // Build succeeded ); if (errorResponse.content) { errorResponse.content.unshift(...buildWarningMessages); } return errorResponse; } } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); log('error', `Error during macOS build & run logic: ${errorMessage}`); const errorResponse = createTextResponse( `Error during macOS build and run: ${errorMessage}`, true, ); return errorResponse; } }
- src/tools/build_macos.ts:289-319 (registration)Tool registration function that calls registerTool with name 'build_run_mac_ws', Zod schema, and handler reference.export function registerMacOSBuildAndRunWorkspaceTool(server: McpServer): void { type WorkspaceParams = { workspacePath: string; scheme: string; configuration?: string; derivedDataPath?: string; arch?: string; extraArgs?: string[]; preferXcodebuild?: boolean; }; registerTool<WorkspaceParams>( server, 'build_run_mac_ws', 'Builds and runs a macOS app from a workspace in one step.', { workspacePath: workspacePathSchema, scheme: schemeSchema, configuration: configurationSchema, derivedDataPath: derivedDataPathSchema, extraArgs: extraArgsSchema, preferXcodebuild: preferXcodebuildSchema, }, async (params) => _handleMacOSBuildAndRunLogic({ ...params, configuration: params.configuration ?? 'Debug', preferXcodebuild: params.preferXcodebuild ?? false, }), ); }
- src/utils/register-tools.ts:204-208 (registration)Central tool registration array entry that conditionally registers the macOS build-run workspace tool.{ register: registerMacOSBuildAndRunWorkspaceTool, groups: [ToolGroup.MACOS_WORKFLOW, ToolGroup.APP_DEPLOYMENT], envVar: 'XCODEBUILDMCP_TOOL_MACOS_BUILD_AND_RUN_WORKSPACE', },
- src/tools/build_macos.ts:304-311 (schema)Zod input schema definition for the tool parameters, composed from common schemas.{ workspacePath: workspacePathSchema, scheme: schemeSchema, configuration: configurationSchema, derivedDataPath: derivedDataPathSchema, extraArgs: extraArgsSchema, preferXcodebuild: preferXcodebuildSchema, },
- src/tools/build_macos.ts:47-71 (helper)Helper function that executes the xcodebuild build command for macOS.async function _handleMacOSBuildLogic(params: { workspacePath?: string; projectPath?: string; scheme: string; configuration: string; derivedDataPath?: string; arch?: string; extraArgs?: string[]; preferXcodebuild?: boolean; }): Promise<ToolResponse> { log('info', `Starting macOS build for scheme ${params.scheme} (internal)`); return executeXcodeBuildCommand( { ...params, }, { platform: XcodePlatform.macOS, arch: params.arch, logPrefix: 'macOS Build', }, params.preferXcodebuild, 'build', ); }