views:

250

answers:

13

I'm writing a web application for public consumption...How do you get over/ deal with the fear of User Input? As a web developer, you know the tricks and holes that exist that can be exploited particularly on the web which are made all the more easier with add-ons like Firebug etc

Sometimes it's so overwhelming you just want to forget the whole deal (does make you appreciate Intranet Development though!)

Sorry if this isn't a question that can be answered simply, but perhaps ideas or strategies that are helpful...Thanks!

A: 

"Quote" everything so that it can not have any meaning in the 'target' language: SQL, HTML, JavaScript, etc.

This will get in the way of course, so you have to be careful to identify when this needs special handling, like through administrative privileges to deal with some if the data.

Don
+1  A: 
  • You don't get over it.
  • Check everything at server side - validate input again, check permissions, etc.
  • Sanitize all data.

That's very easy to write in bold letter and a little harder to do in practice.

Kobi
+5  A: 

One word: server-side validation (ok, that may have been three words).

ChssPly76
+2  A: 

If its "security" related concerns you need to just push through it, security and exploits are a fact of life in software, and they need to be addressed head-on as part of the development process.

Here are some suggestions:

  • Keep it in perspective - Security, Exploits and compromises are going to happen to any application which is popular or useful, be prepared for them and expect them to occur
  • Test it, then test it again - QA, Acceptance testing and sign off should be first class parts of your design and production process, even if you are a one-man shop. Enlist users to test as a dedicated (and vocal) user will be your most useful tool in finding problems
  • Know your platform - Make sure you know the technology, and hardware you are deploying on. Ensure that relevant patches and security updates are applied
  • research - look at applications similar to your own and see what issues they experience, surf their forums, read their bug logs etc.
  • Be realistic - You are not going to be able to fix every bug and close every hole. Pick the most impactful ones and address those
  • Lots of eyes - Enlist as many people to review your designs and code as possible. This should be in addition to your QA resources
GrayWizardx
A: 

There are multiple types of injection and cross-site scripting (see this earlier answer), but there are defenses against all of them. You'll clearly want to look at stored procedures, white-listing (e.g. for HTML input), and validation, to start.

Beyond that, it's hard to give general advice. Other people have given some good tips, such as always doing server-side validation and researching past attacks.

Be vigilant, but not afraid.

Matthew Flaschen
+1  A: 

First, I'll try to comfort you a bit by pointing out that it's good to be paranoid. Just as it's good to be a little scared while driving, it's good to be afraid of user input. Assume the worst as much as you can, and you won't be disappointed.

Second, program defensively. Assume any communication you have with the outside world is entirely compromised. Take in only parameters that the user should be able to control. Expose only that data that the user should be able to see.

Sanitize input. Sanitize sanitize sanitize. If it's input that will be displayed on the site (nicknames for a leaderboard, messages on a forum, anything), sanitize it appropriately. If it's input that might be sent to SQL, sanitize that too. In fact, don't even write SQL directly, use an intermediary of some sort.

There's really only one thing you can't defend from if you're using HTTP. If you use a cookie to identify somebody's identity, there's nothing you can do from preventing somebody else in a coffeehouse from sniffing the cookie of somebody else in that coffee house if they're both using the same wireless connection. As long as they're not using a secure connection, nothing can save you from that. Even Gmail isn't safe from that attack. The only thing you can do is make sure an authorization cookie can't last forever, and consider making them re-login before they do something big like change password or buy something.

But don't sweat it. A lot of the security details have been taken care of by whatever system you're building on top of (you ARE building on top of SOMETHING, aren't you? Spring MVC? Rails? Struts? ). It's really not that tough. If there's big money at stake, you can pay a security auditing company to try and break it. If there's not, just try to think of everything reasonable and fix holes when they're found.

But don't stop being paranoid. They're always out to get you. That's just part of being popular.

P.S. One more hint. If you have javascript like this:

if( document.forms["myForm"]["payment"].value < 0 ) {
  alert("You must enter a positive number!");
  return false;
}

Then you'd sure as hell have code in the backend that goes:

verify( input.payment >= 0 )
CaptainAwesomePants
BTW, one of these conditions needs an equals. A value of zero passes on the client but not the server. I normally check maximums as well as minimums to ensure "reasonableness" too.
devstuff
+1 for "it's good to be paranoid."
vonconrad
A: 
  • No validation in web-application layer.
  • All validations and security checks should be done by the domain layer or business layer.
  • Throw exceptions with valid error messages and let these execptions be caught and processed at presentation layer or web-application.

You can use validation framework to automate validations with the help of custom validation attributes.

http://imar.spaanjaars.com/QuickDocId.aspx?quickdoc=477

this. __curious_geek
A: 

There should be some documentation of known exploits for the language/system you're using. I know the Zend PHP Certification covers that issue a bit and you can read the study guide.

Why not hire an expert to audit your applications from time to time? It's a worthwhile investment considering your level of concern.

Rimian
+1  A: 

Something I always did was wrap all user strings in an object, something like StringWrapper which forces you to call an encoding method to get the string. In other words, just provide access to s.htmlEncode() s.urlEncode().htmlEncode() etc. Of course you need to get the raw string so you can have a s.rawString() method, but now you have something you can grep for to review all uses of raw strings.

So when you come to 'echo userString' you will get a type error, and you are then reminded to encode/escape the string through the public methods.

Some other general things:

  • Prefer white-lists over black lists
  • Don't go overboard with stripping out bad input. I want to be able to use the < character in posts/comments/etc! Just make sure you encode data correctly
  • Use parameterized SQL queries. If you are SQL escaping user input yourself, you are doing it wrong.
Mike Weller
+3  A: 

There's lots of sound advice in other answers, but I'll add a less "programming" answer:

Have a plan for dealing with it.

Be ready for the contingency that malicious users do manage to sneak something past you. Have plans in place to mitigate damage, restore clean and complete data, and communicate with users (and potentially other interested parties such as the issuers of any credit card details you hold) to tell them what's going on. Know how you will detect the breach and close it. Know that key operational and development personnel are reachable, so that a bad guy striking at 5:01pm on the Friday before a public holiday won't get 72+ clear hours before you can go offline let alone start fixing things.

Having plans in place won't help you stop bad user input, but it should help a bit with overcoming your fears.

itowlson
A: 

Our client always say: "Deal with my users as they dont differentiate between the date and text fields!!"

I code in Java, and my code is full of asserts i assume everything is wrong from the client and i check it all at server.

medopal
A: 

#1 thing for me is to always construct static SQL queries and pass your data as parameters. This limits the quoting issues you have to deal with enormously. See also http://xkcd.com/327/

This also has performance benefits, as you can re-use the prepared queries.

Sharkey
A: 

There are actually only 2 things you need to take care with:

  1. Avoid SQL injection. Use parameterized queries to save user-controlled input in database. In Java terms: use PreparedStatement. In PHP terms: use mysql_real_escape_string() or PDO.

  2. Avoid XSS. Escape user-controlled input during display. In Java/JSP terms: use JSTL <c:out>. In PHP terms: use htmlspecialchars().

That's all. You don't need to worry about the format of the data. Just about the way how you handle it.

BalusC