Is there any Spring boot Security specific solution to my needs? - spring

I started using spring 4 mounth ago, I want to try any idea that I got and now I want to know if what I m trying to do is possible, if so is there any specific security mechanism that I m not yet aware of.
I successfully implmented a secured API that have Authentication and Authorization using the basic auth and ssl enabled, this API handles a cruds of pizza fabrication with it ingerdiants.
Now I Want to create another API that will handle billing of pizza so this api is going to use the previous.
this reuse principle got my attention is it possible to implement a security mechanisme in my second api that ask my first if my current user is loged in ?
the scenario in my head is looking like
user authentication and authorization in API pizza
user ask api bill to get a bill of a pizza (some request with headers ...)
the bill api asks the pizza api if the request source is already authenticated
pizza api answers if is authenticated or not
bill api store in memory the authentication state
By googling I m not sure if the spring security token based authentication is a solution.
NB: I m using only http Request there is no form or front end

High-level overview of the solution would be as follows:
Establish OAuth2 Server and Zuul gateway.
Service "A" authenticates against OAuth2 authentication server and calls service "B"'s Rest endpoint via Zuul gateway (i.e Zuul proxies call to Service "B") with OAuth2 token stored in the session and adds OAuth2 token in HTTP "Authorization" header on request.
Zuul looks up service "B" endpoint, propagates service "A"'s OAuth2 token using it's filter by inspecting Headers and and forwards call with the same token in "Authorization" header.
Service "B", which is protected resource, receives request, inspects headers and validates recived token against OAuth2 server.
You can also let Zuul automatically propagate OAuth2 access tokens further and authorize incoming requests against the OAuth2 service by using the #EnableOAuth2Sso annotation.

Related

Spring boot API with both Oauth 2.0/OpenID Connect and internal authentication?

I'm having a hard time figuring a good way to implement Oauth 2.0 and OpenID Connect authentication alongside an existing internal email+password authentication for a B2B Web app's API using Spring security.
We have a backend REST API that is a Spring Boot servlet application which currently authenticates users with OAuth 1.0 and the password grant. The front-end is an Angular single-page app through which users must log in with their username and password. The API's /oauth/token endpoint then delivers an opaque access token to be used for fetching secured resources that are then displayed within the app.
We'd like to add the possibility to log in using external authentication with OpenID connect, which is a perfect opportunity for switching to OAuth 2.0 and JWT tokens. Our API would then accept JWT tokens it delivered as well as external JWT tokens emitted by accepted issuers.
Reading and validating JWT tokens won't be a problem using Spring security's OAuth Resource Server. However things get complicated with how to make the classic username+password login flow work with JWT tokens.
We thought about delivering JWT access tokens the same way we used to with our old OAuth 1.0 tokens. The thing is, newer OAuth specifications advise against using the password grant, plus it simply isn't supported in the Spring authorization server project we're planning to use. The authorization-code flow w/ PKCE seems like too much for this case as we do not want the back-end API to render a login form but use credentials entered in the existing login form that is part of the single-page app.
I've read a lot about not using OAuth for 1st party login since its primary use is for external authentication, but again, that doesn't apply since we also want 3rd party authentication.
What would be a secure way to implement a Spring boot authorization server that can deliver JWT access tokens to a 1st party client in exchange for a user's credentials, all this using the existing log in page, and given the password grant type no longer being supported?
I thought about implementing a preliminary step that would be a POST request with Basic authentication to a /login endpoint that just returns a 200 HTTP status, then proceeding to the /oauth2/authorize request that would deliver the authorization code immediately without redirecting since my session is authenticated.
I'll be happy to provide more details if needed. Here are the resources I'm using for this project.
What about setting up an authorization-server capable of identity federation?
In such configuration, the authorization-server is responsible for providing with identities, proxying one or more sources (your existing user database for instance, plus maybe Google, Facebook, Github, etc.)
Keycloak does it for instance.
From the client point of view (your Angular app), the authorization-server is used to get:
access-token: put in Authorization header of requests to secured resource-server(s) (can be a JWT or an opaque string, doesn't matter, clients should not try to extract data from access-tokens)
refresh-token: send to authorization-server to renew access-token before it expires
id-token: get user-profile data (email, username, profile picture, etc.)
You should have a look at https://github.com/damienbod/angular-auth-oidc-client for connecting an Angular app to an OIDC authorization-server.
From resource-server point of view, access-tokens are the source ofr setting-up security-context, either by decoding and validating a JWT locally or with token introspection on authorization-server.
Have a look at those tutorials for such resource-servers configuration.

Debugging The interface between Resource Server and Authorization Server (oauth 2.0. validation access token)

There are two spring-boot apps.
client
resource-sever
there is dev okta account that is used as auth server
(those 2 apps are standard Spring Boot client -> resource-server, almost out of the box with okta setup for them, should not be problem there)
client - securely sends messages to--> secure-sever (passing the access token in the header as prove that it's authorized to call it and get data back)
(it works as expected)
But I am trying to figure out what's going on between all them, traffic wise
I'm trying to spot that moment when resource-server checks the token it got from the client that got it from the auth server.
Here is a sequence diagram of standard oauth 2.0 flow and that part that I want to debug (arrow)
auth server
And there is a communications between client, resource-sever:
There seems I can not confirm that Resource Server (from the right) does any token validation with the auth-server (okta)..?
Question: is why? From my understanding it is supposed to validate it (somehow).
I was expecting to see a call from resource-server to auth-server (otka) with the token-validation-request (ETF RFC 7662 in October 2015) like this:
How to validate an OAuth 2.0 access token for a resource server?
I was expecting, lets say, tat for every client call, resource server would check if that token the client passes is valid. Yet I do not see any calls from resource service to okta that would use the token in its requests to okta.
This comes down to the difference between JWTs and opaque tokens.
It looks like your application is using JWTs, based on the calls I'm seeing to /keys.
When using JWT authentication the resource server will query the jwks_url (in this case /keys) on startup to retrieve a set of public keys that it can use to validate the JWT-encoded bearer tokens.
Then, when the resource server receives a bearer token in a request from the client it will validate its signature against a public key obtained from the jwks_url endpoint.
This means the resource server doesn't have to query the authorization server on every request.
You can read more about this process in the OAuth 2.0 Resource Server JWT section of the Spring Security reference documentation.
The question that you linked to refers to opaque tokens.
In this setup, the resource server must call the authorization server introspection endpoint to validate the token every time.
You can read more about this process in the OAuth 2.0 Resource Server Opaque Token section of the Spring Security reference documentation.

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.

How to validate the user in jwt

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.

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.

Resources