summaryrefslogtreecommitdiff
path: root/scripts
diff options
context:
space:
mode:
Diffstat (limited to 'scripts')
-rw-r--r--scripts/Acquire-McpConformance.ps136
-rw-r--r--scripts/Publish-Release.ps18
-rw-r--r--scripts/Run-McpConformance.ps127
-rw-r--r--scripts/Run-McpTasksConformance.ps157
4 files changed, 127 insertions, 1 deletions
diff --git a/scripts/Acquire-McpConformance.ps1 b/scripts/Acquire-McpConformance.ps1
new file mode 100644
index 0000000..f6fa38f
--- /dev/null
+++ b/scripts/Acquire-McpConformance.ps1
@@ -0,0 +1,36 @@
+[CmdletBinding()]
+param(
+ [string]$EvidenceDirectory = "artifacts/evidence/mcp-2026-07-28/conformance-acquisition"
+)
+
+$ErrorActionPreference = "Stop"
+$repository = (Resolve-Path (Join-Path $PSScriptRoot "..")).Path
+$runnerDirectory = Join-Path $repository "build/conformance-runner"
+$evidence = [IO.Path]::GetFullPath($EvidenceDirectory, $repository)
+New-Item -ItemType Directory -Force -Path $runnerDirectory, $evidence | Out-Null
+
+$package = "@modelcontextprotocol/conformance@0.2.0-alpha.11"
+& npm install --prefix $runnerDirectory --package-lock=true --ignore-scripts --no-audit --no-fund $package 2>&1 |
+ Tee-Object -FilePath (Join-Path $evidence "npm-install.txt")
+if ($LASTEXITCODE -ne 0) { throw "npm install failed with exit code $LASTEXITCODE" }
+
+$packageJson = Join-Path $runnerDirectory "node_modules/@modelcontextprotocol/conformance/package.json"
+$metadata = Get-Content -Raw -LiteralPath $packageJson | ConvertFrom-Json
+if ($metadata.version -ne "0.2.0-alpha.11") { throw "Unexpected conformance version: $($metadata.version)" }
+$lockPath = Join-Path $runnerDirectory "package-lock.json"
+$lock = Get-Content -Raw -LiteralPath $lockPath | ConvertFrom-Json -AsHashtable
+$entry = $lock.packages["node_modules/@modelcontextprotocol/conformance"]
+[ordered]@{
+ package = $metadata.name
+ version = $metadata.version
+ integrity = $entry.integrity
+ resolved = $entry.resolved
+ acquired_at = [DateTimeOffset]::UtcNow.ToString("O")
+ node = (& node --version)
+ npm = (& npm --version)
+} | ConvertTo-Json | Set-Content -Encoding utf8 -LiteralPath (Join-Path $evidence "package.json")
+
+$bin = $metadata.bin.conformance
+& node (Join-Path (Split-Path $packageJson) $bin) list --server --requirements 2026-07-28 2>&1 |
+ Tee-Object -FilePath (Join-Path $evidence "server-scenarios.txt")
+if ($LASTEXITCODE -ne 0) { throw "Conformance scenario listing failed with exit code $LASTEXITCODE" }
diff --git a/scripts/Publish-Release.ps1 b/scripts/Publish-Release.ps1
index 8ada466..78b97ef 100644
--- a/scripts/Publish-Release.ps1
+++ b/scripts/Publish-Release.ps1
@@ -17,7 +17,13 @@ $zip = Join-Path $outputRootPath "$bundleName.zip"
$checksum = "$zip.sha256"
New-Item -ItemType Directory -Force -Path $outputRootPath | Out-Null
-if (Test-Path -LiteralPath $bundle) { Remove-Item -LiteralPath $bundle -Recurse -Force }
+if (Test-Path -LiteralPath $bundle) {
+ $resolvedBundle = (Resolve-Path -LiteralPath $bundle).Path
+ if (-not $resolvedBundle.StartsWith($outputRootPath + [IO.Path]::DirectorySeparatorChar, [StringComparison]::OrdinalIgnoreCase)) {
+ throw 'Existing Release Bundle escaped the validated output root.'
+ }
+ Get-ChildItem -LiteralPath $resolvedBundle -Force | Remove-Item -Recurse -Force
+}
if (Test-Path -LiteralPath $zip) { Remove-Item -LiteralPath $zip -Force }
if (Test-Path -LiteralPath $checksum) { Remove-Item -LiteralPath $checksum -Force }
diff --git a/scripts/Run-McpConformance.ps1 b/scripts/Run-McpConformance.ps1
new file mode 100644
index 0000000..d43095c
--- /dev/null
+++ b/scripts/Run-McpConformance.ps1
@@ -0,0 +1,27 @@
+[CmdletBinding()]
+param(
+ [Parameter(Mandatory)] [uri]$Url,
+ [string[]]$Scenario = @("server-stateless", "tools-list", "json-schema-2020-12", "server-sse-multiple-streams", "dns-rebinding-protection", "caching", "http-header-validation"),
+ [string]$EvidenceDirectory = "artifacts/evidence/mcp-2026-07-28/conformance-production"
+)
+
+$ErrorActionPreference = "Stop"
+if (-not $Url.IsLoopback) { throw "Conformance target must be loopback." }
+$repository = (Resolve-Path (Join-Path $PSScriptRoot "..")).Path
+$runnerDirectory = Join-Path $repository "build/conformance-runner"
+$packageJson = Join-Path $runnerDirectory "node_modules/@modelcontextprotocol/conformance/package.json"
+if (-not (Test-Path -LiteralPath $packageJson)) { throw "Offline runner is absent. Run scripts/Acquire-McpConformance.ps1 first." }
+$metadata = Get-Content -Raw -LiteralPath $packageJson | ConvertFrom-Json
+if ($metadata.version -ne "0.2.0-alpha.11") { throw "Unexpected conformance version: $($metadata.version)" }
+$cli = Join-Path (Split-Path $packageJson) $metadata.bin.conformance
+$evidence = [IO.Path]::GetFullPath($EvidenceDirectory, $repository)
+New-Item -ItemType Directory -Force -Path $evidence | Out-Null
+
+$failures = 0
+foreach ($name in $Scenario) {
+ $output = Join-Path $evidence $name
+ & node $cli server --url $Url.AbsoluteUri --scenario $name --spec-version 2026-07-28 --output-dir $output --verbose 2>&1 |
+ Tee-Object -FilePath (Join-Path $evidence "$name.txt")
+ if ($LASTEXITCODE -ne 0) { $failures++ }
+}
+if ($failures -ne 0) { throw "$failures conformance scenario(s) failed; no expected-failure baseline is permitted." }
diff --git a/scripts/Run-McpTasksConformance.ps1 b/scripts/Run-McpTasksConformance.ps1
new file mode 100644
index 0000000..470f6df
--- /dev/null
+++ b/scripts/Run-McpTasksConformance.ps1
@@ -0,0 +1,57 @@
+[CmdletBinding()]
+param(
+ [Parameter(Mandatory)] [uri]$Url,
+ [string]$EvidenceDirectory = "artifacts/evidence/mcp-2026-07-28/conformance-tasks"
+)
+
+$ErrorActionPreference = "Stop"
+if (-not $Url.IsLoopback) { throw "Conformance target must be loopback." }
+$repository = (Resolve-Path (Join-Path $PSScriptRoot "..")).Path
+$packageJson = Join-Path $repository "build/conformance-runner/node_modules/@modelcontextprotocol/conformance/package.json"
+if (-not (Test-Path -LiteralPath $packageJson)) { throw "Offline runner is absent. Run scripts/Acquire-McpConformance.ps1 first." }
+$metadata = Get-Content -Raw -LiteralPath $packageJson | ConvertFrom-Json
+if ($metadata.version -ne "0.2.0-alpha.11") { throw "Unexpected conformance version: $($metadata.version)" }
+$cli = Join-Path (Split-Path $packageJson) $metadata.bin.conformance
+$evidence = [IO.Path]::GetFullPath($EvidenceDirectory, $repository)
+New-Item -ItemType Directory -Force -Path $evidence | Out-Null
+$scenarios = @(
+ "tasks-lifecycle", "tasks-capability-negotiation", "tasks-wire-fields", "tasks-request-state-removal",
+ "tasks-mrtr-input", "tasks-request-headers", "tasks-dispatch-and-envelope", "tasks-status-notifications",
+ "tasks-required-task-error", "tasks-mrtr-composition"
+)
+
+$applicationFailures = @()
+$runnerLimitations = @()
+foreach ($scenario in $scenarios) {
+ $output = Join-Path $evidence $scenario
+ & node $cli server --url $Url.AbsoluteUri --scenario $scenario --spec-version 2026-07-28 --force --output-dir $output 2>&1 |
+ Tee-Object -FilePath (Join-Path $evidence "$scenario.txt")
+ $runnerExitCode = $LASTEXITCODE
+ $resultDirectory = Get-ChildItem -LiteralPath $output -Directory | Sort-Object LastWriteTimeUtc -Descending | Select-Object -First 1
+ if ($null -eq $resultDirectory) {
+ $runnerLimitations += "$scenario`:runner_exit_$runnerExitCode`:no_result_directory"
+ continue
+ }
+ $checksPath = Join-Path $resultDirectory.FullName "checks.json"
+ if (-not (Test-Path -LiteralPath $checksPath)) {
+ $runnerLimitations += "$scenario`:runner_exit_$runnerExitCode`:checks_missing"
+ continue
+ }
+ foreach ($check in (Get-Content -Raw -LiteralPath $checksPath | ConvertFrom-Json)) {
+ if ($check.status -ne "FAILURE") { continue }
+ if ($check.id -eq "wire-schema-valid" -and $check.errorMessage -match "CallToolResult: must have required property 'content'.*resultType.*task") {
+ $runnerLimitations += "$scenario`:$($check.id)"
+ } else {
+ $applicationFailures += "$scenario`:$($check.id) - $($check.errorMessage)"
+ }
+ }
+}
+[ordered]@{
+ runner_version = $metadata.version
+ scenarios = $scenarios
+ application_failure_count = $applicationFailures.Count
+ application_failures = $applicationFailures
+ runner_limitation_count = $runnerLimitations.Count
+ runner_limitations = $runnerLimitations
+} | ConvertTo-Json -Depth 5 | Set-Content -Encoding utf8 -LiteralPath (Join-Path $evidence "summary.json")
+if ($applicationFailures.Count -ne 0) { throw "$($applicationFailures.Count) application Tasks conformance check(s) failed." }