| name | mcp-app-verification |
| description | Comprehensive verification checklists for MCP Apps. Tests with basic-host reference, validates handler-before-connect, text fallback, resource URI linking, single-file bundling, host styling, CSP, and legacy pattern detection. |
| allowed-tools | Read, Bash, Glob, Grep |
| graph | {"domains":["domain:software-engineering"],"specializations":["specialization:ai-agents-conversational"],"skillAreas":["skill-area:mcp-server-implementation","skill-area:agent-simulation-testing"],"roles":["role:backend-engineer","role:fullstack-engineer"],"workflows":["workflow:feature-development"],"topics":["topic:api-design"]} |
mcp-app-verification
Run comprehensive verification checklists for MCP Apps covering correctness, compatibility, and migration completeness.
Overview
MCP Apps have several critical invariants that must be verified before deployment. This skill provides systematic verification across multiple dimensions:
- Runtime verification: App loads and functions in basic-host reference
- Pattern verification: Critical code patterns are correct (handler-before-connect, text fallback)
- Build verification: Single-file bundle is valid and complete
- Styling verification: Host theming applies correctly
- CSP verification: All origins declared, no silent failures
- Migration verification: No remaining legacy patterns (OpenAI, old MIME types, snake_case)
Capabilities
basic-host Test Execution
- Build the MCP App
- Start the server
- Launch basic-host reference implementation against the server
- Verify app loads without console errors
- Verify handlers fire correctly
Handler-Before-Connect Invariant
- Search source code for
app.connect() call
- Verify ALL handlers (
ontoolinput, ontoolresult, onhostcontextchanged, onteardown) are registered BEFORE connect
- Flag violations -- handlers registered after connect will silently not work
Text Fallback Verification
- Search all tool handlers for
content array in return value
- Verify each tool returns at least one
{ type: 'text', text: '...' } entry
- Flag tools that only return
structuredContent without text fallback
Resource URI Link Integrity
- Extract all
resourceUri values from registerAppTool calls
- Extract all URIs from
registerAppResource calls
- Verify every tool
resourceUri has a matching registered resource
- Flag orphaned resources (registered but not referenced)
Single-File Bundle Verification
- Build the project
- Verify
dist/mcp-app.html (or equivalent) exists
- Check the HTML file is self-contained (no external
<script src>, <link href>, <img src> to relative paths)
- Verify
vite-plugin-singlefile is in dev dependencies
Host Styling Verification
- Search CSS for
var(--color-*, var(--font-*, var(--border-radius-* patterns
- Verify fallback values are present:
var(--color-background-primary, #ffffff) not just var(--color-background-primary)
- Check
onhostcontextchanged handler exists and applies styling
CSP Verification
- Build and search output for network origins
- Compare against CSP configuration in
registerAppResource
- Flag origins present in code but missing from CSP
- Verify conditional origins match between runtime and CSP config
Legacy Pattern Detection (Migration)
- Search for remaining OpenAI patterns:
window.openai.toolInput, window.openai.toolOutput, window.openai
- Search for old metadata paths:
openai/
- Search for old MIME types:
text/html+skybridge
- Search for hardcoded MIME type:
text/html;profile=mcp-app (should use RESOURCE_MIME_TYPE)
- Search for snake_case CSP:
_domains" or _domains: (should be camelCase)
Usage
Full Verification Workflow
npm run build
ls -la dist/mcp-app.html
grep -E '<script src="|<link.*href="|<img src="(?!data:)' dist/mcp-app.html
npm run serve &
SERVER_PID=$!
cd /tmp/mcp-ext-apps/examples/basic-host
SERVERS='["http://localhost:3001/mcp"]' npm run start
kill $SERVER_PID
Pattern Verification Commands
grep -n 'app\.connect\|\.ontoolinput\|\.ontoolresult\|\.onhostcontextchanged\|\.onteardown' src/main.ts
grep -A5 'return {' src/server.ts | grep -c 'content:'
grep 'resourceUri' src/server.ts
grep "registerAppResource" src/server.ts
grep 'RESOURCE_MIME_TYPE' src/server.ts
grep "text/html;profile" src/server.ts
grep -c 'var(--.*,' src/global.css
grep 'var(--' src/global.css | grep -v ','
Migration Verification (OpenAI -> MCP)
grep -rn 'openai/' src/
grep -rn 'text/html+skybridge' src/
grep -rn "text/html;profile=mcp-app" src/
grep -rn '_domains"' src/
grep -rn "_domains:" src/
grep -rn 'window\.openai\.toolInput' src/
grep -rn 'window\.openai\.toolOutput' src/
grep -rn 'window\.openai' src/
Automated Verification Script
#!/bin/bash
ERRORS=0
echo "=== MCP App Verification ==="
echo "[1/8] Building..."
npm run build 2>&1 || { echo "FAIL: Build failed"; ERRORS=$((ERRORS+1)); }
echo "[2/8] Checking single-file bundle..."
if [ ! -f dist/mcp-app.html ]; then
echo "FAIL: dist/mcp-app.html not found"
ERRORS=$((ERRORS+1))
fi
echo "[3/8] Checking for external references..."
EXT_REFS=$(grep -cE 'src="(?!data:)[^"]+"|href="(?!data:)[^"]+\.css"' dist/mcp-app.html 2>/dev/null || echo "0")
if [ "$EXT_REFS" -gt 0 ]; then
echo "WARN: Found $EXT_REFS potential external references"
fi
echo "[4/8] Checking handler-before-connect..."
CONNECT_LINE=$(grep -n 'app\.connect()' src/main.ts* 2>/dev/null | head -1 | cut -d: -f2)
if [ -n "$CONNECT_LINE" ]; then
LATE_HANDLERS=$(grep -n '\.on\(toolinput\|toolresult\|hostcontextchanged\|teardown\)' src/main.ts* 2>/dev/null | awk -F: -v cl="$CONNECT_LINE" '$2 > cl')
if [ -n "$LATE_HANDLERS" ]; then
echo "FAIL: Handlers registered after app.connect()"
ERRORS=$((ERRORS+1))
fi
fi
echo "[5/8] Checking text fallback..."
echo "[6/8] Checking RESOURCE_MIME_TYPE usage..."
HARDCODED=$(grep -rn "text/html;profile=mcp-app" src/ 2>/dev/null | wc -l)
if [ "$HARDCODED" -gt 0 ]; then
echo "FAIL: Hardcoded MIME type found (use RESOURCE_MIME_TYPE)"
ERRORS=$((ERRORS+1))
fi
echo "[7/8] Checking CSS variable fallbacks..."
NO_FALLBACK=$(grep 'var(--' src/*.css 2>/dev/null | grep -v ',' | wc -l)
if [ "$NO_FALLBACK" -gt 0 ]; then
echo "WARN: $NO_FALLBACK CSS variables without fallback values"
fi
echo "[8/8] Checking for legacy patterns..."
LEGACY=$(grep -rn 'window\.openai\|text/html+skybridge\|_domains"' src/ 2>/dev/null | wc -l)
if [ "$LEGACY" -gt 0 ]; then
echo "FAIL: $LEGACY legacy patterns found"
ERRORS=$((ERRORS+1))
fi
echo ""
if [ "$ERRORS" -eq 0 ]; then
echo "PASS: All verification checks passed"
else
echo "FAIL: $ERRORS verification errors found"
fi
exit $ERRORS
Verification Checklist (Summary)
Core Invariants
Styling
CSP (if applicable)
Migration (if applicable)
Runtime
Task Definition
const mcpAppVerificationTask = defineTask({
name: 'mcp-app-verification',
description: 'Run comprehensive MCP App verification',
inputs: {
projectDir: { type: 'string', required: true },
isMigration: { type: 'boolean', default: false },
migrationSource: { type: 'string', default: '' },
checkCsp: { type: 'boolean', default: true }
},
outputs: {
passed: { type: 'boolean' },
errors: { type: 'array' },
warnings: { type: 'array' },
artifacts: { type: 'array' }
},
async run(inputs, taskCtx) {
return {
kind: 'skill',
title: `Verify MCP App: ${inputs.projectDir}`,
skill: {
name: 'mcp-app-verification',
context: {
projectDir: inputs.projectDir,
isMigration: inputs.isMigration,
migrationSource: inputs.migrationSource,
checkCsp: inputs.checkCsp,
instructions: [
'Build the application',
'Verify single-file bundle integrity',
'Check handler-before-connect invariant',
'Verify text fallback in all tools',
'Validate resource URI linking',
'Check CSS variable fallbacks',
inputs.checkCsp ? 'Verify CSP completeness' : null,
inputs.isMigration ? 'Search for legacy patterns' : null,
'Test with basic-host reference'
].filter(Boolean)
}
},
io: {
inputJsonPath: `tasks/${taskCtx.effectId}/input.json`,
outputJsonPath: `tasks/${taskCtx.effectId}/result.json`
}
};
}
});
Applicable Processes
- create-mcp-app.js
- add-app-to-mcp-server.js
- convert-web-app-to-mcp.js
- migrate-openai-app-to-mcp.js
External Dependencies
- basic-host reference implementation (from SDK repo clone)
- Build toolchain for the target application
- grep/ripgrep for pattern searching
References
Related Skills
- mcp-tool-resource-pattern
- mcp-host-styling-integration
- mcp-csp-investigation
- single-file-bundling
- mcp-app-scaffolding
Related Agents
- mcp-app-architect
- mcp-ui-developer
- csp-security-auditor