ATS capability scanner drops overloaded methods with same MethodName instead of disambiguating
- Dominant language
- C#
- Stars
- 6.3k
- Forks
- 991
- Avg merge
- 2d 15h
- Merged PRs (30d)
- 196
Description
## Description
The `FilterMethodNameCollisions()` method in `AtsCapabilityScanner.cs` (lines 827-887) drops capabilities when multiple exports share the same `MethodName`, instead of disambiguating them with numeric suffixes.
## Root Cause
When multiple `[AspireExport]` attributes map to the same `MethodName` for the same target type, the scanner:
1. Groups by `(TargetType, MethodName)`
2. Sorts by `CapabilityId` alphabetically
3. **Keeps only the first**, removes the rest with a warning diagnostic
For example, `ParameterResourceBuilderExtensions` has:
```csharp
[AspireExport("addParameter", Description = "Adds a parameter resource")]
public static IResourceBuilder AddParameter(... string name, bool secret = false)
[AspireExport("addParameterWithValue", MethodName = "addParameter", Description = "Adds a parameter with a default value")]
public static IResourceBuilder AddParameter(... string name, string value, bool publishValueAsDefault = false, bool secret = false)
```
Both have `MethodName = "addParameter"`. The scanner keeps `addParameter` (alphabetically first) and silently drops `addParameterWithValue`.
## Expected Behavior
The scanner should disambiguate colliding methods with numeric suffixes (e.g., `addParameter` and `addParameter1`), matching the behavior of the TypeScript code generator's `RegisterOptionsInterface` which already uses this pattern for options interfaces (`AddParameterOptions`, `AddParameter1Options`).
**Note:** The playground's pre-generated SDK (generated from source via a different code path) correctly produces both `addParameter` and `addParameter1`. Only the runtime SDK (generated via the ATS server's capability enumeration) drops the overload.
## Impact
Users of TypeScript/polyglot AppHosts cannot use `AddParameter` with a default value. The parameter overload is silently unavailable with no user-facing error message. This also likely affects other methods with the same pattern (e.g., any `[AspireExport]` with a `MethodName` override that matches an existing export).
## Reproduction
1. Create a TypeScript AppHost with `addParameter` calls
2. Run `aspire run`
3. The generated `.modules/aspire.ts` will have `addParameter(name, {secret})` and `addParameterFromConfiguration` but no overload for providing a default value
## Environment
- Aspire CLI: `13.2.0-preview.1.26161.4`
- Code location: `src/Aspire.Hosting/Ats/AtsCapabilityScanner.cs`, `FilterMethodNameCollisions()` method
Contributor guide
Research direction
Start in src/Aspire.Hosting/Ats/AtsCapabilityScanner.cs, focusing on FilterMethodNameCollisions() at lines 827-887, then compare its collision handling with the TypeScript generator's RegisterOptionsInterface. Reproduce with a TypeScript AppHost and inspect the generated .modules/aspire.ts. Done means overloaded exports receive distinct numeric-suffixed method names instead of one being dropped.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- csharp, typescript
- Domain
- tooling
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Stale
- Clarity
- Clearly specified
- Newbie friendliness
- 58/100