I have an external endpoint which is going to hit the Azure API gateway and that would route it to the backend API which is protected by IdentityServer4 authorization.
I am getting the access token if I hit it through the Postman client with the interactive UI from IdentityServer.
Is there a way I can get the access token required from the Azure API Management to validate against the IdentityServer4 and append it to the header in the request to the backend API?
Yes it is possible to achieve it through custom policy. You can ask your external API-Client/Consumer to paas in credentials in heaser, and then you write a policy inside inbound to can read those user credentials and do a API request (similar to your postman) and get the access token. You can then append the same token and let your request gets forwarded to backend API.
As per your problem statement, this should work. In case not, you might have to explain your scenario with more description/steps.
Here are some of the reference materials for you, I hope it helps.
https://learn.microsoft.com/en-us/azure/api-management/api-management-advanced-policies#SendRequest
https://learn.microsoft.com/en-us/azure/api-management/api-management-sample-send-request
Postman has a luxury of a human user seeing the UI and authorizing API access and IdentityServer4 to issue a token for Postman. There is no such luxury when call is being processed by APIM server, as you could send request for token to IdentityServer4, but who would be presented UI to authorize the action?
The only way is to provision some sort of secret to APIM (header, query, certificate) that would be recognized by IdentityServer4 to allow it issuing tokens for APIM. If such secred is available you could use send-request policy to make a call to IdentityServer4 and obtain required token.
Or make sure that every request to APIM has a token already.
Related
I am very new to Keycloak server and want to use it to protect my front-end app and the backend rest API which are also open over the internet. So far what I understand and did is to create 2 clients on Keycloack, 1 is for frontend which used Client Protocol(openid-connect) with access type(Public) and then in client side i am using adopter to redirect the users to Keycloak login page and authenticate and get token. Now for the backend(rest-apis), I have created a separate client which again use Client Protocol(openid-connect) but with access type(confidential) and in Authentication Flow: both Browser Flow and Direct Grant Flow are direct grant and after that i get client-id and client-secret to call Keycloak rest api.
Now i want that when user are authenticated from frontend and get the token and send in header request to my rest API, here i call some Keycloak rest api to verify this token by providing client_id and client_secret.
I am using following rest api from Keycloak to verify the token which i generated at frontend:
http://localhost:8120/auth/realms/evva_realm/protocol/openid-connect/token/introspect
but result is getting like that:
{
"active": false
}
It my be i am using some wrong api OR the whole archetecture to verify and protect my backend apis are not correct. Can someone help me to understand where is the problem?
#user565 I found this medium post that works for me. I believe that you can benefit from it as well.
It basically creates two clients, one for the backend, and another for the frontend. The catch is that they share the same roles by leveraging the client scope, roles, and composite roles features.
Hope it helps: https://medium.com/devops-dudes/secure-front-end-react-js-and-back-end-node-js-express-rest-api-with-keycloak-daf159f0a94e
I'm auditing an API whose client is a mobile application using the OAuth2 workflow but I'm missing something. I have a first endpoint of the /token.oauth2 API which allows me with credentials to get an access token needed to call other endpoints of the API. So far OK but on top of that I have an "x-api-key" which is transmitted along with the access token and if both the API key and the access token are not present, the server sends me a HTTP 401 response.
I can't find any mention of a connection flow using both an "x-api-key" and an access token in the OAuth2 standard. When do you think?
I'm setting up a service which needs to authorize against an existing Gitlab as OAuth Provider.
The service is a SPA which gets served by a webpack dev server in dev mode and a nginx server in production mode.
I'm also setting up an external API which should handle the Database and make request to the given gitlab instance (for example pull repos).
My SPA is authorizing against the Gitlab OAuth with the implicit_grant flow and is getting an access token. Currently I pass the access_token after the redirect to my API backend and there I get the Gitlab userid and username via a request to the gitlab instance with the access_token. With these I generate a jwt and send it to the client (SPA) and save it there so I can authorize my API with this JWT.
How would I handle the initial access_token in my backend (cause I need the token to make gitlab calls)?
Currently I'm thinking about writing it to the user in the database and get the user everytime he makes a request (normal passport flow), so I also have the token. But what if the token gets invalid or expires?
Should I use an interceptor in the backend and if the token is invalid (gitlab would give me a 401) redirect the 401 to my client, let him get a new token and pass it back to the backend, generate a new JWT, send this again to the client and let him do the same request as original reuested(via interceptor, too)?
Or should I just redirect the 401 to my client, let him get a new token, let him post this token to for example /renewToken and save the token to the database and use the old JWT?
Hope someone can help me unserstand this flow.
The Credential Management API should be what your looking for on the client. That will retrieve the id and access tokens to that you can compare access tokens with your server/ap and then validate the id token.
Haven't seen a Git example but there are Google and Facebook examples.
You could let the user send the initial access token and your backend API will just act based on the initial access token. Seems to me that it is not necessary to produce another JWT token in this case.
we plan to introduce an API management solution and we're currently setting up a proof of concept with WSO2 AM. We want to use the WSO2 API gateway to check whether a certain consumer application is allowed to use an API and to throttle the request rate.
I work on the identity workflow and I wonder how a consuming application can pass a JWT token to the backend service with WSO2-AM in between.
First, this is our current scenario:
Without API gateway
The consuming application gets a JWT token for its carbon user from an identity provider. The JWT contains some claims about the user, e.g. the roles he/she belongs to.
The app calls the service an passes the JWT token in the Authorization HTTP header like: Authorization: Bearer
The service validates the issuer and signature of the JWT and retrieves the claims from it.
So, this is pretty straight forward. Now we put an API gateway in between the application and the service:
With API gateway
The consuming application gets a JWT token for its carbon user from an identity provider.
The consuming application uses OAuth2 to get an access token for the following API calls. We can use the client_credentials grant type and simply pass the the client id and client secret. I haven't yet tried it, but we could possibly use the JWT grant type (see https://docs.wso2.com/display/ISCONNECTORS/Configuring+JWT+Grant+Type) and use the JWT for passing user information to the API gateway.
The API gateway validates the JWT against the public key of the identity provider when using the JWT grant type.
An access token is returned to the app.
The app sends an API request to the gateway and passes the access token in the Authorization HTTP header.
The gateway validates the access token.
The gateway forwards the API request to the service.
And there is my problem: How can the JWT from 1/2. be passed to the service?
There is a documentation for "Passing Enduser Attributes to the Backend Using JWT" (see https://docs.wso2.com/display/AM210/Passing+Enduser+Attributes+to+the+Backend+Using+JWT), but this would introduce a new JWT, issued and signed by WSO2-AM, and I'm not sure, whether this JWT contains all information from the JWT used to create the access token (or even the original JWT).
Another way I could think of is using a custom HTTP header for passing the JWT through the gateway to the service. I cannot use the Authorization header (as we do without the API gateway), because WSO2-AM expects the access token in that header.
Since I'm not happy with either solutions, I want to ask the experts: How would you solve this?
Thanks,
Torsten
The only possibility I can think of is to send the JWT token in a custom Header for the backend service.
We are current building a collection of back-end ASP.NET Core microservices. These services will not be accessed directly from the front-end application, but rather accessed through an ASP.NET Core API gateway. We are using IdentityServer4 for the OpenID Connect server. I have been able to setup the UseJwtBearerAuthentication middleware to have API gateway validate the JWT bearer token (access_token) against IdentityServer4. I would like to be able to have the API gateway inject the id_token, based on the access_token, into the requests made to the back-end services that may need to know the end-user.
Is there a way to configure the JWT middleware to retrieve the id_token when validation the access_token or do I need to manually call the OpenID Connect server in the API gateway?
You don't use id_tokens at APIs - they are for clients.
If you want to have access to certain identity claims, either include them in the access token (by configuring the ScopeClaims on the resource scope), or use the access token to contact the userinfo endoint which in turn will return the identity claims.
The JWT middleware performs standalone verification, it does not contact the identity server to verify or retrieve anything. You'll have to make an additional call.