From 124ea10c493eaaf7cc163cb6a9c5d7907a647f21 Mon Sep 17 00:00:00 2001 From: Sourabh Mehta Date: Fri, 17 Apr 2026 10:14:22 +0200 Subject: [PATCH 1/2] Show nightly dependency graph in GH summary --- .github/workflows/nightly.yml | 11 +++ scripts/get-package-deps.ts | 129 ++++++++++++++++++++++++++++++++++ 2 files changed, 140 insertions(+) create mode 100644 scripts/get-package-deps.ts diff --git a/.github/workflows/nightly.yml b/.github/workflows/nightly.yml index 16e1b548..c887f794 100644 --- a/.github/workflows/nightly.yml +++ b/.github/workflows/nightly.yml @@ -83,6 +83,7 @@ jobs: run: npm run lint - name: Update version for nightly build + id: nightly_version run: | # Increment patch version by 1 (e.g. 1.64.1 -> 1.64.2) BASE_VERSION=$(node -p "require('./package.json').version.split('-')[0]") @@ -111,6 +112,12 @@ jobs: # Create nightly version: 1.64.2-12-abc1234 NIGHTLY_VERSION="${NEXT_PATCH_VERSION}-${COMMIT_COUNT}-${SHORT_SHA}" echo "Setting version to ${NIGHTLY_VERSION}" + echo "nightly_version=${NIGHTLY_VERSION}" >> $GITHUB_OUTPUT + + # Print badge to GitHub Actions summary + echo "### Nightly Build Version" >> $GITHUB_STEP_SUMMARY + NIGHTLY_VERSION_BADGE=${NIGHTLY_VERSION//-/--} + echo "![Nightly Version](https://img.shields.io/badge/version-${NIGHTLY_VERSION_BADGE}-blue)" >> $GITHUB_STEP_SUMMARY # Update package.json npm version "${NIGHTLY_VERSION}" --no-git-tag-version @@ -221,6 +228,10 @@ jobs: path: ./*darwin-arm64*.vsix retention-days: 1 + - name: Print nightly build snapshot + run: | + npx tsx scripts/get-package-deps.ts "${{ steps.nightly_version.outputs.nightly_version }}" >> "$GITHUB_STEP_SUMMARY" + test: name: 'Test (windows-latest)' runs-on: windows-latest diff --git a/scripts/get-package-deps.ts b/scripts/get-package-deps.ts new file mode 100644 index 00000000..fe11a011 --- /dev/null +++ b/scripts/get-package-deps.ts @@ -0,0 +1,129 @@ +/** + * Copyright 2026 Arm Limited + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +// generated with AI + +/* + * Script to extract version info from manifest_*.yml files in ./tools/cmsis-toolbox + * and print a dependency graph in the format used in the GitHub Actions summary. + * Usage: npx tsx scripts/print-toolbox-deps.ts + */ +import fs from 'fs'; +import path from 'path'; +import yaml from 'yaml'; +import { fileURLToPath } from 'url'; + +// ESM-compatible __dirname +const __filename = fileURLToPath(import.meta.url); +const __dirname = path.dirname(__filename); + +const TOOLBOX_DIR = path.join(__dirname, '../tools/cmsis-toolbox'); +const UV2CSOLUTION_DIR = path.join(__dirname, '../tools/uv2csolution'); +const PACKAGE_JSON_PATH = path.join(__dirname, '../package.json'); +const MANIFEST_PATTERN = /^manifest_.*\.yml$/; + +// Children of cmsis-toolbox (in display order) +const TOOLBOX_CHILDREN = [ + 'cbridge', + 'cbuild', + 'cbuild2cmake', + 'cbuildgen', + 'cpackget', + 'csolution', + 'packchk', + 'svdconv', + 'vidx2pidx', +]; + +function findManifestFiles(dir: string): string[] { + return fs.readdirSync(dir) + .filter(f => MANIFEST_PATTERN.test(f)) + .map(f => path.join(dir, f)); +} + +function parseManifest(file: string): Record { + const doc = yaml.parse(fs.readFileSync(file, 'utf8')) as any; + const versions: Record = {}; + // Top-level cmsis-toolbox version + if (doc?.version) { + versions['cmsis-toolbox'] = doc.version; + } + // binaries is a map: { cbridge: { version: '...' }, cbuild: { version: '...' }, ... } + if (doc?.binaries && typeof doc.binaries === 'object') { + for (const [name, info] of Object.entries(doc.binaries as Record)) { + if (info?.version) { + versions[name] = info.version; + } + } + } + return versions; +} + +function getUv2csolutionVersion(): string | undefined { + // Try version.txt in the uv2csolution folder first + const versionFile = path.join(UV2CSOLUTION_DIR, 'version.txt'); + if (fs.existsSync(versionFile)) { + const v = fs.readFileSync(versionFile, 'utf8').trim(); + if (v) return v; + } + // Fall back to package.json csolution.uv2csolutionVersion + if (fs.existsSync(PACKAGE_JSON_PATH)) { + const pkg = JSON.parse(fs.readFileSync(PACKAGE_JSON_PATH, 'utf8')); + const v = pkg?.csolution?.uv2csolutionVersion; + if (v) return String(v); + } + return undefined; +} + +function mergeVersions(manifests: Record[]): Record { + const merged: Record = {}; + for (const m of manifests) { + for (const [k, v] of Object.entries(m)) { + merged[k] = v; + } + } + return merged; +} + +function printDependencyGraph(versions: Record, uv2csolutionVersion: string | undefined, nightlyVersion: string) { + console.log('```text'); + console.log(`vscode-cmsis-solution ${nightlyVersion}`); + console.log(` └── cmsis-toolbox v${versions['cmsis-toolbox'] ?? 'unknown'}`); + for (let i = 0; i < TOOLBOX_CHILDREN.length; ++i) { + const tool = TOOLBOX_CHILDREN[i]; + const ver = versions[tool] ?? 'unknown'; + const isLast = i === TOOLBOX_CHILDREN.length - 1; + const prefix = isLast ? ' │ └──' : ' │ ├──'; + console.log(`${prefix} ${tool} v${ver}`); + } + console.log(` └─── uv2csolution v${uv2csolutionVersion ?? 'unknown'}`); + console.log('```'); +} + +function main() { + const nightlyVersion = process.argv[2] || process.env.NIGHTLY_VERSION || 'unknown'; + const manifestFiles = findManifestFiles(TOOLBOX_DIR); + if (manifestFiles.length === 0) { + console.error('No manifest_*.yml files found in', TOOLBOX_DIR); + process.exit(1); + } + const manifests = manifestFiles.map(parseManifest); + const versions = mergeVersions(manifests); + const uv2csolutionVersion = getUv2csolutionVersion(); + printDependencyGraph(versions, uv2csolutionVersion, nightlyVersion); +} + +main(); \ No newline at end of file From fae5dc0f3acf890d8dc7669750b66212f3fb5986 Mon Sep 17 00:00:00 2001 From: Sourabh Mehta Date: Mon, 20 Apr 2026 14:00:58 +0200 Subject: [PATCH 2/2] Addressed review findings --- scripts/get-package-deps.ts | 29 ++++++++++++++++++++++------- 1 file changed, 22 insertions(+), 7 deletions(-) diff --git a/scripts/get-package-deps.ts b/scripts/get-package-deps.ts index fe11a011..e9798e56 100644 --- a/scripts/get-package-deps.ts +++ b/scripts/get-package-deps.ts @@ -1,3 +1,5 @@ +#!npx tsx + /** * Copyright 2026 Arm Limited * @@ -19,7 +21,7 @@ /* * Script to extract version info from manifest_*.yml files in ./tools/cmsis-toolbox * and print a dependency graph in the format used in the GitHub Actions summary. - * Usage: npx tsx scripts/print-toolbox-deps.ts + * Usage: npx tsx scripts/get-package-deps.ts */ import fs from 'fs'; import path from 'path'; @@ -49,9 +51,21 @@ const TOOLBOX_CHILDREN = [ ]; function findManifestFiles(dir: string): string[] { - return fs.readdirSync(dir) - .filter(f => MANIFEST_PATTERN.test(f)) - .map(f => path.join(dir, f)); + if (!fs.existsSync(dir)) { + console.error(`Toolbox directory not found: ${dir}`); + process.exit(1); + } + + try { + return fs.readdirSync(dir) + .filter(f => MANIFEST_PATTERN.test(f)) + .map(f => path.join(dir, f)); + } + catch (error) { + const message = error instanceof Error ? error.message : String(error); + console.error(`Failed to read toolbox directory "${dir}": ${message}`); + process.exit(1); + } } function parseManifest(file: string): Record { @@ -101,15 +115,16 @@ function mergeVersions(manifests: Record[]): Record, uv2csolutionVersion: string | undefined, nightlyVersion: string) { console.log('```text'); console.log(`vscode-cmsis-solution ${nightlyVersion}`); - console.log(` └── cmsis-toolbox v${versions['cmsis-toolbox'] ?? 'unknown'}`); + + console.log(` ├── cmsis-toolbox v${versions['cmsis-toolbox'] ?? 'unknown'}`); for (let i = 0; i < TOOLBOX_CHILDREN.length; ++i) { const tool = TOOLBOX_CHILDREN[i]; const ver = versions[tool] ?? 'unknown'; const isLast = i === TOOLBOX_CHILDREN.length - 1; - const prefix = isLast ? ' │ └──' : ' │ ├──'; + const prefix = isLast ? ' │ └──' : ' │ ├──'; console.log(`${prefix} ${tool} v${ver}`); } - console.log(` └─── uv2csolution v${uv2csolutionVersion ?? 'unknown'}`); + console.log(` └── uv2csolution v${uv2csolutionVersion ?? 'unknown'}`); console.log('```'); }