Source precedence limits for package IDs absent from NuGet source mapping
0 reputation · 14 Sept 2021, 14:56 UTC
0 reputation · 14 Sept 2021, 14:56 UTC
When multiple package sources are listed in NuGet.Config, NuGet evaluates them in the order they appear unless a source mapping section redirects a specific package ID. For package IDs that are not covered by source mapping, changing the order of sources can cause a restore to select a different version of the same package if the feeds expose different versions. This creates a practical design question about determinism for teams that cannot enumerate every package ID in a mapping section.
The uncertainty is whether source mapping is the only supported mechanism to guarantee a fixed source for a given package ID, or whether NuGet applies additional precedence rules when mapping is incomplete. Without full coverage, a reordered NuGet.Config may introduce version drift across restores, but the exact boundary between supported behavior and unsupported configuration is not obvious from the documentation alone.
Is source mapping the only supported way to enforce per-package source precedence in NuGet, or are there other configuration options that override the default source order?
When a package ID is absent from source mapping and multiple sources contain different versions, does NuGet cache the previously selected source and version, or does it re-evaluate source order on every restore?
Are there documented limits on how source mapping patterns interact with the default source list for unmapped package IDs?
34775 reputation · 14 Sept 2021, 21:20 UTC
Is source mapping the only supported way to enforce per‑package source precedence in NuGet?
Yes. In NuGet.Config the <packageSourceMapping> element is the sole mechanism that can bind a specific package ID (or pattern) to a particular source. No other configuration setting – such as credentials, globalPackagesFolder, or enable/disable flags – changes the per‑package precedence.
When a package ID is absent from source mapping and multiple sources expose different versions, does NuGet cache the previously selected source and version, or does it re‑evaluate source order on every restore?
NuGet re‑evaluates the source order on every restore. The decision is made at restore time by scanning the ordered <packageSources> list and picking the first source that provides a version matching the project’s request. The package cache (the folder that stores downloaded packages) does not influence this lookup – it only stores the binaries once they have been downloaded.
Only a lock file changes that. If the project contains a lock file (either .nuget.lock or the project.assets.json generated by a prior restore), NuGet will use the exact source and version recorded in that file, regardless of any later changes to <packageSources> or <packageSourceMapping>.
Are there documented limits on how source mapping patterns interact with the default source list for unmapped package IDs?
There is no hard limit on the number or complexity of mapping patterns beyond the syntax supported by the <packageSourceMapping> element. The resolution algorithm works as follows:
<packageSources> list.Because the mapping step is evaluated before the default list, there is no overlap or conflict between the two – the mapping simply short‑circuits the default order for the matched packages.
NuGet.Config with two sources:
packageSources:
- id: SourceA
value: https://sourcea.example.com/nuget
- id: SourceB
value: https://sourceb.example.com/nuget
SourceA hosts PackageX 1.0.0 and SourceB hosts PackageX 2.0.0.dotnet restore and inspect project.assets.json – you should see the source field pointing to SourceA and the version 1.0.0.dotnet restore --lockfile (or --use-lock-file). Swap the source order again and confirm that the version from the lock file is retained.To ensure deterministic restores without relying on source order, confirm whether your project has a lock file. If it does, source order changes will have no effect. If it doesn’t, any reorder of <packageSources> will change the resolved version for unmapped packages.
Do you currently have a lock file (e.g., .nuget.lock or project.assets.json) in your repository? Knowing that will determine whether source order changes are already mitigated in your workflow.
Use comments to ask for clarification. Post a solution as an answer.
6,510 reputation · 14 Sept 2021, 20:36 UTC
When <packageSourceMapping> directs a package ID to a particular source, NuGet first consults that mapping. If the mapped source is marked enabled="false" (or is otherwise unavailable), the mapping is treated as a mismatch and NuGet falls back to the default source order defined in <packageSources>. This means that a disabled source never wins even if it hosts the requested package.
Multiple NuGet.Config files are merged before resolution, so a mapping in a higher‑level config can override a mapping in a project‑level file, but the same disabled‑source rule applies across the merged set.