Skip to content

Add Foundry project role assignments#16736

Open
sebastienros wants to merge 6 commits intomainfrom
sebros/foundry-role-assignments
Open

Add Foundry project role assignments#16736
sebastienros wants to merge 6 commits intomainfrom
sebros/foundry-role-assignments

Conversation

@sebastienros
Copy link
Copy Markdown
Contributor

@sebastienros sebastienros commented May 4, 2026

Description

Foundry project identities need access to the parent Foundry/Cognitive Services account in order to use model deployments. This adds a default Cognitive Services User assignment on the parent account for each Foundry project identity, plus APIs to replace or clear those roles from .NET and polyglot app hosts.

The ATS export scanner now preserves concrete target-specific role-assignment exports when generic role-assignment exports share the same generated method name, so Foundry polyglot apps can keep using the normal withRoleAssignments convention without collisions.

Validation included targeted Foundry role-assignment tests, ATS scanner tests, Foundry polyglot app host validation across TypeScript/Go/Java/Python, and an Azure deployment repro that completed successfully with the project identity role assignment present on the parent Foundry account.

image

Fixes: #15971

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?

Fixes #16397

Add default parent Foundry account role assignments for project identities so deployed agents can use model deployments.

Support overriding or clearing the project role assignments from .NET and polyglot app hosts, and preserve concrete ATS role-assignment exports when generic exports share the same method name.

Add Bicep snapshot tests, ATS scanner regression coverage, and Foundry polyglot coverage.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot AI review requested due to automatic review settings May 4, 2026 17:36
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 4, 2026

🚀 Dogfood this PR with:

⚠️ WARNING: Do not do this without first carefully reviewing the code of this PR to satisfy yourself it is safe.

curl -fsSL https://raw.githubusercontent.com/microsoft/aspire/main/eng/scripts/get-aspire-cli-pr.sh | bash -s -- 16736

Or

  • Run remotely in PowerShell:
iex "& { $(irm https://raw.githubusercontent.com/microsoft/aspire/main/eng/scripts/get-aspire-cli-pr.ps1) } 16736"

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Adds Foundry-project support for assigning roles on the parent Foundry/Cognitive Services account, and updates ATS collision handling so polyglot withRoleAssignments exports can coexist with the generic role-assignment export.

Changes:

  • Added project-level Foundry role-assignment APIs and default parent-account CognitiveServicesUser provisioning.
  • Updated ATS method-collision filtering to prefer concrete target bindings over generic ones.
  • Added/updated Foundry provisioning snapshots, scanner tests, and polyglot apphost samples to exercise the new role-assignment flow.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
tests/PolyglotAppHosts/Aspire.Hosting.Foundry/TypeScript/apphost.ts Exercises project role assignments from the TypeScript polyglot host.
tests/PolyglotAppHosts/Aspire.Hosting.Foundry/Python/apphost.py Exercises project role assignments from the Python polyglot host.
tests/PolyglotAppHosts/Aspire.Hosting.Foundry/Java/AppHost.java Exercises project role assignments from the Java polyglot host.
tests/PolyglotAppHosts/Aspire.Hosting.Foundry/Go/apphost.go Exercises project role assignments from the Go polyglot host and removes old placeholder enum usage.
tests/Aspire.Hosting.RemoteHost.Tests/AtsCapabilityScannerTests.cs Adds coverage for ATS method-name collision handling between generic and concrete exports.
tests/Aspire.Hosting.Azure.Tests/Snapshots/FoundryExtensionsTests.AddProject_WithRoleAssignments_ReplacesDefaultRoleAssignmentsOnParentFoundry.verified.bicep Verifies replacing default parent Foundry role assignments in generated Bicep.
tests/Aspire.Hosting.Azure.Tests/Snapshots/FoundryExtensionsTests.AddProject_WithEmptyRoleAssignments_RemovesDefaultRoleAssignmentsOnParentFoundry.verified.bicep Verifies clearing parent Foundry role assignments in generated Bicep.
tests/Aspire.Hosting.Azure.Tests/Snapshots/FoundryExtensionsTests.AddProject_GeneratesDefaultRoleAssignmentOnParentFoundry.verified.bicep Verifies the new default parent Foundry role assignment in generated Bicep.
tests/Aspire.Hosting.Azure.Tests/FoundryExtensionsTests.cs Adds snapshot-based tests for default, replacement, and empty parent-role-assignment behavior.
src/Aspire.Hosting.RemoteHost/AtsCapabilityScanner.cs Changes collision filtering to remove only conflicting target bindings and prefer directly targeted capabilities.
src/Aspire.Hosting.Foundry/Project/ProjectResource.cs Stores the default parent-account role assignments for Foundry projects.
src/Aspire.Hosting.Foundry/Project/ProjectBuilderExtension.cs Adds project-specific role-assignment APIs and emits parent-account role assignments during provisioning.
src/Aspire.Hosting.Foundry/FoundryRole.cs Introduces shared conversion helpers from ATS-safe FoundryRole values to Cognitive Services built-in roles.
src/Aspire.Hosting.Foundry/FoundryExtensions.cs Reuses the shared Foundry-role conversion helper for generic Foundry role assignments.

