force signalr to re authorize user - asp.net

I'm using signalr and since I wanna use websockets the [Authorize] attribute only authorize the client when the connection opens and then everything is ok. I would like the [Authorize] process to be triggered somehow.
Note: Must works using websockets
For example (I use Owin.Security.Cookies (UseCookieAuthentication)):
I connect to my application with a valid token in my cookie, once I've done this I manually remove the cookie in my browser and everything still works OK until I reload the page. Another example is if the client already has an open and valid connection, but the token limit expires - it's still valid until a reload is done.
Now to my question - Is there anyway I can force signalr to re-authorize the token every x min?

For the rest of this answer, I'm going to assume you're using SignalR hubs instead of PersistentConnections.
When you use SignalR's [Authorize] attribute or your own custom version of it, there are three methods to be aware of.
AuthorizeHubMethodInvocation
This is called, as you might expect, when a method on your hub is called. This could be any method, or only methods you apply an [Authorize] attribute to. You could put your code here.
AuthorizeHubConnection
This is probably what you want. Every time the client connects to the hub- which is a fairly frequent occurrence- this method is called. Do NOT confuse this with SignalR's Hub's idea of a connection. When a client is communicating with a SignalR hub, this method is called frequently- every method call or two on average.
This is where I would put the code you're talking about. You'll want to create a new attribute that inherits from SignalR.AuthorizeAttribute. In there, you'll want to override either AuthorizeHubConnection or AuthorizeHubMethodInvocation. Do note that if you don't override one of these methods, they will call UserAuthorized to make their decision.
In one of those two methods, you want them to return true if their cookie is valid (it exists, has a valid token, and hasn't expired), and false otherwise. This code will be called every time- or just about every time- a call is made to the hub, and deny access to the client if anything's wrong.
Hope this works!

Related

Adding custom validation logic to dart:io HttpClient

I am trying to create an HttpClient that can validate an SSL certificate after every TLS handshake and before any other data is fetched/sent.
So the flow would look like this:
Create an HttpClient
Execute a request
The client connects to the host via HTTPS
After the TLS handshake was done, the client now knows the certificate
Pass the certificate to a callback. Execute actual request when callback succeeds, abort the request otherwise
In case the callback was successful, proceed as usual (e.g. pass the response etc.)
I was looking into SecurityContext already. The problem is that it only validates against a fixed set of certificates, but I want to validate the certificate dynamically based on the certificate that was sent by the host.
Also, I saw that there is a badCertificateCallback method in HttpClient, but this does not serve my usecase well as I want to validate every certificate, not just the invalid/bad ones.
I was wondering whether I could theoretically create a class that uses HttpClient as a superclass and therefore modify it's behaviour, but I am wondering whether there is a more elegant way that doesn't break that easily when the implementation of HttpClient changes.
Another idea of mine is to set a SecurityContext that rejects every single certificate by default. I could then use the badCerificateCallback to do the checks normally done by SecurityContext (check against a list of trusted certificates) and add my own validation on top of that. Is anyone aware of any drawbacks this might have? I got a little bit uncertain when reading about the limitations regarding iOS.
Has anyone here done similar things before and could give me a hint? :)
Thanks in advance!
For your usecase, it is better that you have your own version of BetterHttpClient.
However, instead of BetterHttpClient inheriting from HttpClient, you can use composition. Compose HttpClient inside BetterHttpClient. This will give you more control over what you want to use/update from the existing implementation and also this will be better guarded against any changes that HttpClient will go through

Risks of AJAX calls to asmx

Currently working on an ajax call to an ASP web service (.asmx).
In a situation where I POST to the url/.asmx/WebMethod, am I exposing information of any kind?
In the 'WebMethod' I am running a PostJsonAsync that calls an API and passes along a json string.
As I am still learning, I've been told that calling any public [WebMethod] exposes the code, but I am not sure how that is possible.
Is it possible at all for a user to access the WebMethod server-side code that I have and peek into the API calls that are available?
I've attempted some minor security methods.. We are working with Sitefinity CMS. What I did was call a WebMethod that receives the CurrentUserIdentity and returns a GUID. If the current user is logged in, it returns a valid Guid, if not it returns a Guid full of zeros.
Then, I call the WebMethod containing my API call and post a json object along with the valid or invalid GUID. The server-side WebMethod code will then verify if the GUID is valid and continues based on if a UserProfile can be generated.
To me, this seems to be secure, but I've been told that this still leaves the WebMethod exposed as well as the API. I am however just not understanding what is exposed and what can be used.
If anybody can direct me to any resources that has more information on this, or if anybody can advise me on WebService security, I would appreciate it.
Thanks in advance.
If you're calling the methods via AJAX, then they are exposed to the public...and can be called by anything that can make a call to your server. That being said, there's nothing wrong with it unless you're doing something that's easily abused.
In your particular case, it sounds like the code is accepting a GUID that is assumed to have come from the first API call. If that's really the case, you may want to rethink how the mechanism works. Adding authentication checks for each method that needs to be restricted may be a better solution.

