Događaj
Power BI DataViz Svetsko prvenstvo
14. feb 16 - 31. mar 16
Sa 4 šanse za ulazak, možete osvojiti konferencijski paket i stići do LIVE Grand Finale u Las Vegasu
Saznajte višeOvaj pregledač više nije podržan.
Nadogradite na Microsoft Edge biste iskoristili najnovije funkcije, bezbednosne ispravke i tehničku podršku.
Napomena
This isn't the latest version of this article. For the current release, see the .NET 9 version of this article.
Upozorenje
This version of ASP.NET Core is no longer supported. For more information, see the .NET and .NET Core Support Policy. For the current release, see the .NET 9 version of this article.
Važno
This information relates to a pre-release product that may be substantially modified before it's commercially released. Microsoft makes no warranties, express or implied, with respect to the information provided here.
For the current release, see the .NET 9 version of this article.
View or download sample code (how to download)
gRPC can be used with ASP.NET Core authentication to associate a user with each call.
The following is an example of Program.cs
which uses gRPC and ASP.NET Core authentication:
app.UseRouting();
app.UseAuthentication();
app.UseAuthorization();
app.MapGrpcService<GreeterService>();
Napomena
The order in which you register the ASP.NET Core authentication middleware matters. Always call UseAuthentication
and UseAuthorization
after UseRouting
and before UseEndpoints
.
The authentication mechanism your app uses during a call needs to be configured. Authentication configuration is added in Program.cs
and will be different depending upon the authentication mechanism your app uses.
Once authentication has been setup, the user can be accessed in a gRPC service methods via the ServerCallContext
.
public override Task<BuyTicketsResponse> BuyTickets(
BuyTicketsRequest request, ServerCallContext context)
{
var user = context.GetHttpContext().User;
// ... access data from ClaimsPrincipal ...
}
The client can provide an access token for authentication. The server validates the token and uses it to identify the user.
On the server, bearer token authentication is configured using the JWT Bearer middleware.
In the .NET gRPC client, the token can be sent with calls by using the Metadata
collection. Entries in the Metadata
collection are sent with a gRPC call as HTTP headers:
public bool DoAuthenticatedCall(
Ticketer.TicketerClient client, string token)
{
var headers = new Metadata();
headers.Add("Authorization", $"Bearer {token}");
var request = new BuyTicketsRequest { Count = 1 };
var response = await client.BuyTicketsAsync(request, headers);
return response.Success;
}
Configuring ChannelCredentials
on a channel is an alternative way to send the token to the service with gRPC calls. A ChannelCredentials
can include CallCredentials
, which provide a way to automatically set Metadata
.
Benefits of using CallCredentials
:
CallCredentials.FromInterceptor
callback is asynchronous. Call credentials can fetch a credential token from an external system if required. Asynchronous methods inside the callback should use the CancellationToken
on AuthInterceptorContext
.Napomena
CallCredentials
are only applied if the channel is secured with TLS. Sending authentication headers over an insecure connection has security implications and shouldn't be done in production environments. An app can configure a channel to ignore this behavior and always use CallCredentials
by setting UnsafeUseInsecureChannelCallCredentials
on a channel.
The credential in the following example configures the channel to send the token with every gRPC call:
private static GrpcChannel CreateAuthenticatedChannel(ITokenProvder tokenProvider)
{
var credentials = CallCredentials.FromInterceptor(async (context, metadata) =>
{
var token = await tokenProvider.GetTokenAsync(context.CancellationToken);
metadata.Add("Authorization", $"Bearer {token}");
});
var channel = GrpcChannel.ForAddress(address, new GrpcChannelOptions
{
Credentials = ChannelCredentials.Create(new SslCredentials(), credentials)
});
return channel;
}
gRPC client factory can create clients that send a bearer token using AddCallCredentials
. This method is available in Grpc.Net.ClientFactory version 2.46.0 or later.
The delegate passed to AddCallCredentials
is executed for each gRPC call:
builder.Services
.AddGrpcClient<Greeter.GreeterClient>(o =>
{
o.Address = new Uri("https://localhost:5001");
})
.AddCallCredentials((context, metadata) =>
{
if (!string.IsNullOrEmpty(_token))
{
metadata.Add("Authorization", $"Bearer {_token}");
}
return Task.CompletedTask;
});
Dependency injection (DI) can be combined with AddCallCredentials
. An overload passes IServiceProvider
to the delegate, which can be used to get a service constructed from DI using scoped and transient services.
Consider an app that has:
ITokenProvider
for getting a bearer token. ITokenProvider
is registered in DI with a scoped lifetime.ITokenProvider
to get a bearer token.public interface ITokenProvider
{
Task<string> GetTokenAsync(CancellationToken cancellationToken);
}
public class AppTokenProvider : ITokenProvider
{
private string _token;
public async Task<string> GetTokenAsync(CancellationToken cancellationToken)
{
if (_token == null)
{
// App code to resolve the token here.
}
return _token;
}
}
builder.Services.AddScoped<ITokenProvider, AppTokenProvider>();
builder.Services
.AddGrpcClient<Greeter.GreeterClient>(o =>
{
o.Address = new Uri("https://localhost:5001");
})
.AddCallCredentials(async (context, metadata, serviceProvider) =>
{
var provider = serviceProvider.GetRequiredService<ITokenProvider>();
var token = await provider.GetTokenAsync(context.CancellationToken);
metadata.Add("Authorization", $"Bearer {token}");
}));
The preceding code:
ITokenProvider
and AppTokenProvider
. These types handle resolving the authentication token for gRPC calls.AppTokenProvider
type with DI in a scoped lifetime. AppTokenProvider
caches the token so that only the first call in the scope is required to calculate it.GreeterClient
type with client factory.AddCallCredentials
for this client. The delegate is executed each time a call is made and adds the token returned by ITokenProvider
to the metadata.A client could alternatively provide a client certificate for authentication. Certificate authentication happens at the TLS level, long before it ever gets to ASP.NET Core. When the request enters ASP.NET Core, the client certificate authentication package allows you to resolve the certificate to a ClaimsPrincipal
.
Napomena
Configure the server to accept client certificates. For information on accepting client certificates in Kestrel, IIS, and Azure, see Configure certificate authentication in ASP.NET Core.
In the .NET gRPC client, the client certificate is added to HttpClientHandler
that is then used to create the gRPC client:
public Ticketer.TicketerClient CreateClientWithCert(
string baseAddress,
X509Certificate2 certificate)
{
// Add client cert to the handler
var handler = new HttpClientHandler();
handler.ClientCertificates.Add(certificate);
// Create the gRPC channel
var channel = GrpcChannel.ForAddress(baseAddress, new GrpcChannelOptions
{
HttpHandler = handler
});
return new Ticketer.TicketerClient(channel);
}
Many ASP.NET Core supported authentication mechanisms work with gRPC:
For more information on configuring authentication on the server, see ASP.NET Core authentication.
Configuring the gRPC client to use authentication will depend on the authentication mechanism you are using. The previous bearer token and client certificate examples show a couple of ways the gRPC client can be configured to send authentication metadata with gRPC calls:
HttpClient
internally. Authentication can be configured on HttpClientHandler, or by adding custom HttpMessageHandler instances to the HttpClient
.CallOptions
argument. Custom headers can be sent using the option's headers collection.Napomena
Windows Authentication (NTLM/Kerberos/Negotiate) can't be used with gRPC. gRPC requires HTTP/2, and HTTP/2 doesn't support Windows Authentication.
By default, all methods in a service can be called by unauthenticated users. To require authentication, apply the [Authorize]
attribute to the service:
[Authorize]
public class TicketerService : Ticketer.TicketerBase
{
}
You can use the constructor arguments and properties of the [Authorize]
attribute to restrict access to only users matching specific authorization policies. For example, if you have a custom authorization policy called MyAuthorizationPolicy
, ensure that only users matching that policy can access the service using the following code:
[Authorize("MyAuthorizationPolicy")]
public class TicketerService : Ticketer.TicketerBase
{
}
Individual service methods can have the [Authorize]
attribute applied as well. If the current user doesn't match the policies applied to both the method and the class, an error is returned to the caller:
[Authorize]
public class TicketerService : Ticketer.TicketerBase
{
public override Task<AvailableTicketsResponse> GetAvailableTickets(
Empty request, ServerCallContext context)
{
// ... buy tickets for the current user ...
}
[Authorize("Administrators")]
public override Task<BuyTicketsResponse> RefundTickets(
BuyTicketsRequest request, ServerCallContext context)
{
// ... refund tickets (something only Administrators can do) ..
}
}
View or download sample code (how to download)
gRPC can be used with ASP.NET Core authentication to associate a user with each call.
The following is an example of Startup.Configure
which uses gRPC and ASP.NET Core authentication:
public void Configure(IApplicationBuilder app)
{
app.UseRouting();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapGrpcService<GreeterService>();
});
}
Napomena
The order in which you register the ASP.NET Core authentication middleware matters. Always call UseAuthentication
and UseAuthorization
after UseRouting
and before UseEndpoints
.
The authentication mechanism your app uses during a call needs to be configured. Authentication configuration is added in Startup.ConfigureServices
and will be different depending upon the authentication mechanism your app uses.
Once authentication has been setup, the user can be accessed in a gRPC service methods via the ServerCallContext
.
public override Task<BuyTicketsResponse> BuyTickets(
BuyTicketsRequest request, ServerCallContext context)
{
var user = context.GetHttpContext().User;
// ... access data from ClaimsPrincipal ...
}
The client can provide an access token for authentication. The server validates the token and uses it to identify the user.
On the server, bearer token authentication is configured using the JWT Bearer middleware.
In the .NET gRPC client, the token can be sent with calls by using the Metadata
collection. Entries in the Metadata
collection are sent with a gRPC call as HTTP headers:
public bool DoAuthenticatedCall(
Ticketer.TicketerClient client, string token)
{
var headers = new Metadata();
headers.Add("Authorization", $"Bearer {token}");
var request = new BuyTicketsRequest { Count = 1 };
var response = await client.BuyTicketsAsync(request, headers);
return response.Success;
}
Configuring ChannelCredentials
on a channel is an alternative way to send the token to the service with gRPC calls. A ChannelCredentials
can include CallCredentials
, which provide a way to automatically set Metadata
.
Benefits of using CallCredentials
:
CallCredentials.FromInterceptor
callback is asynchronous. Call credentials can fetch a credential token from an external system if required. Asynchronous methods inside the callback should use the CancellationToken
on AuthInterceptorContext
.Napomena
CallCredentials
are only applied if the channel is secured with TLS. Sending authentication headers over an insecure connection has security implications and shouldn't be done in production environments. An app can configure a channel to ignore this behavior and always use CallCredentials
by setting UnsafeUseInsecureChannelCallCredentials
on a channel.
The credential in the following example configures the channel to send the token with every gRPC call:
private static GrpcChannel CreateAuthenticatedChannel(ITokenProvder tokenProvider)
{
var credentials = CallCredentials.FromInterceptor(async (context, metadata) =>
{
var token = await tokenProvider.GetTokenAsync(context.CancellationToken);
metadata.Add("Authorization", $"Bearer {token}");
});
var channel = GrpcChannel.ForAddress(address, new GrpcChannelOptions
{
Credentials = ChannelCredentials.Create(new SslCredentials(), credentials)
});
return channel;
}
gRPC client factory can create clients that send a bearer token using AddCallCredentials
. This method is available in Grpc.Net.ClientFactory version 2.46.0 or later.
The delegate passed to AddCallCredentials
is executed for each gRPC call:
services
.AddGrpcClient<Greeter.GreeterClient>(o =>
{
o.Address = new Uri("https://localhost:5001");
})
.AddCallCredentials((context, metadata) =>
{
if (!string.IsNullOrEmpty(_token))
{
metadata.Add("Authorization", $"Bearer {_token}");
}
return Task.CompletedTask;
});
Dependency injection (DI) can be combined with AddCallCredentials
. An overload passes IServiceProvider
to the delegate, which can be used to get a service constructed from DI using scoped and transient services.
Consider an app that has:
ITokenProvider
for getting a bearer token. ITokenProvider
is registered in DI with a scoped lifetime.ITokenProvider
to get a bearer token.public interface ITokenProvider
{
Task<string> GetTokenAsync(CancellationToken cancellationToken);
}
public class AppTokenProvider : ITokenProvider
{
private string _token;
public async Task<string> GetTokenAsync(CancellationToken cancellationToken)
{
if (_token == null)
{
// App code to resolve the token here.
}
return _token;
}
}
services.AddScoped<ITokenProvider, AppTokenProvider>();
services
.AddGrpcClient<Greeter.GreeterClient>(o =>
{
o.Address = new Uri("https://localhost:5001");
})
.AddCallCredentials(async (context, metadata, serviceProvider) =>
{
var provider = serviceProvider.GetRequiredService<ITokenProvider>();
var token = await provider.GetTokenAsync(context.CancellationToken);
metadata.Add("Authorization", $"Bearer {token}");
}));
The preceding code:
ITokenProvider
and AppTokenProvider
. These types handle resolving the authentication token for gRPC calls.AppTokenProvider
type with DI in a scoped lifetime. AppTokenProvider
caches the token so that only the first call in the scope is required to calculate it.GreeterClient
type with client factory.AddCallCredentials
for this client. The delegate is executed each time a call is made and adds the token returned by ITokenProvider
to the metadata.A client could alternatively provide a client certificate for authentication. Certificate authentication happens at the TLS level, long before it ever gets to ASP.NET Core. When the request enters ASP.NET Core, the client certificate authentication package allows you to resolve the certificate to a ClaimsPrincipal
.
Napomena
Configure the server to accept client certificates. For information on accepting client certificates in Kestrel, IIS, and Azure, see Configure certificate authentication in ASP.NET Core.
In the .NET gRPC client, the client certificate is added to HttpClientHandler
that is then used to create the gRPC client:
public Ticketer.TicketerClient CreateClientWithCert(
string baseAddress,
X509Certificate2 certificate)
{
// Add client cert to the handler
var handler = new HttpClientHandler();
handler.ClientCertificates.Add(certificate);
// Create the gRPC channel
var channel = GrpcChannel.ForAddress(baseAddress, new GrpcChannelOptions
{
HttpHandler = handler
});
return new Ticketer.TicketerClient(channel);
}
Many ASP.NET Core supported authentication mechanisms work with gRPC:
For more information on configuring authentication on the server, see ASP.NET Core authentication.
Configuring the gRPC client to use authentication will depend on the authentication mechanism you are using. The previous bearer token and client certificate examples show a couple of ways the gRPC client can be configured to send authentication metadata with gRPC calls:
HttpClient
internally. Authentication can be configured on HttpClientHandler, or by adding custom HttpMessageHandler instances to the HttpClient
.CallOptions
argument. Custom headers can be sent using the option's headers collection.Napomena
Windows Authentication (NTLM/Kerberos/Negotiate) can't be used with gRPC. gRPC requires HTTP/2, and HTTP/2 doesn't support Windows Authentication.
By default, all methods in a service can be called by unauthenticated users. To require authentication, apply the [Authorize]
attribute to the service:
[Authorize]
public class TicketerService : Ticketer.TicketerBase
{
}
You can use the constructor arguments and properties of the [Authorize]
attribute to restrict access to only users matching specific authorization policies. For example, if you have a custom authorization policy called MyAuthorizationPolicy
, ensure that only users matching that policy can access the service using the following code:
[Authorize("MyAuthorizationPolicy")]
public class TicketerService : Ticketer.TicketerBase
{
}
Individual service methods can have the [Authorize]
attribute applied as well. If the current user doesn't match the policies applied to both the method and the class, an error is returned to the caller:
[Authorize]
public class TicketerService : Ticketer.TicketerBase
{
public override Task<AvailableTicketsResponse> GetAvailableTickets(
Empty request, ServerCallContext context)
{
// ... buy tickets for the current user ...
}
[Authorize("Administrators")]
public override Task<BuyTicketsResponse> RefundTickets(
BuyTicketsRequest request, ServerCallContext context)
{
// ... refund tickets (something only Administrators can do) ..
}
}
Authorizaton can also be controlled using standard ASP.NET Core authorization extension methods, such as AllowAnonymous
and RequireAuthorization
.
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddGrpc();
var app = builder.Build();
app.MapGrpcService<TicketerService>().RequireAuthorization("Administrators");
app.Run();
Povratne informacije za ASP.NET Core
ASP.NET Core je projekat otvorenog koda. Izaberite vezu da biste pružili povratne informacije:
Događaj
Power BI DataViz Svetsko prvenstvo
14. feb 16 - 31. mar 16
Sa 4 šanse za ulazak, možete osvojiti konferencijski paket i stići do LIVE Grand Finale u Las Vegasu
Saznajte višeObuka
Putanja učenja
AZ-204: Implement user authentication and authorization - Training
AZ-204: Implement user authentication and authorization
Certifikacija
Microsoft Certified: Identity and Access Administrator Associate - Certifications
Demonstrate the features of Microsoft Entra ID to modernize identity solutions, implement hybrid solutions, and implement identity governance.
Dokumentacija
Learn how to use gRPC interceptors on .NET.
Learn how to configure gRPC for .NET apps.
Security considerations in gRPC for ASP.NET Core
Learn about security considerations for gRPC for ASP.NET Core.