Skip to content

Fix platform-specific builds via CI matrix#4

Open
josh-hemphill wants to merge 1 commit into
lextudio:masterfrom
josh-hemphill:cursor/ci-matrix-platform-specific-vsix
Open

Fix platform-specific builds via CI matrix#4
josh-hemphill wants to merge 1 commit into
lextudio:masterfrom
josh-hemphill:cursor/ci-matrix-platform-specific-vsix

Conversation

@josh-hemphill

Copy link
Copy Markdown

Problem

Releases were packaged as a single generic VSIX built on the author's ARM
machine. Because dotnet publish was called without a Runtime Identifier, the
bundled .NET apphosts (XamlDesigner.exe, wpf-xaml-ls.exe,
wpf-project-analyzer) were ARM64 native — but shipped to all users,
including x64. x64 users got binaries that don't run.

There was also no CI, and package.json referenced scripts that don't exist
(dist.windows.ps1, publish.ps1).

Fix

Build platform-specific VSIXes on matching CI runners, with architecture
derived automatically from the vsce target:

Artifact Arch mechanism Why
Modern XamlDesigner.exe, wpf-xaml-ls.exe, wpf-project-analyzer RID (-r win-x64) apphost bitness + R2R
net481 designer PlatformTarget (x64/ARM64) .NET Framework has no RID
WpfHotReload.Runtime.dll none (AnyCPU) injected into user's process; must load on any arch

Changes

  • .github/workflows/ci.yml — new: test → 6-leg package matrix → tag-gated publish
  • dist.all.ps1-Target, -RuntimeIdentifier, -PlatformTarget, and -All; RID/PlatformTarget derived from -Target
  • scripts/build-designer.ps1 — RID for modern designer, PlatformTarget for net481
  • XamlLanguageServer.Wpf.csproj — R2R enabled only when a RID is present
  • package.json — fixed dead script references
  • CLAUDE.md — documents build/release + local cross-publishing

Cross-arch correctness is now automatic

Since the RID comes from -Target, you can build a correct package for any
platform from any machine (e.g. a valid x64 VSIX on your ARM laptop).


How to publish (for author)

Recommended: let CI publish (one-time setup)

  1. Create a Marketplace PAT and add it as a repo secret named VSCE_PAT
    (Settings → Secrets and variables → Actions → New repository secret).
  2. Push a version tag:
    git tag v0.9.15
    git push origin v0.9.15
  3. The publish job runs after all six package legs succeed and publishes
    every platform VSIX in one shot. Marketplace routes each target to the
    matching VS Code host.

Note: package.json version is synced from the latest tag, so tag first.

Until VSCE_PAT is set up: publish locally

Authenticate once, then build + publish everything:

npx @vscode/vsce login <publisher>        # or: set the VSCE_PAT env var
pwsh ./dist.all.ps1 -All -Publish         # builds & publishes all 6 targets

Or build all without publishing (inspect first):

pwsh ./dist.all.ps1 -All

Publishing a single platform (or skipping a broken one)

Each target is independent — build/publish them one at a time:

pwsh ./dist.all.ps1 -Target win32-x64   -Publish
pwsh ./dist.all.ps1 -Target win32-arm64 -Publish
pwsh ./dist.all.ps1 -Target darwin-arm64 -Publish
pwsh ./dist.all.ps1 -Target darwin-x64   -Publish
pwsh ./dist.all.ps1 -Target linux-x64    -Publish
pwsh ./dist.all.ps1 -Target linux-arm64  -Publish

Drop -Publish to only produce the .vsix. To publish a .vsix you already
built:

npx @vscode/vsce publish --packagePath vscode-wpf-<version>-<target>.vsix

Valid targets: win32-x64, win32-arm64, darwin-x64, darwin-arm64,
linux-x64, linux-arm64.


Notes / things to watch

  • Cross-building Windows targets locally: the modern .NET apphosts honor the
    RID, so this works from any host. The net481 designer uses PlatformTarget;
    building the win32-arm64 leg's net481 variant is unusual for .NET Framework
    and is the most likely leg to need attention — it runs on the windows-11-arm
    runner in CI.
  • First platform-specific release: once a version ships with --target,
    the Marketplace expects a package for every supported platform at that version.
    Publish all legs for the same version (CI does this automatically).
  • Skipping a platform: if one leg is broken, you can publish the others
    individually (commands above) and add the missing one later under the same
    version.

Build per-target VSIXes with architecture derived from the vsce target:
RID for .NET Core apphosts, PlatformTarget for the net481 designer. Adds
GitHub Actions test/package/publish workflow and a -All local cross-publish
path; fixes dead package.json script references.
@CLAassistant

CLAassistant commented Jun 20, 2026

Copy link
Copy Markdown

CLA assistant check
All committers have signed the CLA.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants