Skip to content

fix: exclude shutting down silos from placement#10219

Open
ReubenBond wants to merge 13 commits into
dotnet:mainfrom
ReubenBond:reubenbond/active-silo-placement
Open

fix: exclude shutting down silos from placement#10219
ReubenBond wants to merge 13 commits into
dotnet:mainfrom
ReubenBond:reubenbond/active-silo-placement

Conversation

@ReubenBond

@ReubenBond ReubenBond commented Jun 11, 2026

Copy link
Copy Markdown
Member

Fixes placement eligibility so a local silo that has transitioned to ShuttingDown is removed from compatible silo candidates even if membership still reports it active. GetCompatibleSilos now returns ImmutableArray and uses the cached active-silo list from ISiloStatusOracle.GetActiveSilos(), with active-silo filtering applied after placement filters so callers only receive active silos.

@ReubenBond ReubenBond force-pushed the reubenbond/active-silo-placement branch from b20e126 to f7a27ef Compare June 12, 2026 17:45
ReubenBond and others added 2 commits June 13, 2026 09:48
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Canonicalize cluster manifests and nested manifest properties so repeated metadata is shared across silo entries and AllGrainManifests contains unique manifests.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@ReubenBond ReubenBond force-pushed the reubenbond/active-silo-placement branch from da9e72d to cdef309 Compare June 13, 2026 17:37
ReubenBond and others added 11 commits June 13, 2026 10:50
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>
Prune cluster manifests when membership versions advance so GrainVersionManifest and version selector caches only expose active silos. Simplify placement compatibility to trust those active-only caches while retaining the active-silo guard after extensible filters.

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>
Prune cluster manifests when membership versions advance so GrainVersionManifest and version selector caches only expose active silos. Simplify placement compatibility to trust those active-only caches while retaining the active-silo guard after extensible filters.

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>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@ReubenBond ReubenBond force-pushed the reubenbond/active-silo-placement branch from cdef309 to 9bb75b5 Compare June 13, 2026 17:54
@ReubenBond ReubenBond requested a review from Copilot June 13, 2026 17:55

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull request overview

This PR updates Orleans placement and cluster-manifest handling so that placement candidates/manifests better reflect current cluster availability (notably around shutdown/termination), while also tightening APIs and reducing manifest duplication.

Changes:

  • Update IPlacementContext.GetCompatibleSilos to return ImmutableArray<SiloAddress> and adjust placement directors/tests to match.
  • Update PlacementService to use ISiloStatusOracle.GetActiveSilos() for active-silo filtering and filter versioned compatible-silo results by active membership.
  • Improve cluster manifest behavior (sync pruning of non-active silos, manifest publishing behavior, manifest deduplication) and add new targeted tests.
