I currently have a server implementation where a javascript front-end connects through the socketio protocol used by Netty-Socketio. The implementation works wonderfully with one flaw.
From what I gather, the only way to make the websocket channel aware of the security context of the user is to pass up the JSESSIONID in the handshake, which means putting it on the client page.
There is no way this is secure right? It would also mean that since we use an HTTPONLY header (Even more reason this shouldn't be on the front-end), we would need to make a call for the JS to return the current user's JSESSIONID. Even if we abstract this with a GUID, it still allows for session hijacking does it not?
Can anyone advice on a method to handle this better?
Related
As captioned, is it possible to achieve this without using cookie or session,and without involving any JavaScript as well?
No, this is not possible without involving some persistence on the client that is going to make the subsequent requests. There's no such notion in the HTTP protocol (other than a cookie) that would indicate to the client to include some header on subsequent requests automatically. So basically if you don't like cookies you might find another place to store the access token on the client - the local storage in the browser seems like a good place and include it in subsequent requests that a javascript client would make. Of course if your clients are not javascript then they will have to find an appropriate place to store the access token.
Question #1:
Is setAuthCookie any less safe than FormsAuthentication.Encrypt(ticketVariable)?
I mean if anyone tries to modify the cookie created by setAuthCookie, by modifying the username, I suppose that'll violate the authentication on subsequent calls?
Question #2:
for those using iphones and tablets to access the site, I suppose FormsAuthentication will fail? Given that I don't want to use cookieless option, is there another approach to make the site secure on both smart phones web browsers and ummm none-smartphone web browsers?
cheers
SetAuthCookie basically creates a new FormsAuthenticationTicket with the supplied username & persistence options, serializes it, FormsAuthentication.Encrypt()'s it, and sets it in the Response.Cookies collection. SetAuthCookie and GetAuthCookie both call FormsAuthentication.Encrypt indirectly.
On subsequent requests, the FormsAuthentiationModule handles the AuthenticateRequest event. If it sees a cookie (it may have expired), it attempts to decrypt it's value with the machineKey (it may have been tampered with) and deserialize it back into a FormsAuthenticationTicket (it may be corrupt). If none of that (bad stuff) happens, the ticket contains the username, issue date, expiration info, etc.. If the ticket hasn't expired, an IIdentity and IPrincipal are created and assigned to HttpContext.Current.User and Thread.CurrentThread.Principal. In .NET 4.5 and later (I think), this is Claims-based (ClaimsIdentity, ClaimsPrincipal). Prior to that, it was a (GenericPrincipal, FormsIdentity) I think.
Any tampering at all on the user side will cause the request to be treated as anonymous. It will fail to decrypt. The only things that would compromise this validation would be if the machineKey in web.config/machine.config somehow got into the hands of an attacker or if there was a bug in the framework code (search for Padding Oracle for a historical example of this).
Aside from that, the other thing to watch out for would be session hijacking. If someone steals your cookie on a public wifi for example, they can present it to the server and the server will behave as if it's you. This generally involves network traffic sniffing. For these reasons, best practice is to use SSL for your entire site and set the cookie to HTTP only and Secure (only presented over https connections) in web.config/system.web/authorization/forms. HTTP only means that it will not be available to client-side Javascript. HTTP Only and Secure effectively means HTTPS only. This will only work if you use SSL on your entire site.
FormsAuthentication will work fine on mobile web browsers. It simply requires the client to accept cookies. As far as I know, all mobile devices will allow this.
I'm using System.Net.Http.HttpClient to talk to a RESTful service in an MVC4 application on the back end. Depending on the user making the request the authentication header will be different for communication with the RESTful service, so the values to set in the header should be cached for each user. These values may change during a session's lifetime.
I am using StructureMap for DI. Some questions:
According to this it sounds like there should be a single instance of HttpClient for all requests. Although some say directly injecting the HttpClient may be a bad idea due to it being IDisposabe, others say that it's not necessary to dispose it. So, what is the best way to inject HttpClient?
Is it possible that the single instance of HttpClient can become disposed of or invalidated during run time (maybe the REST server reboots)? If so, then I think there is no choice in directly injecting HttpClient and it must be wrapped in a manager class that will check if the HttClient instance is valid and instantiate a new client if there's a problem. The issue is that I don't see a way make that test.
Where is the best place to cache the user specific authentication header information? I don't think that passing the information to the service layer from the controller is clean, as it seems to be suggested here, so I'm thinking an HttpSession scoped injected object in the data layer is the way to go here, but would love to hear other ideas.
Create the HttpClient when your MVC4 application starts and dispose it when it shuts down. If the server you are calling with the HttpClient reboots that will not require you to create a new instance of HttpClient. TCP connections are managed independently under the covers by the ServicePointManager.
I don't understand your question regarding user specific auth information. Are you trying to get your MVC site to impersonate the user when you call to the RESTful service? If so, then just set the Auth header on each request.
How does the new routing service deal with security? According to http://blogs.microsoft.co.il/blogs/applisec/archive/2011/12/12/wcf-routing-and-message-security.aspx, it might be difficult when default windows security is not chosen (typically a simple username/password scenario).
Can wcf routing actually support a scenario where the router receives a WS-Security secured message over HTTP and forwards it to another server over HTTP, without unwrapping the security token?
My scenario is as follows:
A server (relying party), a custom STS with username/password authentication and a client. We use ws2007FederationHttpBinding and message security.
Now we setup wcf routing, it works with basicHttp or wsHttp.
Then we using WIF, we can instanciate proxies, the STS generates claims, but it fails at the first service call. It seems the router is waiting for the certificate definition (included, otherwise we get an error), then seems to require Cardspace UI (while in fact we're using username/password).
If so, would you have an example ?
Thanks.
Good question, i couldn't find anything about this on google yet beside this question also being unanswered on msdn. I don't think this is added out of the box as normally u would need to use delegatation (ActAs) whenever u want to route the request to another service.
The only solution i can think of is creating a message inspector and use that one in your WCF Routing Service. And ofcourse u'll need to use "SupportInteractive = false"
I did found something that might be the answer, see the following post (ignore silverlight lol) http://zamd.net/2011/02/08/silverlight-claim-based-security/
Zamd says:
For the 2nd part I have implemented a message inspector along with an extension method which makes it super easy to attach the SAML with outgoing messages.
I have an application a the moment which for a particular set of reasons will be interacting oddly with the hosting server.
The application is to be accessed through a larger portal and can be encapsulated within the portal display, however it makes extensive use of AJAX requests which are not intercepted by the portal. These requests are made directly to the hosting server, however I am seeing a problem.
When the first ajax request is made (a little way into the application flow) the Ajax request is not carrying with it the JSessionId cookie (obviously as it's sending this to a different server than it received it from)
Is there a good grails way to find the session the AJAX call should be interacting with. I have tried setting grails.views.enable.jsessionid to true, but this only works if the browser is not accepting cookies.
Create a hidden form input value that has the jsessionid in it on the page you send back to the portal on the first request. Then read that form variable, and set the cookie in your javascript code that makes the AJAX request.
I'm guessing seeing that this already works, cross-site scripting isn't an issue? AJAX requests to domains other than that which the main page originated from will be blocked by the browser.
The most reliable way will be for you to set up your own "cookie" and pass that along with the requests.
It sounds like you are running into issues due to the portal and it's cookies and then having to continue that "session" onto a different server. Your application needs to simply handle it's own sessions itself in order to prevent getting stomped on by the "normal" cookies.
The idea is essentially to create a session token when the portal makes a request from to your application, and then the subsequent AJAX calls your application makes back to it's own server should include that token. You can then easily associate that token with the session you need to be using.
If you are looking to make it a bit more robust and handle it above the level of your application, you can leverage the fact that Grails is built on Spring MVC deep down and override the default session handler to pick up on whatever mechanism you decide to go with. I'm not sure of exactly how to do this with Grails, but I've done similar things on Spring MVC projects and it isn't too tough once you get your head wrapped around the various injection points of the framework.
It isn't ideal, since there is now a fair bit more complexity, but in theory, the benefits of the portal are outweighing the added complexity required for traditionally "handled" things like sessions and expiring them, etc.