What is the correct way to add an EventListener to an AtmosphereResource?

I am using Atmosphere Framework 2.0.8.
I have implemented an AtmosphereHandler in my application and have two way communication occurring correctly over WebSockets and Long Polling.
I am trying to add some handling code for when the client disconnects to clean up some resources specific to that client (ie. I have an entry in a table I want to remove).
I have read the following wiki entries:
OnDisconnect Tricks: https://github.com/Atmosphere/atmosphere/wiki/onDisconnect-tricks
Configuring Atmosphere Listener: https://github.com/Atmosphere/atmosphere/wiki/Configuring-Atmosphere-Listener
The thing I am not clear on is where I should add the call to
atmosphereResource.addEventListener( new AtmosphereResourceEventListenerAdapter() {} );
I eventually found some example code in the JavaDoc for the AtmosphereHandler that registers the EventListener in the onRequest() method. http://atmosphere.github.io/atmosphere/apidocs/org/atmosphere/cpr/AtmosphereHandler.html
What I would like to know is if this is the correct way to go about it?
It is my understanding that the AtmosphereResource represents the connection between a client and the server for the life of that connection. The uuid stays consistent for the object on multiple calls through the onRequest() method from the same client. As such, the same AtmosphereResource object will get the EventListener added every time the onRequest method is called.
This seems wrong. Wouldn't this lead to thousands of EventListeners being registered for each AtmosphereResource?
It seems that the EventLister should only be registered once for each AtmosphereResource.
I feel like I am missing something fundamental here. Could someone please explain?
Here's an example using MeteorServlet, so it won't look exactly like what you'll have to do, but it should get you started. I add the listener to a Meteor instance, and you'll add yours to an AtmosphereResource. Each resource gets just one listener.
The overridden onDisconnect() method calls this Grails service method that handles the event. Of course, you'll want to call something that cleans up your database resource.
Note that the servlet is configured using these options. I think you might need the org.atmosphere.interceptor.HeartbeatInterceptor, but it's been so long since I initially set it up, I can't remember if it's necessary.

Securing web method on a public web app

I have a public web app that calls ASP.NET web method in an ASMX file, located in the same site folder in IIS. But, to prevent bots to ping the service directly, we'd like to secure the API so that only our HTML 5 client page can access it. Do you have a suggestion on how should I implement this kind of thing ? Not too much, just a simple mechanism that won't take a week of testing please. Doesn't have to be a 100% full proof method since it is public data and the API just pumps data out, not inserting anything. Just something to limit possibilities of DDOS attack on the API.
The way I've tackled this in the past is with a custom header.
Essentially if your web page is using some form of AJAX call to call back to your services layer, then you can use something like:
xhr.setRequestHeader('custom-header', 'value');
where 'xhr' is an XML Http request that you've built in Javascript
of course you could also take the much easier route of just adding a parameter to your calls query string, EG:
in your ajax call, request:
http://my.services/service.asmx?somesecretkey=foobar
instead of just
http://my.services/service.asmx
Then you can just use the request's query string collection server side to see if it's present or not, and refuse the connection if it's not.
You could even go so far as providing some seed value in the data passed to the page in the first place, then use that seed value to create a unique value (one the server can also calculate) that is returned back in your request to the server.
Doing it that way would provide a slightly higher level of security, as the values would be semi random and not easy for a bot to guess.
Bear in mind also, that if you control the calling page, and you are doing this by ajax, you can also put this key in your post variables collection too so it doesn't have to be visible in the get request.

How to insert the username into MDC for the entire web request

I am trying to use a Mapped Diagnostic Context to add the username of the user making a page request to all relevant logging statements. However I have tried three different ways to make it work without success:
Pushing the username into the MDC after login and removing after logout. This method ends up mixing up which logging statement came from which user.
Using a ServletFilter to push the username into the MDC on each page load and pop it back off as the request ends. This only catches some of the data and only in Spring security layer.
Using a AOP #Around interceptor in front of all the Controller methods flat out didn't work.
Does anyone have any suggestions on how to make this happen?
What were the problems with MDC? What do you mean by Spring security layer? I used this approach in one web application and it worked well. Because MDC is bound to thread, all logging statements coming from this thread will have username set, i.e. service and repository layer as well.
Of course if some users are served from using threads (e.g. servlet 3.0 asynchronous processing, JMS listeners, executors), you will need the other way of injecting username to MDC in pooled threads.
Also see my answer here.

Resources