Show a summary per file
File Description
test/Orleans.Core.Tests/Runtime/PlacementServiceTests.cs Adds coverage for excluding local silo during shutdown; updates test scaffolding for GetActiveSilos()/ImmutableArray.
test/Orleans.Core.Tests/Runtime/LocalPlacementDirectorTests.cs Updates mocks to return ImmutableArray from GetCompatibleSilos.
test/Orleans.Core.Tests/Runtime/ActivationCountPlacementDirectorTests.cs Updates mocks to return ImmutableArray from GetCompatibleSilos.
test/Orleans.Core.Tests/Manifest/ClusterManifestProviderTests.cs New tests validating manifest pruning/publishing behavior and placement’s active-only results.
test/Orleans.Core.Tests/Manifest/ClusterManifestDeduplicationTests.cs New tests validating structural equality/deduplication of manifest objects.
test/Grains/TestGrains/VersionAwarePlacementDirector.cs Adjusts to treat compatible silos as IReadOnlyList for ImmutableArray compatibility.
src/Orleans.Runtime/Versions/CachedVersionSelectorManager.cs Switches cached suitable-silos list to ImmutableArray.
src/Orleans.Runtime/Placement/SiloRoleBasedPlacementDirector.cs Uses ImmutableArray for compatible-silo list and IsEmpty checks.
src/Orleans.Runtime/Placement/PlacementService.cs Changes compatible-silo API to ImmutableArray, uses GetActiveSilos(), and filters versioned results by actives.
src/Orleans.Runtime/Placement/ActivationCountPlacementDirector.cs Updates selector helper signature to accept ImmutableArray.
src/Orleans.Runtime/Manifest/ClusterManifestProvider.cs Refactors manifest synchronization/publishing and membership-update processing; now depends on IClusterMembershipService.
src/Orleans.Core/Placement/IPlacementDirector.cs Updates placement hint helper signature to accept ImmutableArray.
src/Orleans.Core/Placement/IPlacementContext.cs Updates placement context API to return ImmutableArray.
src/Orleans.Core/Manifest/GrainBindings.cs Small refactor to centralize manifest processing loop into a local function.
src/Orleans.Core/Core/GrainInterfaceTypeToGrainTypeResolver.cs Refactor to centralize per-manifest cache building logic into a helper method.
src/Orleans.Core.Abstractions/Manifest/GrainProperties.cs Adds structural equality/hash support for deduplication.
src/Orleans.Core.Abstractions/Manifest/GrainManifest.cs Adds structural equality/hash support for deduplication.
src/Orleans.Core.Abstractions/Manifest/GrainInterfaceProperties.cs Adds structural equality/hash support for deduplication.
src/Orleans.Core.Abstractions/Manifest/ClusterManifest.cs Adds AllGrainManifests ctor and implements manifest/property deduplication.
src/api/Orleans.Core/Orleans.Core.cs Public API update for GetCompatibleSilos and GetPlacementHint signatures.
src/api/Orleans.Core.Abstractions/Orleans.Core.Abstractions.cs Public API update for new ClusterManifest ctor and new equality members.

Copilot's findings

  • Files reviewed: 21/21 changed files
  • Comments generated: 6

Comment on lines +192 to 196
if (member.SiloAddress.Equals(_localSiloAddress))
{
// If the member is not yet active, it may not be ready to process requests.
// Local membership changes are applied synchronously by EnsureCurrentManifestVersion.
continue;
}
compatibleSilos = filteredSilos.ToArray();
}

compatibleSilos = compatibleSilos.Intersect(_siloStatusOracle.GetActiveSilos()).ToImmutableArray();
Comment on lines +249 to +252
var activeSilos = _siloStatusOracle.GetActiveSilos();
return silos.ToDictionary(
static entry => entry.Key,
entry => entry.Value.Intersect(activeSilos).ToArray());
Comment on lines +114 to +119
configureOptions: options => options.AssumeHomogenousSilosForTesting = true,
configureSiloStatusOracle: (siloStatusOracle, localSilo) =>
{
siloStatusOracle.CurrentStatus.Returns(SiloStatus.ShuttingDown);
siloStatusOracle.GetActiveSilos().Returns(ImmutableArray.Create(remoteSilo));
});
@@ -31,7 +32,7 @@ Task<SiloAddress> OnAddActivation(
/// <param name="requestContextData">The request context data.</param>
/// <param name="compatibleSilos">The compatible silos.</param>
/// <returns>The placement hint, if present and valid, or <see landword="null"/> otherwise.</returns>
Comment on lines +124 to +145
var builder = ImmutableDictionary.CreateBuilder<TKey, TValue>(properties.KeyComparer, properties.ValueComparer);
modified = false;
foreach (var entry in properties)
{
if (canonicalProperties.TryGetValue(entry.Value, out var canonicalProperty))
{
if (!ReferenceEquals(canonicalProperty, entry.Value))
{
modified = true;
}

builder[entry.Key] = canonicalProperty;
}
else
{
canonicalProperties.Add(entry.Value, entry.Value);
builder[entry.Key] = entry.Value;
}
}

return modified ? builder.ToImmutable() : properties;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants