Aracılığıyla paylaş


.NET'te gRPC kesişimcileri

Not

Bu, bu makalenin en son sürümü değildir. Geçerli sürüm için bu makalenin .NET 9 sürümüne bakın.

Uyarı

ASP.NET Core'un bu sürümü artık desteklenmiyor. Daha fazla bilgi için bkz . .NET ve .NET Core Destek İlkesi. Geçerli sürüm için bu makalenin .NET 8 sürümüne bakın.

Önemli

Bu bilgiler, ticari olarak piyasaya sürülmeden önce önemli ölçüde değiştirilebilen bir yayın öncesi ürünle ilgilidir. Burada verilen bilgilerle ilgili olarak Microsoft açık veya zımni hiçbir garanti vermez.

Geçerli sürüm için bu makalenin .NET 9 sürümüne bakın.

Tarafından Ernest Nguyen

Kesiciler, uygulamaların gelen veya giden gRPC çağrılarıyla etkileşim kurmasını sağlayan bir gRPC kavramıdır. İstek işleme işlem hattını zenginleştirmek için bir yol sunar.

Kesiciler bir kanal veya hizmet için yapılandırılır ve her gRPC çağrısı için otomatik olarak yürütülür. Kesme makineleri kullanıcının uygulama mantığına göre saydam olduğundan günlük kaydı, izleme, kimlik doğrulaması ve doğrulama gibi yaygın durumlar için mükemmel bir çözüm sunar.

Interceptor tür

Kesiciler, türünden Interceptor devralan bir sınıf oluşturularak hem gRPC sunucuları hem de istemcileri için uygulanabilir:

public class ExampleInterceptor : Interceptor
{
}

Varsayılan olarak, Interceptor temel sınıf hiçbir şey yapmaz. Bir kesme noktası uygulamasında uygun temel sınıf yöntemlerini geçersiz kılarak bir kesiciye davranış ekleyin.

İstemci kesişimcileri

gRPC istemci kesme makineleri giden RPC çağrılarını durdurur. Gönderilen istek, gelen yanıt ve istemci tarafı çağrısı bağlamı için erişim sağlar.

Interceptor istemcisini geçersiz kılma yöntemleri:

  • BlockingUnaryCall: Birli RPC'nin engelleyici çağrısını durdurur.
  • AsyncUnaryCall: Birli RPC'nin zaman uyumsuz çağrısını durdurur.
  • AsyncClientStreamingCall: İstemci akışı RPC'sinin zaman uyumsuz çağrısını durdurur.
  • AsyncServerStreamingCall: Sunucu akışı RPC'sinin zaman uyumsuz çağrısını durdurur.
  • AsyncDuplexStreamingCall: Çift yönlü akış RPC'sinin zaman uyumsuz çağrısını durdurur.

Uyarı

Hem hem de BlockingUnaryCall AsyncUnaryCall birli RPC'lere başvuruda bulunmakla birlikte, bunlar birbirinin yerine kullanılamaz. Engelleme çağrısı tarafından AsyncUnaryCallkesilmez ve zaman uyumsuz çağırma bir BlockingUnaryCalltarafından kesilmez.

İstemci gRPC kesme noktası oluşturma

Aşağıdaki kod, birli çağrının zaman uyumsuz çağrısını kesmenin temel bir örneğini sunar:

public class ClientLoggingInterceptor : Interceptor
{
    private readonly ILogger _logger;

    public ClientLoggingInterceptor(ILoggerFactory loggerFactory)
    {
        _logger = loggerFactory.CreateLogger<ClientLoggingInterceptor>();
    }

    public override AsyncUnaryCall<TResponse> AsyncUnaryCall<TRequest, TResponse>(
        TRequest request,
        ClientInterceptorContext<TRequest, TResponse> context,
        AsyncUnaryCallContinuation<TRequest, TResponse> continuation)
    {
        _logger.LogInformation("Starting call. Type/Method: {Type} / {Method}",
            context.Method.Type, context.Method.Name);
        return continuation(request, context);
    }
}

Geçersiz kılma AsyncUnaryCall:

  • Zaman uyumsuz bir tekli çağrıyı durdurur.
  • Aramayla ilgili ayrıntıları günlüğe kaydeder.
  • yöntemine continuation geçirilen parametresini çağırır. Bu, son kesme noktası ise zincirdeki sonraki kesme noktasını veya temel alınan çağrı çağırıcısını çağırır.

Her tür hizmet yöntemi için üzerindeki Interceptor yöntemlerin farklı imzaları vardır. Ancak, ve parametrelerinin ardındaki continuation context kavram aynı kalır:

  • continuation zincirdeki sonraki kesme noktasını veya temel alınan çağrı çağırıcısını çağıran bir temsilcidir (zincirde kesme noktası kalmadıysa). Sıfır veya birden çok kez çağırmak bir hata değildir. Kesme noktalarının temsilciden döndürülen bir çağrı gösterimi (AsyncUnaryCall birli RPC olması durumunda) döndürmesi continuation gerekmez. Temsilci çağrısını atlayıp kendi çağrı gösterimi örneğinizi döndürmek, kesmecilerin zincirini bozar ve ilişkili yanıtı hemen döndürür.
  • context istemci tarafı çağrısıyla ilişkili kapsamlı değerler taşır. Güvenlik sorumluları, kimlik bilgileri veya izleme verileri gibi meta verileri geçirmek için kullanın context . Ayrıca, context son tarihler ve iptaller hakkında bilgi taşır. Daha fazla bilgi için bkz . Son tarihler ve iptal ile güvenilir gRPC hizmetleri.

İstemci kesme aracında yanıt bekleniyor

Bir kesme noktası, veya AsyncClientStreamingCall<TRequest, TResponse>.ResponseAsync değerini güncelleştirerek tekli ve istemci akış çağrılarında AsyncUnaryCall<TResponse>.ResponseAsync yanıtı bekleyebilirsiniz.

public class ErrorHandlerInterceptor : Interceptor
{
    public override AsyncUnaryCall<TResponse> AsyncUnaryCall<TRequest, TResponse>(
        TRequest request,
        ClientInterceptorContext<TRequest, TResponse> context,
        AsyncUnaryCallContinuation<TRequest, TResponse> continuation)
    {
        var call = continuation(request, context);

        return new AsyncUnaryCall<TResponse>(
            HandleResponse(call.ResponseAsync),
            call.ResponseHeadersAsync,
            call.GetStatus,
            call.GetTrailers,
            call.Dispose);
    }

    private async Task<TResponse> HandleResponse<TResponse>(Task<TResponse> inner)
    {
        try
        {
            return await inner;
        }
        catch (Exception ex)
        {
            throw new InvalidOperationException("Custom error", ex);
        }
    }
}

Yukarıdaki kod:

  • öğesini geçersiz kılan AsyncUnaryCallyeni bir kesme noktası oluşturur.
  • Geçersiz kılma AsyncUnaryCall:
    • Kesme noktası zincirindeki continuation sonraki öğeyi çağırmak için parametresini çağırır.
    • Devamlılık sonucuna göre yeni AsyncUnaryCall<TResponse> bir örnek oluşturur.
    • yöntemini kullanarak HandleResponse görevi sarmalarResponseAsync.
    • ile HandleResponseyanıt bekler. Yanıtın beklenmesi, istemci yanıtı aldıktan sonra mantığın eklenmesini sağlar. Try-catch bloğunda yanıt beklenerek çağrılardan gelen hatalar günlüğe kaydedilebilir.

İstemci kesme noktası oluşturma hakkında daha fazla bilgi için GitHub deposundaki ClientLoggerInterceptor.cs grpc/grpc-dotnetörneği inceleyin.

İstemci kesme noktası oluşturucularını yapılandırma

gRPC istemci kesme cihazları bir kanalda yapılandırılır.

Aşağıdaki kod:

  • kullanarak GrpcChannel.ForAddressbir kanal oluşturur.
  • Intercept Kanalı kesme noktasını kullanacak şekilde yapılandırmak için uzantı yöntemini kullanır. Bu yöntemin bir CallInvokerdöndürdüğünü unutmayın. Kesin türe sahip gRPC istemcileri, bir kanal gibi bir çağırıcıdan oluşturulabilir.
  • Çağırıcıdan bir istemci oluşturur. İstemci tarafından yapılan gRPC çağrıları, kesme noktasını otomatik olarak yürütür.
