How to validate the user in jwt - spring-boot

I have a rest service which stores comments from the users in the database, my architecture is an angular fronted which connects to a load balancer server (zuul) which connects to an auth server to generate the jwt.
With the jwt the frontend generate the requests to the same zuul server with the jwt, this zuul server validate the jwt and if valid will connect to another backend service to store the comment.
The backend service where the comment is stored doesn't have any security validation all endpoints are accessible as the route of this microservices are not going to be exposed? Is there any risk on this?
As there is no jwt reaching the "comment backend service" how can I get the user that actually made the request? Should I implement some kind of filter in the zuul server to get the logged user from the jwt token and include the information in the request that is being sent to the "comment backend service"? If this is possible, any ideas on how to implement it?
Thanks
Regards

By default, Zuul considers the Authorization header as a sensitive header and it will not pass it downstream. So the first thing you need to do is to update Zuul configurations. Read the documentation here.
After that, in each of your downstream service, you need to add the capability to read the JWT token from the Authorization header and extract relevant information such as username, etc.

Related

Server-2-server authorizaton in microservice architecture

It's clear for me about users authorization in microservice architecture (API Gateway for handling auth, SSO, authorization microservice and so on).
Now i'm thinking about authorization request between microservices.
And there is one question - which options i have in case when i have not got a user?
For example - analytics service, which requests data from billing and builds complex reports. There is no user, but do i need authorize request from analytics service to billing?
I know that there can be endless tokens, but i think its not good idea.
What another options for authorization request between services?
In OAuth2 specification there is such thing called machine-to-machine token. Which is different than password credentials flow which is refering to your user authorization.
To create a machine-to-machine token you should implement a flow called client credentials flow. In this flow basically all services have a specific client id and client secret and with those you are making a call to your central oauth-server to get a token. As it is also required to configure client details in the central service you will have the authorization in between client calls in terms of which client could call which others. There is also configurations for the time to live for each token.
If you already have the OAuth2 setup on your side it might be easy to introduce this new flow. But if you don't to implement such a thing on your side with your own setup could be tricky. Please check https://www.digitalocean.com/community/tutorials/an-introduction-to-oauth-2#grant-type-client-credentials

How do I implement oauth2 with kong api gateway?

I want to implement an api gateway for a bunch of micro services running on laravel. In front of the gateway there is an angular client where the user has to login with the username and password. The idea is that the user sends the request with the credentials to the gateway which forwards it to the authentication service. If the data is correct, a token will be issued, which will be included in every further request.
I think I will implement the gateway with kong and the oauth2 plugin. I have already looked at their documentation https://docs.konghq.com/hub/kong-inc/oauth2/#resource-owner-password-credentials but I don't really understand the flow.
Does the angular client have to communicate directly with the authentication service on the first request? And if so, does the authentication service need an own url? I think it would make more sense if all the request would go through the gateway, wouldn't it?
Thank you!
From what I understood, your angular app can send username:password to kong gateway and that will proxy the request to your authentication service. You can verify if the user is legit in your auth service.
1) if legit, then make a request to /oauth2/token endpoint provided by kong's oauth2 plugin. Kong will return your auth service an access_token which you can return back to the user
2) If not legit then throw an error.
Does the angular client have to communicate directly with the authentication service on the first request?
Only if your auth service is a third party service you can do that.

Securing SpringBoot API for desktop application client

