Skip to content

Use an MSBuild Task for RID selection instead of shelling out #8686

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 3 commits into
base: main
Choose a base branch
from

Conversation

baronfel
Copy link
Member

Description

This is mostly a perf optimization. Today, during every restore, we shell out to a binary that takes ~120ms:
image

This PR replaces this with a native MSBuild Task which takes ~3ms:
image

This handles the packaging too - this is such a simple task that we can reuse a lot of the previous mechanisms with minimal structural changes.

Checklist

  • Is this feature complete?
    • Yes. Ready to ship.
    • No. Follow-up changes expected.
  • Are you including unit tests for the changes and scenario tests if relevant?
    • Yes
    • No
  • Did you add public API?
    • Yes
      • If yes, did you have an API Review for it?
        • Yes
        • No
      • Did you add <remarks /> and <code /> elements on your triple slash comments?
        • Yes
        • No
    • No
  • Does the change make any security assumptions or guarantees?
    • Yes
      • If yes, have you done a threat model and had a security review?
        • Yes
        • No
    • No
  • Does the change require an update in our Aspire docs?

@github-actions github-actions bot added the needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners label Apr 10, 2025
@baronfel baronfel force-pushed the use-task-for-rid-selection branch 2 times, most recently from c0a9533 to b39d2a4 Compare April 10, 2025 02:03
removing dotnet_host logic since we're no longer spawning anything. consolidate RID patterns for easier viewing in binlogs
@baronfel baronfel force-pushed the use-task-for-rid-selection branch from b39d2a4 to 64b9551 Compare April 10, 2025 02:05
<_DashboardAndDCPSupportedTargetingRIDs Include="linux-arm64" />
<_DashboardAndDCPSupportedTargetingRIDs Include="osx-x64" />
<_DashboardAndDCPSupportedTargetingRIDs Include="osx-arm64" />
<_DashboardAndDCPSupportedTargetingRIDs Include="win-x64;win-x86;win-arm64;linux-x64;linux-arm64;osx-x64;osx-arm64" />
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is a nitpick kind of thing - when the items are declared inline like this they show as one 'thing' in the binlog viewer:
image

this is easier to look at than N separate items.

Comment on lines -108 to -122
<!-- If running in .NET Core, DOTNET_HOST_PATH is set to point to the dotnet executable being used
for the build. -->
<PropertyGroup>
<_DotNetHostPath>$(DOTNET_HOST_PATH)</_DotNetHostPath>
</PropertyGroup>

<!-- If running on .NET Framework MSBuild, then DOTNET_HOST_PATH won't be set, so we need to construct
the path using well-known properties. -->
<PropertyGroup Condition="'$(_DotNetHostPath)' == ''">
<_DotNetHostDirectory>$(NetCoreRoot)</_DotNetHostDirectory>
<_DotNetHostFileName>dotnet</_DotNetHostFileName>
<_DotNetHostFileName Condition="'$(OS)' == 'Windows_NT'">dotnet.exe</_DotNetHostFileName>

<_DotNetHostPath>$(_DotNetHostDirectory)\$(_DotNetHostFileName)</_DotNetHostPath>
</PropertyGroup>
Copy link
Member Author

@baronfel baronfel Apr 10, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

none of this is necessary if we're not spawning binaries anymore in the SDK-delivered targets

<OutputType>Exe</OutputType>
<TargetFramework>$(DefaultTargetFramework)</TargetFramework>
<RollForward>Major</RollForward>
<TargetFramework>netstandard2.0</TargetFramework>
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I chose ns2.0 so that we should work in VS and in CLI. I've tested both and that does seem to be the case.

@baronfel
Copy link
Member Author

I logged dotnet/sdk#48352 to track the SDK providing a Task to do this in-box, so that eventually you could remove this one.

<_DashboardAndDcpRID>@(_AspireRidToolOutput)</_DashboardAndDcpRID>
</PropertyGroup>
<!-- Compute the RID for Dashboard and DCP packages -->
<PickBestRid RuntimeGraphPath="$(BundledRuntimeIdentifierGraphFile)" CurrentRid="$(NETCoreSdkRuntimeIdentifier)" SupportedRids="@(_DashboardAndDCPSupportedTargetingRIDs)">
Copy link
Member

@tmds tmds Apr 10, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could NETCoreSdkPortableRuntimeIdentifier be an alternative to doing a rid graph lookup?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe? I was mostly focused on translating the behaviors that existed before. I like than an explicit lookup will have a clearer error message than a missing implicitly-defined PackageReference.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Most use cases are expressed with portable rids.

Either the portable rid comes from the user, or it's the one from the SDK.

For the latter, rather than mapping NETCoreSdkRuntimeIdentifier via the rid graph, NETCoreSdkPortableRuntimeIdentifier can be used.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

On a linux-musl-x64 system, should this use linux-x64 assets? Or would those be binary incompatible?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can't use NETCoreSdkPortableRuntimeIdentifier as there are platforms where that won't be correct. This is how we originally had it, where we'd just use that to infer the package name but it didn't work for some distros where that is more specific and we don't cross-compile for it. As an example of the types of things that would show up if we did this are #5486 which this logic was specifically fixing.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@joperezr are you sure you were using NETCoreSdkPortableRuntimeIdentifier? (Note: this contains: Portable.)

I'm looking at #5695 and I don't see it.

@eerhardt
Copy link
Member

I believe @joperezr made this out of proc to not have to depend on the NuGet version used by the SDK. See #5695 (comment)

cc @dsplaisted

@baronfel
Copy link
Member Author

If that's the concern, couldn't we just use a lower version of the nuget package as a compile time only asset, letting the ambient one from whichever SDK was in use be the one that is actually executed at runtime?

@eerhardt
Copy link
Member

couldn't we just use a lower version of the nuget package as a compile time only asset, letting the ambient one from whichever SDK was in use be the one that is actually executed at runtime?

That would work if the NuGet libraries never make binary breaking changes, which they have in the past.

@joperezr
Copy link
Member

As @eerhardt, it was intentional to make this run out-of-proc in order to avoid having to fix dependency versions. We are okay with doing this as the plan is temporary, because the intent is to move all of this logic to the SDK instead, and therefore not have the dependency management concerns.

@dsplaisted
Copy link
Member

What dependencies does this PR actually add? I think when @joperezr was originally trying this out there were a bunch of dependencies that had to be added. But I don't really see any in this PR. Is that because they're coming in transitively from an MSBuild pakcage?

If we don't want to make this change in Aspire, then the ideal solution is to add a GetBestMatchingRid task to the SDK, and then when Aspire requires a version of the SDK that has that task it can switch to using it.

@danmoseley danmoseley added area-engineering-systems infrastructure helix infra engineering repo stuff and removed needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners labels Apr 16, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area-engineering-systems infrastructure helix infra engineering repo stuff
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants