콘텐츠로 이동

.NET Location 설정과 운영 공개 인터페이스

.NET 언어별 interface 목차 · Location runtime · Provider SPI · Host monitoring

1. 범위

이 문서는 application이 사용하는 Location 설정, readiness와 운영 query만 정의한다. Store provider가 구현하는 기술적 primitive는 provider SPI가 소유한다.

Authority key·version, owner token, descriptor record, capacity fence, reservation, aggregate와 relocation reference는 Framework 내부 정보이므로 이 application contract에 선언하지 않는다.

2. Location option

public sealed class ZLinkLocationOptions
{
 public TimeSpan OwnerLeaseRenewInterval { get; set; }
 = TimeSpan.FromSeconds(5);
 public TimeSpan OwnerLeaseTtl { get; set; }
 = TimeSpan.FromSeconds(15);
 public TimeSpan PollingInterval { get; set; }
 = TimeSpan.FromSeconds(1);
 public TimeSpan StoreFailureGrace { get; set; }
 = TimeSpan.FromSeconds(30);
 public TimeSpan OwnerLeaseFencingMargin { get; set; }
 = TimeSpan.FromSeconds(5);
 public TimeSpan OwnerLeaseRenewTimeout { get; set; }
 = TimeSpan.FromSeconds(3);
 public TimeSpan RouteCacheMaxAge { get; set; }
 = TimeSpan.FromSeconds(15);
 public TimeSpan MessageFollowDuration { get; set; }
 = TimeSpan.FromSeconds(30);
 public TimeSpan SessionRelocationSealTimeout { get; set; }
 = TimeSpan.FromSeconds(3);
 public long RelocationPayloadChunkLimit { get; set; }
 = 256 * 1024;
 public long RelocationInFlightPayloadBudget { get; set; }
 = 16 * 1024 * 1024;
 public long RelocationNodeInFlightPayloadBudget { get; set; }
 = 0;
 public TimeSpan RelocationCutoverWaitTimeout { get; set; }
 = TimeSpan.FromSeconds(1);
}

Root의 AddLocationStore(...), AddRelocationStore(...)ConfigureLocations() signature는 Topology configuration가 소유한다. Store는 역할별로 정확히 하나 등록한다. 같은 역할을 두 번 등록하면 socket bind 전에 ZLinkConfigurationException으로 startup을 실패한다.

Lease와 polling option은 0보다 커야 한다. 모든 Location host는 다음 관계를 만족해야 한다.

OwnerLeaseRenewInterval + OwnerLeaseRenewTimeout
 < OwnerLeaseTtl - OwnerLeaseFencingMargin

RouteCacheMaxAgeMessageFollowDuration은 0 이상이다. 둘 다 양수이면 cache age가 Message Follow duration보다 최소 5초 작아야 한다. 0은 해당 기능을 끈다.

SessionRelocationSealTimeout은 startup-only 양수 duration이고 기본값은 3초다. 0, 음수, 무한대와 TimeSpan을 유한 millisecond로 표현할 수 없는 값은 socket bind 전에 configuration error다.

RelocationPayloadChunkLimit은 relocation payload를 나눈 encoded chunk 하나의 최대 크기(byte)이고 기본값은 256 KiB다. Transport가 협상한 frame 한도를 넘게 설정하면 socket bind 전에 startup configuration error다. RelocationInFlightPayloadBudget은 peer 연결 하나에 대해 동시에 전송 중인 relocation chunk byte 합계의 상한이고 기본값은 16 MiB이며 0은 예산을 적용하지 않는다. RelocationNodeInFlightPayloadBudget은 같은 계상 규칙을 node 전체 합계에 적용하며 기본값 0은 미적용이다. RelocationCutoverWaitTimeout은 target이 cutover를 기다리는 시간이자 source가 재전송용 boundary batch 사본을 유지하는 시간이고 기본값은 1초다. 네 값 모두 startup-only이며 음수는 socket bind 전에 configuration error다.

3. Readiness와 운영 query

public sealed record ZLinkLocationRuntimeStatus(
 bool StoreHealthy,
 bool OwnerLeaseHealthy,
 DateTimeOffset? LastRefreshAt,
 DateTimeOffset? OwnerLeaseRenewedAt);

public enum ZLinkLocationTopologyState
{
 Discovered = 1,
 Connecting = 2,
 Ready = 3,
 Lost = 4,
 Error = 5,
 Stopped = 6
}

public sealed record ZLinkLocationTopologyFilter(
 string? MeshName = null,
 RoutingId? NodeRid = null,
 ZLinkLocationTopologyState? State = null);

public sealed record ZLinkLocationTopologyEntry(
 string MeshName,
 RoutingId NodeRid,
 string Endpoint,
 bool Draining,
 ZLinkLocationTopologyState State,
 DateTimeOffset UpdatedAt);

public sealed record ZLinkLocationServiceSummaryFilter(
 string? MeshName = null);

