Protecting web service against malicious requests to crawl for all data? - web-services

We have a web service that we want to protect against malicious attacks to make lots of requests to effectively get all the data out of it.
We have some level of protection with tokens that signed and exchanged, but a determined attacker could get these tokens and replay them on requests to our web service.
So I'm thinking the only protection is at the server level. One thought was to implement a request threshold in a specific time interval them block for duration of time, that grows if subsequent requests are made during the blackout period. After repeated attempts, completely blacklist.
However, I hate the idea of custom rolling our own solution and even using IPs at all since one bad user behind a proxy gets everyone else behind that proxy blocked.
What are the best practices for protecting a web service?
Update: To clarify, this is a general question about protection a web service against mass harvesting of data.

There are several solutions out there, but this one is nice and secure, IMO. Use X.509 certificate in SOAP headers for authentication at the message level. Here are a few links on the subject:
http://msdn.microsoft.com/en-us/library/ff648643.aspx
http://msdn.microsoft.com/en-us/library/ff648129.aspx
http://www.aspfree.com/c/a/VB.NET/Securing-Web-Services-with-X509-Certificates/
How can I configure WCF to use x509 certificates over the internet?

You don't tell us much about the data/service, but I once worked on the design of a system that would detect attacks by looking at patterns of the queries.

Related

Security about a simple REST web service

