microsoft / microsoft/foundry-local

[Bug] Microsoft.AI.Foundry.Local.Core sets a global RuntimeIdentifier in buildTransitive, silently making consuming apps RID-specific

Open
#1,118 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

bug
Dominant language
C++
Stars
2.6k
Forks
369
Avg merge
2d 17h
Merged PRs (30d)
39

Description

### Describe the issue

`buildTransitive/Microsoft.AI.Foundry.Local.Core.targets` pins the consuming project's RuntimeIdentifier to the build machine's RID. The file's entire contents:

```


$(NETCoreSdkRuntimeIdentifier)

```

For a portable app that ships to more than one architecture this is silently destructive. It flips the whole project from portable to RID-specific, which changes how NuGet resolves native assets: they stop arriving as `RuntimeTargetsCopyLocalItems` destined for runtimes//native/ and instead arrive as `NativeCopyLocalItems` flattened into the output root, for one architecture only.

The failure is maximally delayed. The build succeeds, the installer succeeds, and the app dies on first launch on any machine whose architecture isn't the build agent's: because deps.json is still generated portable, with per-RID runtimeTargets entries. The host looks for e.g. runtimes/win-arm64/native/libSkiaSharp.dll, doesn't find it, falls back to the app directory, and loads the x64 copy the build left there. `BadImageFormatException`.

### To reproduce

```

net10.0-windows
win-x64;win-arm64

```

```
msbuild App.csproj -t:ResolvePackageAssets -getProperty:RuntimeIdentifier
msbuild App.csproj -t:ResolvePackageAssets -getItem:NativeCopyLocalItems,RuntimeTargetsCopyLocalItems
```

| | without the package | with it |
|---------------------------------|--------------------------------------------------------------------------------------|----------------------|
| RuntimeIdentifier after targets | (empty) | win-x64 (the host's) |
| item group | RuntimeTargetsCopyLocalItems | NativeCopyLocalItems |
| DestinationSubPath | runtimes\win-x64\native\libSkiaSharp.dll, runtimes\win-arm64\native\libSkiaSharp.dll | libSkiaSharp.dll |

Note RuntimeIdentifier evaluates empty and only becomes non-empty after targets run, so -getProperty without -t: won't show it. MSBUILDLOGPROPERTYTRACKING=15 attributes it to the package's targets file.

### Urgency

Why this is a packaging bug, not a preference

1. A library shouldn't set a global property that redefines its consumer's build: asset resolution, output layout and deps.json all change, none of it requested.
2. It's in buildTransitive, the widest possible reach, so it hits projects that never referenced the package. In our case the PackageReference was on a library; the damage landed in the application project several hops away.
3. Defaulting to the build host's RID is wrong for anything built once and shipped to many architectures. CI agents are overwhelmingly x64; users increasingly are not.
4. Condition="'$(RuntimeIdentifier)'==''" means it's invisible to anyone already setting a RID; i.e. it only fires on exactly the projects it will break.

**Workaround**:

This must be applied to every project that produces a payload, not just the one with the direct reference. The targets flow transitively through ProjectReference. Nothing is lost; that six-line targets file is the package's entire build contribution.

### Platform and architecture

Windows ARM64

### OS Version

Any

### Installation type

Released package/binary

### Foundry Local version

1.2.5

### API or surface area

C# SDK

### Hardware acceleration/backend

Other / Unknown

### Backend/runtime version

Doesn't matter

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with buildTransitive/Microsoft.AI.Foundry.Local.Core.targets, then run the listed MSBuild ResolvePackageAssets commands against the reproduction project. Verify that consuming projects no longer receive a host-derived RuntimeIdentifier and that SkiaSharp assets remain in RuntimeTargetsCopyLocalItems with per-RID paths for win-x64 and win-arm64.

Written by the indexing model from the issue text.

Assessment

Tech stack
csharp
Domain
build-system
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Active
Clarity
Clearly specified
Newbie friendliness
72/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.