I’m facing a permission/authorization issue while calling an AppService of one microservice from another in an ABP-based microservice architecture.
Scenario MS1Service contains ProductsAppService Permission required: MS1Service.Products
MS2Service calls ProductsAppService of MS1Service using client credentials flow
I created an Application Client with the following details:
ClientId: DAS Client Type: Confidential Grant Type: Client Credentials Allowed Scope: MS1Service Granted Permission: MS1Service.Products
**MS2Service **appsettings.json
"RemoteServices": {
"MS1Service": {
"BaseUrl": "https://localhost:44388/",
"UseCurrentAccessToken": "false"
}
},
"IdentityClients": {
"Default": {
"GrantType": "client_credentials",
"ClientId": "DAS",
"ClientSecret": "1q2w3e*",
"Authority": "https://localhost:44322",
"Scope": "MS1Service"
}
}
When **MS2Service **calls the AppService of MS1Service, I receive the following authorization error:
[INF] Authorization failed. These requirements were not met:
PermissionRequirement: MS1Service.Products
[WRN] ---------- RemoteServiceErrorInfo ----------
{
"code": "Volo.Authorization:010001",
"message": "Authorization failed! Given policy has not granted."
}
Is granting permission to the Application Client (DAS) sufficient for client-to-service calls? Is any additional configuration required in UseCurrentAccessToken or AbpAuthorizationOptions.
I’m trying to understand the correct and recommended way to authorize service-to-service AppService calls in ABP using client credentials.
Any pointers, examples, or documentation references would be greatly appreciated.
Thanks in advance!
4 Answer(s)
-
0
- Granting the permission to the client (DAS) is necessary, but it’s not sufficient by itself if MS1Service is not configured to evaluate permissions for client principals (client_credentials tokens) or if the access token doesn’t contain the client id in a way ABP can resolve and use for permission checks.
UseCurrentAccessToken=falseis correct for service-to-service calls (there is no “current user” token to forward). In that mode ABP should obtain a token using the configured IdentityClients:Default settings.
What to do (recommended ABP way)
Ensure MS2Service really sends a client_credentials access token
- The outgoing request to MS1Service must have:
Authorization: Bearer <token>. - That token must be issued for the API/scope of MS1Service (you used
Scope = "MS1Service"which is the right idea).
- The outgoing request to MS1Service must have:
Ensure MS1Service authentication is configured with the correct API name/audience
- In ABP microservice solutions, each microservice API is typically protected by its own API resource name (e.g.,
ProductService), and the host is configured with:AuthServer:AuthorityAuthServer:ApiName(the protected resource name)
- If
ApiName/audience doesn’t match what IdentityServer issues forMS1Service, MS1Service may authenticate the token but not map it as expected for permission checks.
- In ABP microservice solutions, each microservice API is typically protected by its own API resource name (e.g.,
Ensure MS1Service permission system supports “Client” permission grants
- ABP’s permission system can grant permissions not only to Users/Roles, but also to Clients (so a client_credentials token can pass
[Authorize(PermissionName)]checks). - Practically, that means:
- The client id must be discoverable from the token (so ABP can treat the current principal as a client).
- The permission must be granted to that client in the permission store/provider that MS1Service uses.
- ABP’s permission system can grant permissions not only to Users/Roles, but also to Clients (so a client_credentials token can pass
(If needed) Use centralized/remote permission checking as in ABP microservice patterns
- In microservice architectures, a common pattern is centralizing permission checks in the Identity service and having other services delegate permission checks there (so permissions granted to clients are evaluated consistently).
- An implementation example/pattern is shown in the “zero trust microservice architecture” community article (it demonstrates client permission checks via
ClientPermissionValueProviderand remote permission checking).
Notes on your specific questions
- Is granting permission to the Application Client sufficient?
- It is sufficient only if MS1Service is actually checking permissions for the authenticated principal as a client (not as a user/anonymous) and the token contains the proper client identity.
- Any additional configuration in
UseCurrentAccessTokenorAbpAuthorizationOptions?UseCurrentAccessToken=falseis the right setting for client_credentials.- The problem is typically not
AbpAuthorizationOptions, but that MS1Service is not resolving the principal as a “client” permission grantee (or the token/audience configuration doesn’t match).
Sources
- https://abp.io/docs/latest/samples/microservice-demo
- https://abp.io/docs/latest/framework/fundamentals/authorization#permission-system
- https://abp.io/community/articles/xpiz9nvh
This response was generated by AI. If it didn’t solve your problem, feel free to post a new answer — our support team will jump in to help you soon.
-
0
hi
You can consider using an integration appservice between microservices. It doesn't need the authentication/permission.
https://abp.io/docs/latest/framework/api-development/integration-services https://abp.io/docs/latest/solution-templates/microservice/http-api-calls
Thanks.
-
0
Hello, I am using ABP 8.1.5 version so I can't use integration service.
-
0
- In ABP 8.1.5, if you can’t use Integration Services, the recommended alternative for service-to-service authorization with client_credentials is to treat the calling microservice as an OAuth client and check permissions for the client (not a user).
- Your error (
PermissionRequirement: MS1Service.Products) indicates MS1Service is receiving the request, but the permission check is not being granted for the current principal (very commonly because the principal is a client and the permission system is not being evaluated against the Client permission provider in your setup).
Solution (ABP 8.1.5-compatible): Centralize permission checks (works with client_credentials)
Implement remote permission checking through your Identity/Auth server (or your central identity microservice) and have MS1Service/MS2Service delegate permission checks there. This is the “zero-trust” pattern and works before Integration Services.
What you do:
Expose an app service in the Identity/Auth microservice to check permissions for both Users and Clients.
- When
Type == "Client": check withClientPermissionValueProvider.ProviderName. - (Example implementation is in the source below.)
- When
In each microservice (MS1Service, MS2Service, etc.) replace
IPermissionCheckerwith a custom implementation that:- Extracts
client_idfrom the currentClaimsPrincipal - Calls the Identity/Auth microservice’s “PermissionChecker” endpoint
- Returns granted/denied to ABP’s authorization pipeline
- Extracts
This makes
[Authorize("MS1Service.Products")]succeed for client_credentials as long as the client has been granted that permission in the central permission store.You can base your implementation on the working sample code below (you can copy the approach as-is in ABP 8.1.5):
- In Identity/Auth service,
CheckPermissionAsync:
if (input.Type.Equals("Client", StringComparison.OrdinalIgnoreCase)) { return await _permissionStore.IsGrantedAsync( input.Name, ClientPermissionValueProvider.ProviderName, input.Id ); }- In other services, custom
IPermissionChecker:
var clientId = claimsPrincipal.FindClientId(); var userId = claimsPrincipal.FindUserId()?.ToString(); return await _permissionAppService.CheckPermissionAsync(new CheckPermissionInput { Name = name, Type = userId == null && clientId != null ? "Client" : "User", Id = userId ?? clientId });This approach avoids relying on per-service local permission evaluation nuances for client principals, and it aligns with ABP microservice patterns when you need service identities and explicit permissions.
About “disable auth/permission for internal calls”
If you cannot use Integration Services in 8.1.5, the other user’s suggestion (“an internal app service without auth/permission”) is technically possible, but it’s not equivalent to service-to-service authorization; it effectively bypasses authorization and is not a secure default for microservices.
Sources (validated)
- https://abp.io/community/articles/xpiz9nvh
- https://abp.io/docs/latest/framework/fundamentals/authorization#permission-system
- https://abp.io/docs/latest/solution-templates/microservice/http-api-calls
This response was generated by AI. If it didn’t solve your problem, feel free to post a new answer — our support team will jump in to help you soon.