feat: MCPB bundle with generated manifest and release packaging #398
Workflow file for this run
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Dependency Compatibility Check | |
| # This workflow verifies that when users install n8n-mcp via npm (without lockfile), | |
| # they get compatible dependency versions. This catches issues like #440, #444, #446, #447, #450 | |
| # where npm resolution gave users incompatible SDK/Zod versions. | |
| on: | |
| push: | |
| branches: [main] | |
| paths: | |
| - 'package.json' | |
| - 'package-lock.json' | |
| - '.github/workflows/dependency-check.yml' | |
| pull_request: | |
| branches: [main] | |
| paths: | |
| - 'package.json' | |
| - 'package-lock.json' | |
| - '.github/workflows/dependency-check.yml' | |
| # Allow manual trigger for debugging | |
| workflow_dispatch: | |
| # Run weekly to catch upstream dependency changes | |
| schedule: | |
| - cron: '0 6 * * 1' # Every Monday at 6 AM UTC | |
| permissions: | |
| contents: read | |
| jobs: | |
| fresh-install-check: | |
| name: Fresh Install Dependency Check | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 10 | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| - name: Setup Node.js | |
| uses: actions/setup-node@v4 | |
| with: | |
| node-version: 20 | |
| - name: Build package | |
| # See test.yml for the --legacy-peer-deps rationale (mappersmith / diff conflict). | |
| run: | | |
| npm ci --legacy-peer-deps | |
| npm run build | |
| - name: Pack package for testing | |
| run: npm pack | |
| - name: Create fresh install test directory | |
| run: | | |
| mkdir -p /tmp/fresh-install-test | |
| cp n8n-mcp-*.tgz /tmp/fresh-install-test/ | |
| - name: Install package fresh (simulating user install) | |
| working-directory: /tmp/fresh-install-test | |
| run: | | |
| npm init -y | |
| # Install from tarball WITHOUT lockfile (simulates npm install n8n-mcp) | |
| # Use --ignore-scripts to skip native compilation of transitive deps like isolated-vm | |
| # (n8n-mcp only reads node metadata, it doesn't execute n8n nodes at runtime) | |
| npm install --ignore-scripts ./n8n-mcp-*.tgz | |
| - name: Verify critical dependency versions | |
| working-directory: /tmp/fresh-install-test | |
| run: | | |
| echo "=== Dependency Version Check ===" | |
| echo "" | |
| # Get actual resolved versions | |
| SDK_VERSION=$(npm list @modelcontextprotocol/sdk --json 2>/dev/null | jq -r '.dependencies["n8n-mcp"].dependencies["@modelcontextprotocol/sdk"].version // .dependencies["@modelcontextprotocol/sdk"].version // "not found"') | |
| ZOD_VERSION=$(npm list zod --json 2>/dev/null | jq -r '.dependencies["n8n-mcp"].dependencies.zod.version // .dependencies.zod.version // "not found"') | |
| echo "MCP SDK version: $SDK_VERSION" | |
| echo "Zod version: $ZOD_VERSION" | |
| echo "" | |
| # Check MCP SDK version - must be exactly 1.28.0 | |
| if [[ "$SDK_VERSION" == "not found" ]]; then | |
| echo "❌ FAILED: Could not determine MCP SDK version!" | |
| echo " The dependency may not have been installed correctly." | |
| exit 1 | |
| fi | |
| if [[ "$SDK_VERSION" != "1.28.0" ]]; then | |
| echo "❌ FAILED: MCP SDK version mismatch!" | |
| echo " Expected: 1.28.0" | |
| echo " Got: $SDK_VERSION" | |
| echo "" | |
| echo "This can cause runtime errors. See issues #440, #444, #446, #447, #450" | |
| exit 1 | |
| fi | |
| echo "✅ MCP SDK version is correct: $SDK_VERSION" | |
| # Check Zod version - must be 3.x (not 4.x, including pre-releases) | |
| if [[ "$ZOD_VERSION" == "not found" ]]; then | |
| echo "❌ FAILED: Could not determine Zod version!" | |
| echo " The dependency may not have been installed correctly." | |
| exit 1 | |
| fi | |
| if [[ "$ZOD_VERSION" =~ ^4\. ]]; then | |
| echo "❌ FAILED: Zod v4 detected - incompatible with MCP SDK 1.27.1!" | |
| echo " Expected: 3.x" | |
| echo " Got: $ZOD_VERSION" | |
| echo "" | |
| echo "Zod v4 causes '_zod' property errors. See issues #440, #444, #446, #447, #450" | |
| exit 1 | |
| fi | |
| echo "✅ Zod version is compatible: $ZOD_VERSION" | |
| echo "" | |
| echo "=== All dependency checks passed ===" | |
| - name: Test basic functionality | |
| working-directory: /tmp/fresh-install-test | |
| run: | | |
| echo "=== Basic Functionality Test ===" | |
| # Create a simple test script | |
| cat > test-import.mjs << 'EOF' | |
| import { spawn } from 'child_process'; | |
| import path from 'path'; | |
| import { fileURLToPath } from 'url'; | |
| const __dirname = path.dirname(fileURLToPath(import.meta.url)); | |
| // Test that the package can be required and basic tools work | |
| async function test() { | |
| console.log('Testing n8n-mcp package import...'); | |
| // Start the MCP server briefly to verify it initializes | |
| const serverPath = path.join(__dirname, 'node_modules/n8n-mcp/dist/mcp/index.js'); | |
| const proc = spawn('node', [serverPath], { | |
| env: { ...process.env, MCP_MODE: 'stdio' }, | |
| stdio: ['pipe', 'pipe', 'pipe'] | |
| }); | |
| // Send initialize request | |
| const initRequest = JSON.stringify({ | |
| jsonrpc: '2.0', | |
| id: 1, | |
| method: 'initialize', | |
| params: { | |
| protocolVersion: '2024-11-05', | |
| capabilities: {}, | |
| clientInfo: { name: 'test', version: '1.0.0' } | |
| } | |
| }); | |
| proc.stdin.write(initRequest + '\n'); | |
| // Wait for response or timeout | |
| let output = ''; | |
| let stderrOutput = ''; | |
| proc.stdout.on('data', (data) => { | |
| output += data.toString(); | |
| }); | |
| proc.stderr.on('data', (data) => { | |
| stderrOutput += data.toString(); | |
| console.error('stderr:', data.toString()); | |
| }); | |
| // Give it 5 seconds to respond | |
| await new Promise((resolve) => setTimeout(resolve, 5000)); | |
| proc.kill(); | |
| // Check for Zod v4 compatibility errors (the bug we're testing for) | |
| const allOutput = output + stderrOutput; | |
| if (allOutput.includes('_zod') || allOutput.includes('Cannot read properties of undefined')) { | |
| console.error('❌ FAILED: Zod compatibility error detected!'); | |
| console.error('This indicates the SDK/Zod version fix is not working.'); | |
| console.error('See issues #440, #444, #446, #447, #450'); | |
| process.exit(1); | |
| } | |
| if (output.includes('"result"')) { | |
| console.log('✅ MCP server initialized successfully'); | |
| return true; | |
| } else { | |
| console.log('Output received:', output.substring(0, 500)); | |
| // Server might not respond in stdio mode without proper framing | |
| // But if we got here without crashing, that's still good | |
| console.log('✅ MCP server started without errors'); | |
| return true; | |
| } | |
| } | |
| test() | |
| .then(() => { | |
| console.log('=== Basic functionality test passed ==='); | |
| process.exit(0); | |
| }) | |
| .catch((err) => { | |
| console.error('❌ Test failed:', err.message); | |
| process.exit(1); | |
| }); | |
| EOF | |
| node test-import.mjs | |
| - name: Generate dependency report | |
| if: always() | |
| working-directory: /tmp/fresh-install-test | |
| run: | | |
| echo "=== Full Dependency Tree ===" > dependency-report.txt | |
| npm list --all >> dependency-report.txt 2>&1 || true | |
| echo "" >> dependency-report.txt | |
| echo "=== Critical Dependencies ===" >> dependency-report.txt | |
| npm list @modelcontextprotocol/sdk zod zod-to-json-schema >> dependency-report.txt 2>&1 || true | |
| cat dependency-report.txt | |
| - name: Upload dependency report | |
| if: always() | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: dependency-report-${{ github.run_number }} | |
| path: /tmp/fresh-install-test/dependency-report.txt | |
| retention-days: 30 |