I just thought about writing a GWT app that just works as a client for a RESTful web service. The web service requires HTTP basic authentication for each call.
Since the client is not 'connected' with the server over a session, I have to remember the authentication credentials on the client side. I could do this within the GWT application, but with this, the client has to log in after every reload, which is not very beautiful. I also don't think it's a good idea to write this information to cookies, since everyone could read them.
So, who knows what I am looking for? :-)
Browsers save the username/password information for a given server/port/domain. So if the client has to login once (at least via the browser standard BASIC http dialog) it's preserved over the reloads.
I don't know if you can do that. Maybe forcing the user to navigate to a page inside the domain (or realm) and then using GWT...
Related
I have a web application running on JBoss server based on JSF framework.
I need to redirect my request to an entirely new web application running on some other server and on some other machine geographically located.
My doubt is if I redirect the request from my web page to another web application web page will it expose the session parameter at the other end.
I have some very critical information stored in the session and I cannot afford to expose the details to another web application..
Along with the redirect request I would be sending some parameters to the remote web application which will use these parameters for certain mathematical computation.
Can anyone guide me on this?
Is it possible for the other web application to see what is present in the session
No. That would have been a huge security hole throughout the current world wide web. Think about it once again, are you able to see what for example google.com and stackoverflow.com have in its session? No? Then the other web application definitely also can't. All which the web application can see from outside is the sole incoming HTTP request in its entirety.
This problem/question has at least nothing to do with JSF.
If you invalidate the session before the redirect then it doesn't matter if the external web application sees your session cookie. They couldn't turn around and emulate requests on your session anyway because the session is no longer valid.
request.getSession().invalidate();
I don't think this will be an issue though because I doubt that the request header to another web application would include the same session cookie.
I have a standard HTML login page, which I would much rather use than the standard HTTP authentication pop-up provided by browsers. Today, I am using session cookies to keep track of the session after logging in, but I'd like to be stateless and pass the HTTP authentication every time. The web services I am hitting already support this, so this is a browser-only issue.
Adding authentication credentials is trivial in jQuery, but I don't know how to keep them around. If you go from the login page (a jsp) to the Home page (another jsp) you clearly don't keep the username and password fields from the login page. I know some browsers will store your HTTP authentication credentials if you enter them from the pop-up, but I don't know if they get stored when using an XHRRequest. If they do, is there much consistency among browsers?
Also, the user needs to be able to "sign out" of the application, too. If the browser stores the authentication credentials, is there a way to clear them using JavaScript.
I feel like I can't be the first person to try to solve this. Is there some jQuery plugin or something that already handles this? Or is it simply not possible to do what I'm trying to do?
You have 2 options:
1) Client-side storage of credentials -- not a good idea. For obvious reasons you don't want to store the username/password on the client. If you had a hashed version of the password, it might not be so bad, but still not recommended. In any case, if you're going to store on the client side, you either have to use a cookie, or HTML5 local storage (which is not widely supported, yet)
2) Server-side storage of credentials -- typically done with sessions. Then the resultant Session ID can be passed back to the client and persisted in either a cookie or in the URL of each subsequent AJAX call (?SESSID=xyz for example)
The server-side approach would be the most secure, reliable, and easiest to implement
Okay, I'll take a stab at helping ...
Firstly, understand how HTTP authentication works. There are two versions - Basic and Digest. Basic transmits in plaintext, digest is encrypted. With these types of authentication, the username/password are passed in the HTTP header with every single request. The browser captures these at login and they are stored in an inaccessible browser session cookie which is deleted when the browser session is closed. So, in answer to one of your questions, you can't access these from javascript.
You could create your own session cookie variables for username and password. The jQuery functions for this are really simple. See jquery-cookie module as one example of how to set session cookies. These could be retrieved from the session cookie and sent with each ajax request and validated in the server. However, this is not a particulary good way to do authentication since sniffing the network will allow anybody to easily grab your auth details. But, it would work.
Using session cookie based authentication where the session ID is sent sent with each request is the best way to do this. At the server side, you need to have a function called for every HTTP request. This function should do the following:
check to see if the session has been authenticated
if no:
redirect to login screen
if yes:
do authorization and allow the user access to the page
Most web frameworks support session cookie authentication and the management of session ids at the server. This is definately the way to go.
This is interesting one.
Manage user sessions on server by use of cookies. Create a session when user first accesses the login page and pass the session id/key as value to one of the cookie via response. When the user is authenticated put user "key" info in cookie and "values" in application context at server. Once user is logged, any subsequent request will be authenticated based on session cookie value at server. Authorization will be done based on user "key" passed as cookie value.
On logout clear the session based cookies from server and refresh the site to default page.
Cookies are bizarre with different browsers - just a note ;)
Hope this helps.
Update
The answer below was posted in 2012 and the links are mostly dead. However, since then, a more elegant standards-based approach to the same solution appeared using JSON Web Tokens. Here is a good blog post explaining how to use them.
Most answers miss the point, which is to avoid having any server-side session. I don't want any application state in the server. I'll award the bounty to answer that came closest, but the real credit goes to the rest-discuss group and Jon Moore for the correct answer and to Mike Amundsen for helping me to actually understand it.
The best answer I've gotten is to use a cookie, but not the typical automatic session id cookie given to you by most application servers. The cookie (which will automatically be sent with each subsequent request) is a user identifier and time signed by the server. You can include an expiration time with the cookie so it simulates the typical 30 minute session on a server (which means you have to push it forward with subsequent requests) as well as keeps the same cookie from being valid forever.
The XHR/AJAX part is a red herring. This will work whether you are doing XHR requests or an old-fashioned page-by-page web application. The main points are:
The cookie is automatically sent on subsequent requests so there's no
special scripting required - it's just how browsers work already.
The server does not need to store any session for the user, so the user
can hit any server in a cluster and not have to re-authenticate.
Slightly interesting in that you consider pushing some of the authent to the client. If you want a conventional solution, KOGI's server-side suggestion is the way to go.
But you also seem to be asking questions about memory leaks involving your user supplied secrets. Good questions. But to take a general stab at answering that I'd say it would have to be browser specific. It's browser internals, javascript engine internals -dependent where a client side application (i.e., the browser, or js in the browser) is storing the values the user inputs.
Most likely those values are not replicated needlessly throughout memory, but there's no way to guarantee that. Apart from responsible javascript coding practices, there's nothing you can do to guarantee the limit of locations of user inputs.
Slight digression
The basic point is if you store it on the client it is not really secure -- unless, the serve stores encrypted information on the client with a key that only the server (or the user via their correct credentials), has. So you could conceivably code a JS application to do some authent on the client -- much the same as how bank card (used to?) do POS authent by checking the PIN to the PIN on the card, and not back at the DB. It's based on the (somewhat flimsy) assumption the user has no direct read/write access of the "dark area" cookie/local storage on client / mag strip on bank card. So I would only advise this as disqualifier for false authents and not as a sole qualifier for the credentials.
Main point
If you do want to be stateless, just store user credentials in localstorage, or as a cookie but encrypt them with a server key. When you need them send an XHR with the encrypted / use stored credentials to the server over HTTPS, let your server decrypt them and send them to the callback. Then pass those cleartext of HTTPS to do your authent.
My question is that suppose, in my web app, I use ajax to call upon methods on the server side, isn't it creating a security hole in the app? Like, say I have an option for the user to deactivate the account, which can be done by clicking a button. This is done via Ajax.
So, can't a hacker send a request to the server to deactivate the account instead of the user?
HELP!!!
My question is that suppose, in my web app, I use ajax to call upon methods on the server side, isn't it creating a security hole in the app?
From a security perspective, there is no difference between an HTTP request that involves JavaScript and one which doesn't (e.g. that uses a regular form, or is handcrafted).
… but you can't call methods from the client, you can only make requests to URIs. The server might cause a method to be called based on receiving a request to a specific URI.
So, can't a hacker send a request to the server to deactivate the account instead of the user?
They could, which is why you need (trustworthy) authentication / authorisation and CSRF protection (just like you would for a request to disable an account that didn't involve Ajax).
This is not a problem with AJAX alone, but with any arbitrary HTTP request that wants to authenticate/maintain a session. The user needs to be authenticated in some way in order to make requests, this is usually done with cookies. Using AJAX does not make the matter any worse though because it is still a HTTP request.
Authentication alone is not enough though, someone could always be listening on the wire and capture the authentication cookie, and thus get hold of the session - "become you". The only solution here is to encrypt the connection on a lower OSI layer level (using SSL/TLS). This is why you should always use SSL when it comes to authentication.
This Ruby on Rails security guide has a great explanation on how to deal with AJAX requests that could be potentially exploited. It's not specific to RoR so the concepts can apply to any platform.
One way to reduce the risk of cross site requests is to use POST for actions that modify or delete data.
I am desiging a RESTful Web Service (JBoss + RESTeasy). The UI programmer is writing an Ajax web app that will use it. The web app will be one HTML page with everything done in JavaScript. For security, all traffic goes through SSL.
Currently I'm using Basic authentication. The UI programmer can show a dialog to get a username and password and put "Authorization: Basic xxxxx" in the header. Unfortunately if the password is wrong, the ugly browser login dialog box comes up. Also there is no way for the user to log off. This is unacceptable.
There appears to be no way to intercept a 401 response to an XMLHttpRequest in any of the browsers we will use.
Form-based authentication won't work for us. We need an automatic logoff after some period of inactivity (the equivalent of a session timeout). We can't have the server suddenly return a login page when the client expects a JSON object.
JBoss offers four authentication strategies: BASIC, FORM, CLIENT-CERT and DIGEST. I think DIGEST has the same problem as BASIC. None of the four is what we want.
This web application will be the only client (for now) so there is no requirement to use BASIC. Is there any other authentication strategy I can install? For instance is there an implementation of WSSE UsernameToken I can use? (As described in Chapter 8 of the O'Reilly RESTful Web Services book.) The server would send "WSSE" instead of "Basic" in the WWW-Authenticate header and presumably the browser would ignore it and pass it right through.
I want to configure security where it belongs -- in the JBoss configuration files, not in my RESTful Web Service -- so I'm looking for an implementation I can just plug into JBoss.
The browser won't present the password dialog if it doesn't recognize the authentication scheme in the WWW-Authenticate header. Your best bet may be to continue using basic auth on the server while setting the header manually to something like "Basic/MyApp" for 401 responses.
I am currently working on the authentication of an AJAX based site, and was wondering if anybody had any reccomendations on best practices for this sort of thing.
My original approach was a cookie based system. Essentially I set a cookie with an auth code, and every data access changed the cookie. As well, whenever there was a failed authentication, all sessions by that user were de-authenticated, to keep hijackers out. To hijack a session, somebody would have to leave themselves logged in, and a hacker would need to have the very last cookie update sent to spoof a session.
Unfortunatley, due to the nature of AJAX, when making multiple requests quickly, they might come back out of order, setting the cookie wrong, and breaking the session, so I need to reimplement.
My ideas were:
A decidedly less secure session based method
using SSL over the whole site (seems like overkill)
Using an iFrame which is ssl authenticated to do secure transactions (I just sorta assume this is possible, with a little bit of jquery hacking)
The issue is not the data being transferred, the only concern is that somebody might get control over an account that is not theirs.
A decidedly less secure session based method
Personally, I have not found using SSL for the entire site (or most of it) to be overkill. Maybe a while ago when speeds and feeds were slower. Now I wouldn't hesitate to put any part of a site under SSL.
If you've decided that using SSL for the entire site is acceptable, you might consider just using the old "Basic Authentication" where the server returns the 401 response which causes the browser to prompt for username/password. If your application can live with this type of login, is works great for AJAX and all other accesses to your site because the browser handles re-submitting requests with appropriate credentials (and it is safe if you use SSL, but only if you use SSL -- don't use Basic auth with plain http!).
SSL is a must, preventing transparent proxy connections that could be used by several users. Then I'd simply check the incoming ip address with the one that got authenticated.
Re-authenticate:
as soon as the ip address changes
on a time out bigger than n seconds without any request
individually on any important transaction
A common solution is to hash the user's session id and pass that in with every request to ensure the request is coming from a valid user (see this slideshow). This is reasonably secure from a CSRF perspective, but if someone was sniffing the data it could be intercepted. Depending on your needs, ssl is always going to be the most secure method.
What if you put a "generated" timestamp on each of the responses from the server and the AJAX application could always use the cookie with the latest timestamp.
Your best bet is using an SSL connection over a previously authenticated connection with something Apache and/or Tomcat. Form based authentication in either one, with a required SSL connection gives you a secure connection. The webapp can then provide security and identity for the session and the client side Ajax doesn't need to be concerned with security.
You might try reading the book Ajax Security,by Billy Hoffman and Bryan Sullivan. I found it changed my way of thinking about security. There are very specific suggestions for each phase of Ajax.