I have a SpringBoot Micro-Service based backend API that uses Zuul as a gateway proxy between a JavaFX Desktop Application. Right now there is no security in place, but I am looking to secure the backend with Spring Security, however, every tutorial I seem to run across seems to be based on web-apps and I haven't seen anything for my particular use case. I don't know much about spring security but would like to know if I can accomplish my goals with it, and if so, what modules or examples should I be looking for.
Goals:
Provide a way for my API to know that requests are coming from the desktop app itself, I think the technical term for this is assigning the desktop app a client id and then having the Zuul Server validate that the client id is that off the desktop app before accepting the request. This should be the case for all requests
Only allow API traffic through the Zuul Proxy, all of the downstream requests to the micro-services behind the Zuul gateway should only be accepted if they are coming from the Zuul Server itself.
Allow requests for logging in and registering as a new user without any type of security other than the desktop client id discussed in 1.
When a user provides a successful username/password on login, they are returned a JWT which is then stored in the JavaFX application and used for all of the other requests to the backend.
Configure the token to expire after a specific time frame, say like 90 minutes and provide a method for automatically refreshing an expired token as long as the users account is still valid. For this, I don't want the user to have to re-login, I just want it to check behind the scenes to make sure their account is still valid and then issue a new token if needed.
Have user based roles so certain features, methods, endpoints, etc. are only accessible to users with the valid role. Within the GUI these features will be hidden or disabled, but I would still like a layer of security on the server side to protect against unwanted access in case someone was able to modify the app.
I am just writing down answers to each of your goals :
Passing the client Id in every request from desktop application doesnt make sense, instead you client Id and secret can be passed during authenticaiton call, Like we have in Oauth 2.0 framework. Rest https calls should be made from client, So to avoid tampering of request, You can also go for mutual SSL between your client application and Zuul API gateway, It assures that call is coming from Desktop client only.
Yes, Zuul api gateway should be single entry point to your application, Your internal microservices should not be exposed to public.
For user registeration, Client authentication can be achieved using client Id and secret
Correct, You can also create http only cookie at backend, which will include your jwt token only.
Token refresh can be achieved at zuul api gateway, if session is active, make call to refresh token endpoint to get new access token.
On server side, At zuul proxy you can validate the incoming bearer token expiry along with signature validation, with generic claims too. Now at microservices level spring security can be used for role based access control for particular methods.

API gateway and microservice authentication

How API Gateway and Micro services works.
Could anyone explain the basic flow of Micro service architecture with Gateway. I couldn't find the proper answer.
Say we have auth server and customer micro service running on separate instances and in front of all the services we have an API gateway.
My question is.
when user try to log in using username and password, the API gateway call auth server and return the access token to user.
Then user trying to access the specific url (/customers - customer micro service) that is running on separate instance.
what API Gateway do ?
validate the token with auth server and get the user id and pass the request to customer service with the user id ?
OR
validate the token and pass the request to customer microservice with the access token ? and customer microservice responsible is to the check the user id (Make an HTTP call to auth server) ?
I think that the most common approach is to use API gateway also as a security gateway, which means that API gateway is responsible for SSL termination and token validation. If token validation is successfully you can put user ID or user API key as a header and forward the request to microservice. Moreover you may also decide to perform not only authentication but also authorisation on the API gateway (usually with help of API management solutions).
Regarding your option #2 - I see no point in validating token 2 times. Best practise is to perform security validations on the edge, because in case of failed validation you use less resources (reject earlier)
To Answer your question , it is close to option #2 that you have mentioned . The API gateway will generally check the validity of the authentication token and then pass over the request to your micro-service . However you need to decide at design time if your micro-service will also do another level of verification of the token.
Please do note that the API gateway will not be enforcing Authorization , the authorization is something that your micro-service will have to enforce.

spring cloud zuul ouath2 password authentication

i am currently building a security solution in spring cloud microservices.
when combining springs OAuth2 and Zuul implementation, it is quite easy to build an authenticationprocess like:
user calls the ui, which knows initially: user is not authenticated
redirect to auth server to ask the user for his login creds
redirects him back to the ui, providing a code or token.
I would prefer a flow with password authentication flow, in a way where the auth server is behind zuul
For example:
1.2.3.4:8080 is Zuul (with a UI with angularJS), domain "example.com"
1.2.3.5:9000 is the Auth Server
I could configure the zuul in a way, to access 1.2.3.5:9000 directly, passing form fields AND basic authentication to pass the client id.
since the auth server registers itself to eureka, I could also use "example.com/auth_server", which is the same, but managed through zuul. Alternatively I could also configure it manually....nevertheless:
Password authentication does not work, since Zuul is removing the basic authentication header from call....
at this point, I see I am doing something wrong...because the edge serve COULD have it's own security solution and tunneling the basic authentication to auth may be not the best way....but
HOW can I manage password authentication with ouath2 through zuul?
Please Help :)
By default "Cookie", "Set-Cookie", "Authorization" are marked as sensitive headers on a route and are not forwarded. Setting zuul.routes.myroute.sensitiveHeaders='' should allow you to pass those headers through, though I'm not sure it's the best idea.
The problem was a late working session in the evening :)
The component making the request didn't send the authorization since some updates which led to no headers ever reached the edge server.
Obviously, everything works as intended if basic or bearer authorization headers are passed over

Resources