using var channel = GrpcChannel.ForAddress("https://localhost:5001");
var invoker = channel.Intercept(new ClientLoggerInterceptor());

var client = new Greeter.GreeterClient(invoker);

Uzantı Intercept yöntemi, bir kanal için birden çok kesme noktası yapılandırmak üzere zincirlenebilir. Alternatif olarak, birden çok kesme noktası kabul eden bir Intercept aşırı yükleme vardır. Aşağıdaki örnekte gösterildiği gibi tek bir gRPC çağrısı için herhangi bir sayıda kesme noktası yürütülebilir:

var invoker = channel
    .Intercept(new ClientTokenInterceptor())
    .Intercept(new ClientMonitoringInterceptor())
    .Intercept(new ClientLoggerInterceptor());

Kesme makineleri zincirlenmiş Intercept uzantı yöntemlerinin ters sırasına göre çağrılır. Önceki kodda, kesme çizgileri aşağıdaki sırayla çağrılır:

  1. ClientLoggerInterceptor
  2. ClientMonitoringInterceptor
  3. ClientTokenInterceptor

gRPC istemci fabrikası ile kesme noktası yapılandırma hakkında bilgi için bkz . .NET'te gRPC istemci fabrikası tümleştirmesi.

Sunucu kesme çizgileri

gRPC sunucusu kesme makineleri gelen RPC isteklerini durdurur. Gelen isteğe, giden yanıta ve sunucu tarafı çağrısının bağlamı için erişim sağlar.

Interceptor sunucu için geçersiz kılınacak yöntemler:

  • UnaryServerHandler: Tek bir RPC'nin yolunu keser.
  • ClientStreamingServerHandler: İstemci akışı RPC'sini durdurur.
  • ServerStreamingServerHandler: Sunucu akışı RPC'sini durdurur.
  • DuplexStreamingServerHandler: Çift yönlü akış RPC'sini durdurur.

Sunucu gRPC kesme noktası oluşturma

Aşağıdaki kod, gelen bir bire bir RPC'yi kesen bir örnek sunar:

public class ServerLoggerInterceptor : Interceptor
{
    private readonly ILogger _logger;

    public ServerLoggerInterceptor(ILogger<ServerLoggerInterceptor> logger)
    {
        _logger = logger;
    }

    public override async Task<TResponse> UnaryServerHandler<TRequest, TResponse>(
        TRequest request,
        ServerCallContext context,
        UnaryServerMethod<TRequest, TResponse> continuation)
    {
        _logger.LogInformation("Starting receiving call. Type/Method: {Type} / {Method}",
            MethodType.Unary, context.Method);
        try
        {
            return await continuation(request, context);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, $"Error thrown by {context.Method}.");
            throw;
        }
    }
}

Geçersiz kılma UnaryServerHandler:

  • Gelen bir çağrıyı durdurur.
  • Aramayla ilgili ayrıntıları günlüğe kaydeder.
  • yöntemine continuation geçirilen parametresini çağırır. Bu, son kesme noktası ise zincirdeki sonraki kesme noktasını veya hizmet işleyicisini çağırır.
  • Özel durumları günlüğe kaydeder. Devamlılık beklendikten sonra hizmet yöntemi yürütüldükten sonra mantığın eklenmesine olanak tanır. Try-catch bloğunda devamı beklenerek, yöntemlerden gelen hatalar günlüğe kaydedilebilir.

hem istemci hem de sunucu kesme noktası yöntemlerinin imzası benzerdir:

  • continuation , zincirdeki sonraki kesme noktasını veya hizmet işleyicisini çağıran (zincirde kesme noktası kalmadıysa) gelen RPC için bir temsilci anlamına gelir. İstemci kesme araçlarına benzer şekilde, istediğiniz zaman çağırabilirsiniz ve doğrudan devamlılık temsilcisinden yanıt döndürmenize gerek yoktur. Devamı beklenerek bir hizmet işleyicisi yürütüldükten sonra giden mantık eklenebilir.
  • context istek meta verileri, son tarihler ve iptal veya RPC sonucu gibi sunucu tarafı çağrısıyla ilişkili meta verileri taşır.