Here is my little API with two URL :
/api/location/list -> GET
/api/location/detail -> GET
I'm looking for a process to secure this service with authentication. For now, it can be accessed by only one user (me).
I think oAuth is too complex in my case and I found this resource for designing a simple API.
I understand the principle of private/public key and HMAC but I have a big concern about this :
Say my webservice is consumed by an ajax request with GET verb. I have something like /api/location/list?apikkey=userid&hash=abcde.
A end user can easily sniffed the network during the request (via a simple chrome console), capture full url and access directly to the service multiple times (I think it's a case of replay attacks).
Differents resources talk about timestamp or nonce to make a request unique but I'm a bit lost with implementation.
Any ideas ?
You can try JWToken auth specs, simpler than Oauth, but avoid authorization data as url parameter if possible and use Header's request instead.
If needed consider also ssl encryption at tcp level.
Perhaps you could try to use a token-based approach for security, as described in this blog post:
Implementing authentication with tokens for RESTful applications - https://templth.wordpress.com/2015/01/05/implementing-authentication-with-tokens-for-restful-applications/
The idea is to authenticate to an authentication resource (that can be part of your application) to get temporary token that can be refreshed with a refresh token when expired.
With the use of HTTPS, it seems to be appropriate.
I think that it depends on the security level you expect. Signature-based authentication (the AWS approach) is great but is a bit complex to implement by hand.
Hope it helps you,
Thierry

Protecting sensitive JSON data that is sent to mobile SDK (turning app into HTTPS)

I have an API endpoint which receives and sends sensitive data to a mobile SDK (that we created). The API lives in a Django Heroku app. I need to protect this information somehow, and I am a bit confused on where to start.
A friend of mine suggested provisioning HTTPS for my heroku app. After reading SSL Endpoints for Heroku, I couldn't be more confused. I read about buying a SSL certificate, yet their are so many different kinds, I don't know which one would fit my needs.
Mainly, my questions are:
What type of SSL certs do people get to protect APIs?
Would the mobile SDK require its own type of cert to interact safely with the web API?
Where can I buy/find a cert that fits my needs?
General question about HTTPS: Without HTTPS enabled, are logins able to be compromised on a heroku application with a custom domain?
Sorry if the questions are silly, I am new to SSL/HTTPS. Thanks!
The main thing that HTTPSprotects you from is man-in-the-middle attacks: that is, someone sitting between the client and the server who reads your web traffic, either copying important data or modifying what you send. In that sense, it gives some protection from compromised logins - in that no-one will be able to sniff your password from the data - but doesn't protect you from anything else, eg getting passwords from cracking, or social engineering (phishing) attacks, etc.
In terms of what to buy, the links on that documentation give you all you need to know, so it's hard to know what you mean by your first or third questions. For the second one, certificates are for the server, not the client, so unless you're serving your mobile API on a completely different domain from the rest, you don't need a separate one.

Repeat username/password authentication with each call to web service

I am creating a web service to expose to my mobile apps. I currently am implementing a token based authentication solution (because that what I have done in the past); however, I am struggling in this context to understand why I do not simply pass the username and password each time? I can maintain the password in RAM while running the Mobile app (encrypted between usages if we want to get overly complicated) and then pass it each time I connect to the server and repeat the hash verification each time. Of course everything is SSL so there is no more risk in terms of network transfer in doing it each time versus do it once is there? The only CON I see is that the hash validation process might me more expensive than a token validation - maybe. Are there other cons I am missing here?
There are a few reasons not to do this:
Every time you transmit the information, you open the risk of interception. (Even if that risk is mostly mitigated by using an encryption system such as SSL).
Passing a username / password combination on every request implies that you will be checking the combination of them on the server-side with every request. This usually requires an extra database hit and some logic which is unnecessary.
If you are passing credentialization such as this on every request, you will need to use SSL for every request - which is expensive overhead. It is much cheaper to send an encrypted authentication token back and forth in plain-text - which only the server-side can read.
This seems like a bit of a hot topic here on SO the last few days, as I've answered several questions about RESTful auth and such. I am providing below some links to those answers - which go much more in-depth. Perhaps if you take a look at the auth schemes I'm proposing - you'll see how it protects you more than simply sending username/password on each request.
Authentication in RESTful web services
Public facing Authentication mechanisms for REST

How can I implement security in web service?

I have a REST service that is called by a mobile app; I need the user to login, then the service generates a unique token associated to user id and this pair of userId/token is passed to every subsequent call to the WS.
I don't like too much this solution because, even if very difficult, if I change the uid and get the right token I can "login" as another user, so I'm trying to understand which is the best practice to handle web service authentication for a mobile (and non) application.
Your issue is not with the methodology, but the fact your service is not checking the combination of UID and token, but rather the token. That is a programming issue, not a methodology issue.
How secure do you need the service to be? Are you talking top secret level of security? Banking? My soccer club site? For high levels of security, you can use digital certificates, but it makes for a much more complex provisioning methodology. But ... Even if you are going to change from UID/Token (or AppId, User, etc), you still need to fix the fact that correct token + wrong UID works. That is a mistake if two-form authentication is a must. Changing methods will solve nothing if you don't have the proper programming on the server side to avoid circumventing the system.
You may also want to look at how you provision the Token. Should this be offline, or is one REST sign up method acceptable. This leads back to the level of security your require.
You might want to forget the token/id solution and consider going the SSL/basic authentication route. SSL will provide the encryption and secure communication, but will not secure the access to your specific web-services on the server side.
For that you can try standard basic http user/password authentication on every call. This way you do not need to worry maintaining state through each REST call. Each call will have an explicit reference to the user. Yes, you will need to re-authenticate the user with each call which is a bit of a pain, but you can cache your results.
However, I am far from an expert on the subject.

Should services ask for credentials at each request?

I wonder what is the optimal authentication method for services and webservices:
user/password is sent on each request
user/password is sent once to obtain an authentication code that will be sent on each request
Is there any alternative? Which is better? Why?
Depends on the protocol.
If the service requests are in the clear (http), then you might want to consider a secure (https) logon transaction, which gains you a limited-time token to authorise future requests (a session cookie, in effect). Then at least eavesdroppers don't get credentials that work forever, just for a limited period.
Likewise even if the logon transaction isn't secure, at least if it only happens once it's slightly harder to eavesdrop. It's also slightly harder to use.
If you don't care about security, I wouldn't even use a username/password, just an API key. Amounts to the same thing, but if the user doesn't choose it then at least it won't be similar to any of their other passwords, so it doesn't affect anything else when it's stolen.
If you care about security sufficiently that everything is done over https, then it doesn't really make a lot of difference what identification mechanism you use, AFAIK. So do something simple.
Finally, you might care about the security of the authentication, but not about the secrecy of the requests themselves. So, you don't mind eavesdroppers seeing the data in flight, you just don't want them to be able to issue requests of their own (or spoof responses). In that case, you could sign the requests (and responses) using a public/private keypair or a shared secret with HMAC. That might (or might not) be easier to set up and lower bandwidth than SSL. Beware replay attacks.
By optimal are you thinking about performance ? I would suggest to send credentials and authenticate on each request unless you really find this to be a bottleneck. SSL is not enough at all, it only provides encryption and authentication of the web service. But think about client authentication (a client cert can help here) and authorisation, may be not all users of the web service is not allowed to call all methods and all methods calls needs to be logged for auditing. In this case the user identity needs to presented for each call.
I develop and maintain a SOA based core system web service developed in WCF that authenticates and authorises against .Net based clients using windows identity and uses 2-way certs authentication against Java clients and I have no performance problem.
Steve Jessop clarified things for me:
if the credentials are memorized I should provide a transient authentication cookie after they are received,
but if the credentials are digitally stored then I should only use an API key, because anyone who can access the credential storage wouldn't need to access the cookie