Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
d4afb15
Add proxyless endpoint port allocator
danegsta Jun 4, 2026
1f97041
Fix proxyless port allocation tests
danegsta Jun 4, 2026
43b1a24
Validate persistent Azure Storage emulator ports
danegsta Jun 4, 2026
b3adb7b
Address port allocator review feedback
danegsta Jun 5, 2026
8ff7ca8
Document proxyless port allocation strategy
danegsta Jun 5, 2026
b2799f3
Move proxyless endpoint helpers out of PrepareServices
danegsta Jun 5, 2026
599a711
Update src/Aspire.Hosting/Dcp/DcpExecutor.cs
danegsta Jun 5, 2026
d4a71b9
Update src/Aspire.Hosting/Dcp/DcpExecutor.cs
danegsta Jun 5, 2026
e743d08
Restore lifecycle event timing
danegsta Jun 5, 2026
281ac77
Clean up fixed public port helper
danegsta Jun 5, 2026
8bbf8f1
Simplify proxyless endpoint port setup
danegsta Jun 6, 2026
99eee27
Tighten proxyless port allocation cleanup
danegsta Jun 6, 2026
5cdb010
Address proxyless allocator review feedback
danegsta Jun 8, 2026
49a1b59
Clarify proxyless allocator traversal
danegsta Jun 9, 2026
bb5320e
Fix health check timing regression test
danegsta Jun 9, 2026
34e6a59
Make health check timing test deterministic
danegsta Jun 9, 2026
78ef056
Revert health check test changes
danegsta Jun 9, 2026
3d23a51
Drop fragile health check URI timing assertion
danegsta Jun 9, 2026
4d2e451
Merge remote-tracking branch 'origin/main' into danegsta/port-allocator
danegsta Jun 10, 2026
31246b6
Cover proxyless port persistence-failure warning; treat any probe bin…
danegsta Jun 10, 2026
f1a338f
Extract shared PortRange validation helper to remove magic port bounds
danegsta Jun 10, 2026
0f52dcb
Use Resources:<resource>:<endpoint>:port user secrets key schema from…
danegsta Jun 10, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 1 addition & 56 deletions src/Aspire.Hosting/ApplicationModel/EndpointReference.cs
Original file line number Diff line number Diff line change
Expand Up @@ -221,61 +221,6 @@ public ReferenceExpression GetTlsValue(ReferenceExpression enabledValue, Referen
GetAllocatedEndpoint()
?? throw new InvalidOperationException($"The endpoint `{EndpointName}` is not allocated for the resource `{Resource.Name}`.");

internal async Task<AllocatedEndpoint> GetAllocatedEndpointAsync(NetworkIdentifier networkId, ValueProviderContext context, CancellationToken cancellationToken = default)
{
var endpointAnnotation = EndpointAnnotation;
if (endpointAnnotation.AllAllocatedEndpoints.TryGetAllocatedEndpoint(networkId, out var endpoint))
{
return endpoint;
}

var allocationAnnotations = Resource.Annotations.OfType<OnDemandEndpointAllocationAnnotation>().ToArray();
if (allocationAnnotations.Length > 0 && await ShouldAllocateEndpointOnDemandAsync(context, cancellationToken).ConfigureAwait(false))
{
foreach (var allocationAnnotation in allocationAnnotations)
{
endpoint = allocationAnnotation.TryAllocate(endpointAnnotation, networkId);
if (endpoint is not null)
{
return endpoint;
}
}
}

// Waiting here preserves late allocation for cases that don't need the on-demand fallback,
// such as proxyless container endpoints whose actual port is reported by DCP after startup.
return await endpointAnnotation.AllAllocatedEndpoints.GetAllocatedEndpointAsync(networkId, cancellationToken).ConfigureAwait(false);
}

private async Task<bool> ShouldAllocateEndpointOnDemandAsync(ValueProviderContext context, CancellationToken cancellationToken)
{
if (context.Caller is not { } caller)
{
return true;
}

if (Resource == caller)
{
return true;
}

if (context.ExecutionContext is not { } executionContext)
{
return true;
}

var dependencies = await Resource.GetResourceDependenciesAsync(
executionContext,
new ResourceDependencyDiscoveryOptions
{
DiscoveryMode = ResourceDependencyDiscoveryMode.Recursive,
CacheAnnotationCallbackResults = true
},
cancellationToken).ConfigureAwait(false);

return dependencies.Contains(caller);
}

private EndpointAnnotation? GetEndpointAnnotation()
{
if (_endpointAnnotation is not null)
Expand Down Expand Up @@ -426,7 +371,7 @@ public class EndpointReferenceExpression(EndpointReference endpointReference, En

async ValueTask<string?> ResolveValueWithAllocatedAddress()
{
var allocatedEndpoint = await Endpoint.GetAllocatedEndpointAsync(networkContext, context, cancellationToken).ConfigureAwait(false);
var allocatedEndpoint = await Endpoint.EndpointAnnotation.AllAllocatedEndpoints.GetAllocatedEndpointAsync(networkContext, cancellationToken).ConfigureAwait(false);

return Property switch
{
Expand Down

This file was deleted.

7 changes: 1 addition & 6 deletions src/Aspire.Hosting/Dcp/ContainerCreator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -199,7 +199,7 @@ public IEnumerable<RenderedModelResource<Container>> PrepareObjects()
}

var containerAppResource = new RenderedModelResource<Container>(container, ctr);
DcpModelUtilities.AddServicesProducedInfo(containerAppResource, _appResources.Get(), _logger);
DcpModelUtilities.AddServicesProducedInfo(containerAppResource, _appResources.Get());
_appResources.Add(containerAppResource);
result.Add(containerAppResource);
}
Expand Down Expand Up @@ -316,11 +316,6 @@ private async Task BuildAndCreateContainerAsync(RenderedModelResource<Container>
spec.RunArgs = runArgs;

var (configuration, pemCertificates, createFiles) = await BuildContainerConfiguration(cr, logger, cToken).ConfigureAwait(false);
// Configuration callbacks are the last pre-creation point where on-demand allocation can run.
cr.ModelResource.Annotations
.OfType<OnDemandEndpointAllocationAnnotation>()
.SingleOrDefault()
?.StopAllocating();

if (configuration.Exception is not null)
{
Expand Down
Loading
Loading