Sunucu kesme noktası oluşturma hakkında daha fazla bilgi için GitHub deposundaki ServerLoggerInterceptor.cs grpc/grpc-dotnetörneği inceleyin.

Sunucu kesme yollarını yapılandırma

gRPC sunucu kesme makineleri başlangıçta yapılandırılır. Aşağıdaki kod:

  • ile AddGrpcuygulamaya gRPC ekler.
  • Hizmet seçeneğinin ServerLoggerInterceptor Interceptors koleksiyonuna ekleyerek tüm hizmetler için yapılandırılır.
public void ConfigureServices(IServiceCollection services)
{
    services.AddGrpc(options =>
    {
        options.Interceptors.Add<ServerLoggerInterceptor>();
    });
}

Kesme noktası, hizmet türü kullanılarak AddServiceOptions ve belirtilerek belirli bir hizmet için de yapılandırılabilir.

public void ConfigureServices(IServiceCollection services)
{
    services
        .AddGrpc()
        .AddServiceOptions<GreeterService>(options =>
        {
            options.Interceptors.Add<ServerLoggerInterceptor>();
        });
}

Kesiciler, öğesine eklenme sırasına InterceptorCollectiongöre çalıştırılır. Hem genel hem de tek hizmet kesme noktası yapılandırılırsa, genel olarak yapılandırılmış kesme çizgileri tek bir hizmet için yapılandırılanlardan önce çalıştırılır.

Varsayılan olarak, gRPC sunucu kesicilerinin istek başına yaşam süresi vardır. Bu davranışı geçersiz kılma, kesme noktası türünü bağımlılık ekleme ile kaydederek mümkündür. Aşağıdaki örnek, 'yi ServerLoggerInterceptor tek bir yaşam süresiyle kaydeder:

public void ConfigureServices(IServiceCollection services)
{
    services.AddGrpc(options =>
    {
        options.Interceptors.Add<ServerLoggerInterceptor>();
    });

    services.AddSingleton<ServerLoggerInterceptor>();
}

gRPC Kesme Makineleri ile Ara Yazılım karşılaştırması

ASP.NET Core ara yazılımı , C çekirdek tabanlı gRPC uygulamalarındaki kesme makinelerine kıyasla benzer işlevler sunar. ASP.NET Core ara yazılımı ve kesme makineleri kavramsal olarak benzerdir. Her ikisi:

  • gRPC isteğini işleyen bir işlem hattı oluşturmak için kullanılır.
  • İşlem hattındaki bir sonraki bileşenden önce veya sonra çalışmanın gerçekleştirilmesine izin verin.
  • erişimi HttpContextsağlayın:
    • Ara yazılımda HttpContext parametresidir.
    • Kesme yollarında, HttpContext uzantısı yöntemiyle ServerCallContext.GetHttpContext parametresi kullanılarak ServerCallContext öğesine erişilebilir. Bu özellik, ASP.NET Core'da çalışan kesişenlere özeldir.

gRPC Interceptor ile ASP.NET Core Ara Yazılımı arasındaki farklar:

  • Interceptors:
    • kullanarak gRPC soyutlama katmanı üzerinde ServerCallContextçalışma.
    • Erişim sağlayın:
      • Çağrıya gönderilen seri durumdan çıkarılmış ileti.
      • Çağrı seri hale getirilmeden önce döndürülen ileti.
    • gRPC hizmetlerinden oluşan özel durumları yakalayabilir ve işleyebilir.
  • Ara yazılım:
    • Tüm HTTP istekleri için çalışır.
    • gRPC kesişimcileri öncesinde çalışır.
    • Temel alınan HTTP/2 iletileri üzerinde çalışır.
    • Yalnızca istek ve yanıt akışlarından baytlara erişebilir.

Ek kaynaklar