1- name : QL MCP Client Integration Tests
1+ name : Build and Test Client - CodeQL Development MCP Server
22
33on :
4- push :
5- branches : [main, next]
4+ pull_request :
5+ branches : [' main', ' next' ]
66 paths :
77 - ' .github/actions/setup-codeql-environment/action.yml'
8- - ' .github/workflows/client-integration-tests .yml'
8+ - ' .github/workflows/build-and-test-client .yml'
99 - ' .codeql-version'
1010 - ' .node-version'
1111 - ' client/**'
1212 - ' server/**'
13- pull_request :
14- branches : [main, next]
13+ push :
14+ branches : [' main', ' next' ]
1515 paths :
1616 - ' .github/actions/setup-codeql-environment/action.yml'
17- - ' .github/workflows/client-integration-tests .yml'
17+ - ' .github/workflows/build-and-test-client .yml'
1818 - ' .codeql-version'
1919 - ' .node-version'
2020 - ' client/**'
@@ -25,8 +25,48 @@ permissions:
2525 contents : read
2626
2727jobs :
28+ build-and-test-client :
29+ name : Build and Unit Test (${{ matrix.os }})
30+ runs-on : ${{ matrix.os }}
31+
32+ strategy :
33+ fail-fast : false
34+ matrix :
35+ os : [ubuntu-latest, windows-latest]
36+
37+ steps :
38+ - name : Checkout repository
39+ uses : actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6
40+
41+ - name : Setup Go environment
42+ uses : actions/setup-go@40f1582b2485089dde7abd97c1529aa768e1baff # v5
43+ with :
44+ cache-dependency-path : ' client/go.sum'
45+ go-version-file : ' client/go.mod'
46+
47+ - name : Build client
48+ shell : bash
49+ run : make -C client build SHELL="$(which bash)"
50+
51+ - name : Run unit tests
52+ shell : bash
53+ run : make -C client test-unit SHELL="$(which bash)"
54+
55+ - name : Lint
56+ shell : bash
57+ run : make -C client lint SHELL="$(which bash)"
58+
59+ - name : Summary
60+ shell : bash
61+ run : |
62+ echo "## Build and Unit Test Client (${{ matrix.os }})" >> $GITHUB_STEP_SUMMARY
63+ echo "✅ Go build completed" >> $GITHUB_STEP_SUMMARY
64+ echo "✅ Unit tests passed" >> $GITHUB_STEP_SUMMARY
65+ echo "✅ Lint checks passed" >> $GITHUB_STEP_SUMMARY
66+
2867 integration-tests :
2968 name : Integration Tests (${{ matrix.os }}, ${{ matrix.mcp-mode }})
69+ needs : build-and-test-client
3070 runs-on : ${{ matrix.os }}
3171
3272 strategy :
@@ -43,33 +83,33 @@ jobs:
4383 URL_SCHEME : ' http'
4484
4585 steps :
46- - name : MCP Integration Tests - Checkout repository
86+ - name : Checkout repository
4787 uses : actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6
4888
49- - name : MCP Integration Tests - Setup Node.js environment
89+ - name : Setup Go environment
90+ uses : actions/setup-go@40f1582b2485089dde7abd97c1529aa768e1baff # v5
91+ with :
92+ cache-dependency-path : ' client/go.sum'
93+ go-version-file : ' client/go.mod'
94+
95+ - name : Setup Node.js environment
5096 uses : actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6
5197 with :
5298 cache : ' npm'
5399 node-version-file : ' .node-version'
54100
55- - name : MCP Integration Tests - Setup Go environment
56- uses : actions/setup-go@40f1582b2485089dde7abd97c1529aa768e1baff # v5
57- with :
58- go-version-file : ' client/go.mod'
59- cache-dependency-path : ' client/go.sum'
60-
61- - name : MCP Integration Tests - Install OS dependencies (Ubuntu)
101+ - name : Install OS dependencies (Ubuntu)
62102 if : runner.os == 'Linux'
63103 run : sudo apt-get install -y jq
64104
65- - name : MCP Integration Tests - Install OS dependencies (Windows)
105+ - name : Install OS dependencies (Windows)
66106 if : runner.os == 'Windows'
67107 run : choco install jq -y
68108
69- - name : MCP Integration Tests - Install node dependencies for server workspace
109+ - name : Install node dependencies for server workspace
70110 run : npm ci --workspace=server
71111
72- - name : MCP Integration Tests - Setup CodeQL environment
112+ - name : Setup CodeQL environment
73113 uses : ./.github/actions/setup-codeql-environment
74114 with :
75115 install-language-runtimes : false
78118 # # bash. On Windows, Node.js spawn()/execFile() require a real .exe
79119 # # binary on PATH, not a bash stub or .cmd wrapper. Fail fast here
80120 # # instead of waiting for integration tests to time out.
81- - name : MCP Integration Tests - Verify CodeQL CLI is spawnable from Node.js
121+ - name : Verify CodeQL CLI is spawnable from Node.js
82122 shell : bash
83123 run : |
84124 node -e "
@@ -93,39 +133,32 @@ jobs:
93133 });
94134 "
95135
96- # # Install packs used in the integration tests.
97- - name : MCP Integration Tests - Install CodeQL packs
136+ - name : Install CodeQL packs
98137 shell : bash
99138 run : ./server/scripts/install-packs.sh
100139
101140 # # Extract test databases used in the integration tests.
102141 # # Defaults to integration scope (javascript/examples + specific tools
103142 # # databases referenced by integration test fixtures).
104- # # Query unit tests auto-extract their own databases via `codeql test run`.
105- - name : MCP Integration Tests - Extract test databases
143+ - name : Extract test databases
106144 shell : bash
107145 run : ./server/scripts/extract-test-databases.sh
108146
109147 # # Configure npm to use bash for running scripts on Windows, since the
110148 # # integration test scripts are bash scripts that cmd.exe cannot execute.
111- - name : MCP Integration Tests - Configure npm script shell (Windows)
149+ - name : Configure npm script shell (Windows)
112150 if : runner.os == 'Windows'
113151 shell : bash
114152 run : npm config set script-shell "$(which bash)"
115153
116154 # # Run integration tests. This script builds the server bundle and runs tests.
117- # # We do NOT use 'npm run build-and-test' as it runs query unit tests which
118- # # have a dedicated workflow (query-unit-tests.yml).
119- # #
120155 # # On Windows, GNU Make's SHELL := bash resolves to WSL's bash.exe
121- # # (C:\Windows\System32\bash.exe) instead of Git Bash, causing
122- # # "Windows Subsystem for Linux has no installed distributions" errors.
123- # # We override SHELL with the full Git Bash path to avoid this.
124- - name : MCP Integration Tests - Run integration tests
156+ # # instead of Git Bash. We override SHELL with the full Git Bash path.
157+ - name : Run integration tests
125158 shell : bash
126159 run : make -C client test-integration SHELL="$(which bash)"
127160
128- - name : MCP Integration Tests - Stop the background MCP server process
161+ - name : Stop the background MCP server process
129162 if : always() && matrix.mcp-mode == 'http'
130163 shell : bash
131164 run : |
@@ -135,7 +168,6 @@ jobs:
135168 if kill -0 "$PID" 2>/dev/null; then
136169 kill "$PID" || true
137170 sleep 2
138- # Force kill if still running
139171 if kill -0 "$PID" 2>/dev/null; then
140172 echo "Force killing server process"
141173 kill -9 "$PID" || true
@@ -147,17 +179,14 @@ jobs:
147179 else
148180 echo "No server.pid file found"
149181 fi
150-
151- # Clean up log files
152182 if [ -f server.log ]; then
153- echo "Removing server.log"
154183 rm -f server.log
155184 fi
156185
157- - name : MCP Integration Tests - Summary
186+ - name : Summary
158187 shell : bash
159188 run : |
160- echo "## Integration Tests Summary (${{ matrix.os }}, ${{ matrix.mcp-mode }})" >> $GITHUB_STEP_SUMMARY
189+ echo "## Integration Tests (${{ matrix.os }}, ${{ matrix.mcp-mode }})" >> $GITHUB_STEP_SUMMARY
161190 echo "✅ MCP server integration tests passed on ${{ matrix.os }} with ${{ matrix.mcp-mode }} transport" >> $GITHUB_STEP_SUMMARY
162191
163192 codeql-path-tests :
@@ -170,40 +199,33 @@ jobs:
170199 os : [macos-latest, ubuntu-latest, windows-latest]
171200
172201 steps :
173- - name : CODEQL_PATH Tests - Checkout repository
202+ - name : Checkout repository
174203 uses : actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6
175204
176- - name : CODEQL_PATH Tests - Setup Node.js
205+ - name : Setup Node.js
177206 uses : actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6
178207 with :
179208 cache : ' npm'
180209 node-version-file : ' .node-version'
181210
182- - name : CODEQL_PATH Tests - Install server dependencies
211+ - name : Install server dependencies
183212 run : npm ci --workspace=server
184213
185- - name : CODEQL_PATH Tests - Build server bundle
214+ - name : Build server bundle
186215 run : npm run bundle -w server
187216
188- - name : CODEQL_PATH Tests - Setup CodeQL environment
217+ - name : Setup CodeQL environment
189218 uses : ./.github/actions/setup-codeql-environment
190219 with :
191220 add-to-path : false
192221 install-language-runtimes : false
193222
194223 # # Locate the real CodeQL binary (not the gh-codeql bash stub).
195- # # The stub delegates to `gh codeql` and works from bash, but Node.js
196- # # execFile() on Windows cannot execute bash scripts — it needs a real
197- # # .exe. We search the gh-codeql distribution directory for the binary.
198- - name : CODEQL_PATH Tests - Locate CodeQL binary
224+ - name : Locate CodeQL binary
199225 id : locate-codeql
200226 shell : bash
201227 run : |
202228 if [[ "$RUNNER_OS" == "Windows" ]]; then
203- # The gh-codeql extension stores CodeQL distributions under
204- # %LOCALAPPDATA%\GitHub\gh-codeql on Windows (its own data dir),
205- # separate from the GitHub CLI extensions directory. Search there
206- # first, then fall back to the extensions dir and all LOCALAPPDATA.
207229 LOCALAPPDATA_DIR="${LOCALAPPDATA:-$HOME/AppData/Local}"
208230 CODEQL_BINARY=""
209231 for search_dir in \
@@ -218,7 +240,6 @@ jobs:
218240 fi
219241 fi
220242 done
221- # Convert MSYS path to Windows mixed-mode path for Node.js
222243 if [[ -n "$CODEQL_BINARY" ]]; then
223244 CODEQL_BINARY=$(cygpath -m "$CODEQL_BINARY")
224245 fi
@@ -238,7 +259,6 @@ jobs:
238259 exit 1
239260 fi
240261
241- # Verify the binary works and reports the expected version
242262 ACTUAL=$("$CODEQL_BINARY" version --format=terse 2>/dev/null)
243263 EXPECTED=$(gh codeql version --format=terse 2>/dev/null)
244264 if [[ "$ACTUAL" != "$EXPECTED" ]]; then
@@ -251,9 +271,7 @@ jobs:
251271 echo "codeql-binary=$CODEQL_BINARY" >> "$GITHUB_OUTPUT"
252272
253273 # # Build a PATH that excludes every directory containing 'codeql'.
254- # # This simulates an environment where the CodeQL CLI is not installed
255- # # globally, forcing the server to rely solely on CODEQL_PATH.
256- - name : CODEQL_PATH Tests - Build clean PATH without CodeQL
274+ - name : Build clean PATH without CodeQL
257275 shell : bash
258276 run : |
259277 CLEAN_PATH=""
@@ -267,7 +285,6 @@ jobs:
267285 esac
268286 done
269287
270- # Verify codeql is NOT findable on the clean PATH
271288 if PATH="$CLEAN_PATH" command -v codeql >/dev/null 2>&1; then
272289 echo "::error::codeql is still discoverable after PATH cleanup"
273290 exit 1
@@ -276,25 +293,19 @@ jobs:
276293 echo "✅ codeql is not on the clean PATH"
277294 echo "CLEAN_PATH=$CLEAN_PATH" >> "$GITHUB_ENV"
278295
279- # # Test 1: The server must fail early at startup when CODEQL_PATH points
280- # # to a non-existent file and codeql is not on PATH.
281- - name : CODEQL_PATH Tests - Test 1 - Fail with invalid CODEQL_PATH
296+ - name : Test 1 - Fail with invalid CODEQL_PATH
282297 shell : bash
283298 run : ./server/scripts/test-codeql-path-invalid.sh
284299
285- # # Test 2: The server must fail at startup when codeql is not on PATH
286- # # and CODEQL_PATH is not set.
287- - name : CODEQL_PATH Tests - Test 2 - Fail when codeql not on PATH and CODEQL_PATH not set
300+ - name : Test 2 - Fail when codeql not on PATH and CODEQL_PATH not set
288301 shell : bash
289302 run : ./server/scripts/test-codeql-path-missing.sh
290303
291- # # Test 3: The server must start without error when CODEQL_PATH points
292- # # to a valid CodeQL binary, even though codeql is not on PATH.
293- - name : CODEQL_PATH Tests - Test 3 - Start with valid CODEQL_PATH
304+ - name : Test 3 - Start with valid CODEQL_PATH
294305 shell : bash
295306 run : ./server/scripts/test-codeql-path-valid.sh "${{ steps.locate-codeql.outputs.codeql-binary }}"
296307
297- - name : CODEQL_PATH Tests - Summary
308+ - name : Summary
298309 shell : bash
299310 run : |
300311 echo "## CODEQL_PATH Tests (${{ matrix.os }})" >> $GITHUB_STEP_SUMMARY
0 commit comments