public sealed record ZLinkLocationServiceSummary(
 string MeshName,
 uint TotalCount,
 uint ReadyCount,
 uint ErrorCount,
 uint StoppedCount,
 DateTimeOffset LastUpdatedAt);

public enum ZLinkLocationObjectKind
{
 Actor = 0,
 UserSpot = 1,
 InstanceSpot = 2
}

public enum ZLinkLocationObjectState
{
 Creating = 0,
 Ready = 1,
 Unavailable = 2
}

public sealed record ZLinkLocationObjectEntry(
 string GlobalId,
 ulong ObjectGeneration,
 string MeshName,
 RoutingId NodeRid,
 ZLinkLocationObjectState State,
 string StableType);

public sealed record ZLinkLocationObjectFilter(
 ZLinkLocationObjectKind ObjectKind,
 string? StableType = null,
 string? MeshName = null);

public readonly record struct ZLinkPageRequest(
 int PageSize = 100,
 string? ContinuationToken = null);

public sealed record ZLinkLocationPage<T>(
 IReadOnlyList<T> Items,
 string? ContinuationToken);

public interface IZLinkLocationReadiness
{
 ValueTask<bool> IsPeerReadyAsync(
 string meshName,
 ZLinkLocationRole role,
 RoutingId? nodeRid = null,
 CancellationToken cancellationToken = default);
}

public interface IZLinkLocationRuntimeQuery
{
 ValueTask<ZLinkLocationRuntimeStatus> GetStatusAsync(
 CancellationToken cancellationToken = default);

 ValueTask<ZLinkLocationPage<ZLinkLocationTopologyEntry>> ListTopologyAsync(
 ZLinkLocationTopologyFilter filter,
 ZLinkPageRequest page = default,
 CancellationToken cancellationToken = default);

 ValueTask<ZLinkLocationPage<ZLinkLocationServiceSummary>>
 ListServiceSummariesAsync(
 ZLinkLocationServiceSummaryFilter filter,
 ZLinkPageRequest page = default,
 CancellationToken cancellationToken = default);

 ValueTask<ZLinkLocationObjectEntry?> FindActorLocationAsync(
 string actorId,
 CancellationToken cancellationToken = default);

 ValueTask<ZLinkLocationObjectEntry?> FindSpotLocationAsync(
 string spotId,
 CancellationToken cancellationToken = default);

 ValueTask<ZLinkLocationPage<ZLinkLocationObjectEntry>>
 ListObjectLocationsAsync(
 ZLinkLocationObjectFilter filter,
 ZLinkPageRequest page = default,
 CancellationToken cancellationToken = default);
}

public enum ZLinkLocationRole : ushort
{
 Invalid = 0,
 Spot = 2,
 Router = 3,
 Dealer = 4,
 Pub = 5,
 Sub = 6
}

운영 query는 사람이 이해할 수 있는 health·topology·service summary와 object location을 반환한다. Store key·version, owner lease generation, descriptor payload와 protocol envelope는 반환하지 않는다. NodeRid는 실제 transport routing identity이므로 public RoutingId로 유지한다.

Page size는 1..1000이고 continuation token은 해당 query가 발급한 opaque value다. Application은 token을 해석하거나 다른 query에 사용하지 않는다.

Actor ID와 Spot ID의 직접 lookup은 각각 현재 object location 하나를 조회한다. Missing이면 null, Creating이면 Creating, Ready이면 Ready, commit 뒤 current owner를 사용할 수 없으면 Unavailable entry를 반환한다. Spot 직접 lookup은 User Spot과 Instance Spot을 같은 Spot ID 조회 계약으로 다룬다. List query의 ObjectKind는 필수이며 StableTypeMeshName은 선택 filter다. Encoded page는 최대 4 MiB다. Store 조회 실패는 ZLinkFrameworkErrorKind.Unavailable이며 page 일부를 반환하지 않는다.

4. Host maintenance

Host maintenance는 IZLinkFrameworkRuntime.RelocateAsync(...)ShutdownAsync(...)가 소유한다. RelocateAsync(...)는 가능한 workload를 다른 owner로 이전하고 Relocated 상태에서 완료한다. PlannedMaintenance는 source와 같은 application version으로만 이전하며 target version을 받지 않는다. RollingUpdate는 source보다 큰 target version을 필수로 받고 그 version과 정확히 일치하는 node로만 이전한다. 두 mode 모두 version, maintenance wave, capability, capacity, placement weight 순서로 candidate를 제한하고 선택한다. 요청 조건을 만족하는 target이 없으면 deadline까지 기다린 뒤 Blocked/TargetUnavailable로 완료한다. Application은 결과를 확인한 뒤 ShutdownAsync(...)로 host를 종료할 수 있다. ShutdownAsync(...)Serving에서 바로 호출하면 새 relocation을 시작하지 않고 bounded cleanup 뒤 host를 종료한다. 정확한 signature와 결과는 Host monitoring이 소유한다.