Closed ssc-hrep3 closed 6 years ago
I totally agree on your analysis. That's also why our JWT tokens have a quite short life - that limits a lot the XSS risk, and for me the biggest issue is a usability one (as you'll be logged out a bit too often). If you want to totally remove the XSS risk, and use a session, then we have 2 other options: session-based authent, and OAuth2 (which in the end is a bit of a mix between JWT and session-based). I personally like session-based authentication, but today it's not what people find "cool" - maybe it will come back in a few years? Those have other issues (typically you'll need to use sticky sessions, etc), so for me it's a choice, and that's why we give the choice to the user when generating the application.
By having a short life, the security vulnerability of JWT tokens in this implementation, gets limited, but not removed at all. We are planning to allow our user base to use the remember-me feature. Then, the (jHipster-default) time period, in which the token can be used by an attacker, is up to a month.
As you've mentioned, the usability is also an issue, when the users get logged out too often. What would speak against using a fingerprinting algorithm as described here?
In this case, a random value gets generated and is sent along as a HttpOnly
cookie to the front-end. The hash of this randomly generated value is part of the JWT token's raw data part. Finally, the back-end checks if the hash of the HttpOnly
cookie is equal to the hash stored in the JWT token, before allowing any access.
It's just a small, additional step, but would increase the security of all JWT jHipster applications (especially, if the remember-me
functionality is enabled).
@ssc-hrep3 I think it's a good improvement, it should be the default behavior even if it should be configurable in case your API has to be consumed only by non browser clients.
I'm not worried about session stickiness as there's no session server-side in this approach and as long as cookie domain is correctly set it should be fine.
Yes that looks like a good improvement. Sending a cookie adds some overhead, as it is sent with each response, but that's a small price to pay for security. We just need to be sure this works well with our microservices architecture, or find a solution if needed.
For microservices I guess it shall only be done on the gateway
I think we already use HttpOnly cookie to store JWT token in case of microservices (at least I am sure of its use with UAA) and CSRF check is enabled on gateway.
On Thu 19 Jul, 2018, 1:22 AM Christophe Bornet, notifications@github.com wrote:
For microservices I guess it shall only be done on the gateway
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/jhipster/generator-jhipster/issues/7992#issuecomment-406053260, or mute the thread https://github.com/notifications/unsubscribe-auth/APQa8ZUAbEJ5kZSfXUM7GwAypoNNVWX2ks5uH5HkgaJpZM4VUzBQ .
Another reason why we store the jwt is for Swagger client, so whatever improvement is done should work with swagger client as well
On Thu, 19 Jul 2018, 4:18 am Vishal Mahajan, notifications@github.com wrote:
I think we already use HttpOnly cookie to store JWT token in case of microservices (at least I am sure of its use with UAA) and CSRF check is enabled on gateway.
On Thu 19 Jul, 2018, 1:22 AM Christophe Bornet, notifications@github.com wrote:
For microservices I guess it shall only be done on the gateway
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub < https://github.com/jhipster/generator-jhipster/issues/7992#issuecomment-406053260 , or mute the thread < https://github.com/notifications/unsubscribe-auth/APQa8ZUAbEJ5kZSfXUM7GwAypoNNVWX2ks5uH5HkgaJpZM4VUzBQ
.
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/jhipster/generator-jhipster/issues/7992#issuecomment-406133009, or mute the thread https://github.com/notifications/unsubscribe-auth/ABDlF6ea4C3CwXeQlx8ux7iNVLC0X9DDks5uH-xpgaJpZM4VUzBQ .
@jdubois Using OIDC is the safest way to implement AuthN and AuthZ using the JWT token. OpenID Connect recommends different types of flows for different use cases. When it comes to JS SPA(Angular), "implicit flow" is recommended as it's a basic Web-based Relying party.
The JS SPA implicit flow with better security can be achieved using the "Silent Renew" process without impacting the "usability".
To refresh your short-lived tokens (e.g: 1 minute) when using the implicit flow you can use a silent refresh. This is a well-known solution that compensates the fact that implicit flow does not allow issuing a refresh token. It uses a hidden iframe to get another token from the auth-server. When the user is there still logged in (by using a cookie) it will respond without user interaction and provide new tokens.
More information can be found in the following Library. This library is certified by OpenID Foundation. (RP Implicit and Config RP)
https://github.com/damienbod/angular-auth-oidc-client
"state" and "nonce" is also available in OIDC to improve the security and it's implemented in the above library.
In OIDC implicit flow implementation, the "remember me" feature is handled by the identity provider/auth-server.
We already use OIDC in our OAuth 2.0 / OIDC authentication option. We use authorization code flow since it’s more secure than implicit flow. However, you can still use implicit flow if you want, you just need to add an @EnableResourceServer implementation. The React Native and Ionic modules for JHipster do this. JHipster for Ionic uses the Angular library you mentioned. It’s awesome!
On Aug 17, 2018, at 18:00, Vinod Anandan notifications@github.com wrote:
@jdubois Using OIDC is the safest way to implement AuthN and AuthZ using the JWT token. OpenID Connect recommends different types of flows for different use cases. When it comes to JS SPA(Angular), "implicit flow" is recommended as it's a basic Web-based Relying party.
The JS SPA implicit flow with better security can be achieved using the "Silent Renew" process without impacting the "usability".
To refresh your short-lived tokens (e.g: 1 minute) when using the implicit flow you can use a silent refresh. This is a well-known solution that compensates the fact that implicit flow does not allow issuing a refresh token. It uses a hidden iframe to get another token from the auth-server. When the user is there still logged in (by using a cookie) it will respond without user interaction and provide new tokens.
More information can be found in the following Library. This library is certified by OpenID Foundation. (RP Implicit and Config RP)
https://github.com/damienbod/angular-auth-oidc-client
"state" and "nonce" is also available in OIDC to improve the security and it's implemented in the above library.
In OIDC implicit flow implementation, the "remember me" feature is handled by the identity provider/auth-server.
— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub, or mute the thread.
Hi @mraible,
Thank you very much for your reply.
Sorry, I think I wasn't clear enough with my point. As OIDC enables a safer AuthN and Authz using the JWT without compromising "usability", why are we considering the insecure implementation of JWT?
OIDC has multiple flows (authorization code flow, implicit flow, hybrid flow) available to meet the most of the JHipster use cases.
Thanks,
Vinod
This has been opened for nearly 2 months and is still "in discussion": I'm sorry but we have 50+ opened bugs at the moment, so I'm closing this as it's not moving forward.
While I totally agree with the initial comment, we do provide both OIDC, JWT and also session (cookie-based) options depending on the user's needs. JWT is less secure, even if we recently reinforced its security. Then:
If anybody wants to implement this feature, he is most welcome, of course. But as we are literaly drowning in unresolved issues, we need to prioritize, and stop stuff that is not moving forward fast enough.
Overview of the feature request
For securing the application, JHipster supports an authentication with JSON Web Tokens (JWT). Those tokens are currently provided by a TokenProvider in Java and then sent to the Angular front-end. The front-end then stores the token either in the session storage or the local storage.
The session storage as well as the local storage allow direct access to the token via JavaScript. This opens up the possibility of a token sidejacking attack. Malicious JavaScript code might send the token to an attacker's server.
With a session authentication, the session ID was usually sent as a cookie with the
HttpOnly
flag. This prevented the JavaScript code to read the ID and e.g. send it to another server. It was automatically sent alongside with every request to the same server. Of course, this opened the issue of a CSRF attack. By using a CSRF prevention method this attack vector could however be remedied.This issue can be solved by implementing a fingerprinting algorithm and using a fingerprint hash in the JWT token, as It is explained here.
It can also be solved by using a strict Content Security Policy (CSP) which allows the configuration of allowed methods (e.g. blocking all ajax requests, except to a specific host). This offers, however, security on another level and should therefore be an additional aspect of the security strategy. It is also not yet supported by all major browsers.
Motivation for or Use Case
By using many JavaScript dependencies, which by themselves also use dependencies, one cannot make sure, that the localStorage or sessionStorage is never read by a malicious attacker.
Second, an XSS attack can occur, when the JS developer uses unsanitized user input and e.g. stores this input in a database. By using Angular, this is not a problem as it used to be, but it still is a potential attack vector.
A stolen JWT token cannot be invalidated before it expires (in the current implementation of jHipster, as far as I've seen). If an attacker gets into possession of the token, he can use the token to steal the user identity of the victim and run API requests independently of the user's browser session in the name of the victim.
Related issues or PR
3405, but closed