Comment thread src/Aspire.Hosting.Foundry/Project/ProjectBuilderExtension.cs
Comment thread src/Aspire.Hosting.Foundry/Project/ProjectBuilderExtension.cs
sebastienros and others added 5 commits May 4, 2026 10:49
Add existing Foundry parent coverage for project role assignments and complete XML docs for the project-specific role assignment API.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Ensure hosted agents get their Foundry project role assignment through the underlying compute target, which is the resource that receives the app identity used by the hosted agent runtime.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@tommasodotNET
Copy link
Copy Markdown
Contributor

tommasodotNET commented May 4, 2026

currently, the foundry agent's playground has the code for the workaround provided by @eerhardt. we should remove it with this pr.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 4, 2026

🎬 CLI E2E Test Recordings — 73 recordings uploaded (commit 7bf58c9)

View all recordings
Status Test Recording
AddPackageInteractiveWhileAppHostRunningDetached ▶️ View Recording
AddPackageWhileAppHostRunningDetached ▶️ View Recording
AgentCommands_AllHelpOutputs_AreCorrect ▶️ View Recording
AgentInitCommand_DefaultSelection_InstallsSkillOnly ▶️ View Recording
AgentInitCommand_MigratesDeprecatedConfig ▶️ View Recording
AspireAddPackageVersionToDirectoryPackagesProps ▶️ View Recording
AspireUpdateRemovesAppHostPackageVersionFromDirectoryPackagesProps ▶️ View Recording
Banner_DisplayedOnFirstRun ▶️ View Recording
Banner_DisplayedWithExplicitFlag ▶️ View Recording
Banner_NotDisplayedWithNoLogoFlag ▶️ View Recording
CertificatesClean_RemovesCertificates ▶️ View Recording
CertificatesTrust_WithNoCert_CreatesAndTrustsCertificate ▶️ View Recording
CertificatesTrust_WithUntrustedCert_TrustsCertificate ▶️ View Recording
ConfigSetGet_CreatesNestedJsonFormat ▶️ View Recording
CreateAndRunAspireStarterProject ▶️ View Recording
CreateAndRunAspireStarterProjectWithBundle ▶️ View Recording
CreateAndRunEmptyAppHostProject ▶️ View Recording
CreateAndRunJavaEmptyAppHostProject ▶️ View Recording
CreateAndRunJsReactProject ▶️ View Recording
CreateAndRunPythonReactProject ▶️ View Recording
CreateAndRunTypeScriptEmptyAppHostProject ▶️ View Recording
CreateAndRunTypeScriptStarterProject ▶️ View Recording
CreateJavaAppHostWithViteApp ▶️ View Recording
CreateTypeScriptAppHostWithViteApp_UsesConfiguredToolchain ▶️ View Recording
DashboardRunWithOtelTracesReturnsNoTraces ▶️ View Recording
DeployK8sBasicApiService ▶️ View Recording
DeployK8sWithGarnet ▶️ View Recording
DeployK8sWithMongoDB ▶️ View Recording
DeployK8sWithPostgres ▶️ View Recording
DeployK8sWithRabbitMQ ▶️ View Recording
DeployK8sWithRedis ▶️ View Recording
DeployK8sWithSqlServer ▶️ View Recording
DeployK8sWithValkey ▶️ View Recording
DeployTypeScriptAppToKubernetes ▶️ View Recording
DescribeCommandResolvesReplicaNames ▶️ View Recording
DescribeCommandShowsRunningResources ▶️ View Recording
DoListStepsShowsPipelineSteps ▶️ View Recording
DocsCommand_RendersInteractiveMarkdownFromLocalSource ▶️ View Recording
DoctorCommand_DetectsDeprecatedAgentConfig ▶️ View Recording
DoctorCommand_TypeScriptAppHostReportsMissingConfiguredToolchain ▶️ View Recording
DoctorCommand_WithSslCertDir_ShowsTrusted ▶️ View Recording
DoctorCommand_WithoutSslCertDir_ShowsPartiallyTrusted ▶️ View Recording
GlobalMigration_HandlesCommentsAndTrailingCommas ▶️ View Recording
GlobalMigration_HandlesMalformedLegacyJson ▶️ View Recording
GlobalMigration_PreservesAllValueTypes ▶️ View Recording
GlobalMigration_SkipsWhenNewConfigExists ▶️ View Recording
GlobalSettings_MigratedFromLegacyFormat ▶️ View Recording
InitTypeScriptAppHost_AugmentsExistingViteRepoAtRoot ▶️ View Recording
InteractiveCSharpInitCreatesExpectedFiles ▶️ View Recording
InvalidAppHostPathWithComments_IsHealedOnRun ▶️ View Recording
LatestCliCanStartStableChannelAppHost ▶️ View Recording
LatestCliCanStartStableChannelTypeScriptAppHost ▶️ View Recording
LegacySettingsMigration_AdjustsRelativeAppHostPath ▶️ View Recording
LogsCommandShowsResourceLogs ▶️ View Recording
OtelLogsReturnsStructuredLogsFromStarterAppCore ▶️ View Recording
PsCommandListsRunningAppHost ▶️ View Recording
PsFormatJsonOutputsOnlyJsonToStdout ▶️ View Recording
PublishWithConfigureEnvFileUpdatesEnvOutput ▶️ View Recording
PublishWithDockerComposeServiceCallbackSucceeds ▶️ View Recording
PublishWithoutOutputPathUsesAppHostDirectoryDefault ▶️ View Recording
RestoreGeneratesSdkFiles ▶️ View Recording
RestoreGeneratesSdkFiles_WithConfiguredToolchain ▶️ View Recording
RestoreRefreshesGeneratedSdkAfterAddingIntegration ▶️ View Recording
RestoreSupportsConfigOnlyHelperPackageAndCrossPackageTypes ▶️ View Recording
RunFromParentDirectory_UsesExistingConfigNearAppHost ▶️ View Recording
SecretCrudOnDotNetAppHost ▶️ View Recording
SecretCrudOnTypeScriptAppHost ▶️ View Recording
StagingChannel_ConfigureAndVerifySettings_ThenSwitchChannels ▶️ View Recording
StartAndWaitForTypeScriptSqlServerAppHostWithNativeAssets ▶️ View Recording
StopAllAppHostsFromAppHostDirectory ▶️ View Recording
StopNonInteractiveSingleAppHost ▶️ View Recording
StopWithNoRunningAppHostExitsSuccessfully ▶️ View Recording
UnAwaitedChainsCompileWithAutoResolvePromises ▶️ View Recording

📹 Recordings uploaded automatically from CI run #25348227472

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

Labels

None yet

Projects

None yet

3 participants