This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
How to prevent SQL injection?
I am setting up a comment system on my site and I wanted to know if this is save. I use PHP and MySQL.
- Do not use code below, it's horribly insecure -
Creating a new comment:
User writes $comment, submits it
$comment = addslashes($comment);
insert $comment into MySQL database
Reading a comment:
User requests a comment, database delivers $comment
$comment = htmlspecialchars(stripslashes($comment));
echo $comment;
The system should be secure against HTML manipulations and MySQL injections. And all other nasty stuff I am not aware of. Am I doing it right?
Bonus question: What collation should I use for $comment in my MySQL table?
Edit: wow I didn't think my question could cause this huge discussion. Thank you for all your answers :)
Consider switching to prepared statements right from the start :-)
They may seem a bit overheaded now, but you safe so much time worrying about escaping each and every parameter that it pays back.
Here is a good Tutorial: http://www.kitebird.com/articles/php-pdo.html.
When printing out user defined content, you still need to use htmlspecialchars to account for XSS invulnerabilities.
Use mysql_real_escape_string (or whatever escaping function comes with your library) instead of addslashes.
Don't use stripslashes, because they have already been stripped by having been parsed by MySQL, and you run the risk of erasing legitimate backslashes in the input.
For the collation, use whatever you like. I prefer latin_general_ci, but if you want unicode you should use a UTF8-compatible collation.
Related
This question already has answers here:
Should I escape an expected integer value using mysql_real_escape_string or can I just use (int)$expectedinteger
(2 answers)
Closed 9 years ago.
I have a PHP script that depending on the value of an id in a GET variable will retrieve different data from a mysql database. The value of the id should be a number at all times. Instead of changing my current mysql query to use PDO, would running isnumeric on the Get variable and exiting the script if it is not a number be sufficient to protect against injection in all or most cases, ie, would it still be possible for some injection sql to slip through isnumeric?
Just a humble comment on the duplicate question issue, I looked at the suggested duplicate question and think that as a beginner it might not be clear on its face that my question is an exact duplicate of that one.
Yes, it would protect in this case. No, it would be a really, really bad idea unless you absolutely know what you're doing and document the choice properly in comments.
There are 2 strategies towards any kind of security:
Denial. Choose the lazy approach that works for the situation at hand instead of fundamentally fixing it. Now wait for the day you forgot this was your 'security', and you change the code and it becomes vulnerable all of a sudden, and kiddie porn is uploaded to your site.
Professionalism. Fix the problem thoroughly, validate the inputs and protect your database layer properly, by either escaping or using prepared statements.
Choose professionalism and thank me a year from now.
Seems like this question has already been answered. And yes, the isNumeric trick essentially would only allow sanitized inputs, thus shielding your application from SQL injection.
This question already has answers here:
How to escape strings in SQL Server using PHP?
(14 answers)
Closed 9 years ago.
I can sanitize and validate my input as much as possible but that definitely doesn't cover everything and if I scrub hard enough, thoroughly enough, I will completely wipe away my input.
I realize there are a lot of posts out there about this topic but it seems like they always go back to PDO or Mysql (yes - even if someone posts about SQL Server, half the answers they receive suggest mysql_real_escape_string - crazy world). I cannot use either. Even as I type and the little "similar questions" appear on the right of my screen, I keep clicking on various links and nothing fully answers my question.
I am using SQL Server. I am using PHP 5.2.4. I cannot use PDO (because...? my boss said 'no' and that's enough reason).
Is there a way I could write a safe way to prepare my own query statements?
In the past, I have tried to build a statement like this in the PHP. (where $input_* variables are some form of user input or I pulled them out of something)
$query = "
declare #varID int
declare #var1 int
declare #var2 varchar(100)
set #varID = cast('$input_ID' as int)
set #var1 = cast('$input_var1' as int)
set #var2 = cast('$input_var2' as varchar(100))
update table_name_goes_here
set var1 = #var1,
var2 = #var2
where ID = #varID;
";
# $query is then executed
but that can be vulnerable, too... obviously.... And the last thing I do is remove all necessary punctuation (sometimes I know they will have no reason to use certain characters)
But there has to be some other option... right? And mssql_bind only works for stored procedures, which is a definite option but I'm not sure if I want to volunteer to expand my responsibilities to include maintenance in the actual database by making insert/update procedures.
I would say that "because the boss said 'no'" is a terrible reason. Tell him (her?) that he is wrong. I know little of PHP, but regardless of the language, the only foolproof way to prevent injection is through paramaterized queries, or stored procedures. If the only way to do that in PHP is to use PDO, then use PDO.
Here is your reasoning for using PDO: https://www.owasp.org/index.php/SQL_Injection_Prevention_Cheat_Sheet
http://msdn.microsoft.com/en-us/magazine/cc163917.aspx
And why is there any SQL in the code at all? It is much easier to maintain if it is in the database, generally in the form of stored procedures.
You haven't answered the question "How do you intent to talk to the MS SQL database if PDO isn't allowed", but I assume there are the mssql_* functions to be used.
These do not have an escaping function readymade, but it seems they offer you to use prepared statements - which will do the job.
Otherwise you would have the security-relevant task to create an escaping function yourself. The character replacement is not really complicated when you first look at it, and you might be lucky to only have to cover your exact use case with a defined encoding. So this might really be as easy as looking up in the MSSQL manual which characters in a string are not allowed as a simple character, and how to escape them.
Be alerted though that you might miss edge cases, and if you can avoid it, I'd rather use the prepared statement feature.
Update: I misread the manual, mssql_execute() only calls stored procedures, not prepared statements. Can't you store procedures? Would be an easy way out. But I'd like to know how you are supposed to talk to the database anyways.
Update2: I found a link in a comment on php.net for mssql_bind pointing back to an SO answer about escaping: How to escape strings in SQL Server using PHP?
This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
Best way to stop SQL Injection in PHP
I'm currently designing and building my own content management system and my main worry is someone using an sql injection on my forms. I have a decent amount of security to get into my CMS but on the front end of the site I'll have a subscriber form and contact for which will link to my mySql database.
What tend to be the conventional PHP methods for preventing sql injection on forms?
any help would be great, thanks.
There's a function mysql_real_escape_string() which is generally seen as a basic requirement for preventing this kind of attack.
Don't forget to also set a character encoding. I'd suggest UTF-8. And make sure your HTML uses the same encoding as your database/tables.
Probably one of the best solutions is to filter all incoming data with function mysql_real_escape_string
To protected yourself against SQL Injection you need to sanitize input and use parameter queries.
I'm not sure about PHP, but I think you have something like prepared statements. You should search and read a little about it.
Also, that is not the only problem you should care about, please (!!!) take a look at https://www.owasp.org/index.php/Main_Page
This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
Best way to stop SQL Injection in PHP
I would like to know which functions is best to use to prevent MySQL injections
There are plenny of functions I can use to prevent sql injections, such as:
mysql_real_escape_string
mysqli_real_escape_string
addslashes
casting values (intval etc...) for numbers
htmlentities with ENT_QUOTES
or simply remove the ' or "
I want to standardize my code using the best and faster anti-SQL-injections method and I would like to know which one should I use for high traffic sites.
You shouldn't use htmlentities for saving data to a database, addslashes isn't 100% secured (some character sets can still make it vulnerable), using mysql_ or mysqli_ is dependent on the driver you're using and not interchangable. Basically, its not a matter of speed or performance - the only right thing to do is using the escape function that comes with your driver (pdo::escape or mysql[I]_real_escape_string) for strings and casting integers/floats to their correct type.
To give you a simple answer, you can use mysql_real_escape_string
http://www.tizag.com/mysqlTutorial/mysql-php-sql-injection.php
http://www.osempire.com/php-injection-attacks-guide
To give you a better answer, try reading Theo's answer in How can I prevent SQL injection in PHP?
I assume you are in the middle of the project already. Once you finish, I suggest learning a new framework like CodeIgniter, Yii and CakePHP to speed up development.
This question already has answers here:
How can I sanitize user input with PHP?
(16 answers)
Closed 9 years ago.
I'm very new to PHP, basically I'm trying to create a commenting system for my site. I have the following function:
$input = $_POST['comment'];
function cleanUserInput($input) {
$input = mysql_real_escape_string($input);
$input = htmlentities($input);
return $input; }
So the question is, is mysql_real_escape_string alone sufficient to prevent sql injection? and is htmlentities() sufficient to prevent scripts, html and styles entered by the user from having actual effect and just be shown as text?
Or do I need to add more to my function to make the input really harmless?
mysql_real_escape_string is NOT enough. You must also take into account how you structure your query. Consider the following simple login script:
$username = mysql_real_escape_string($_GET['username']);
$password = mysql_real_escape_string($_GET['password']);
$sql = "SELECT * FROM users WHERE username = $username AND password = $password";
without quotes around $username and $password, injection is STILL possible. (Consider a username = test; DROP TABLE users; --. Bye bye data! :(
mysql_real_escape_string is sufficient from a sanitization point IF you structure your query correctly. For a properly constructed query, this works fine.
A better question is "what are you trying to prevent?" You should also be aware of XSS (cross-site-scripting) stored and reflected. If you are storing input from users in your database and that data is rendered in the browser, you'll want to strip out <script> tags at the very least.
There are many filters and code available on line for this depending on your language. If you use Rails or CodeIgniter, it's done for you.
As far as this type of security is concerned, I recommend using the following:
download and install damn vulnerable web app. its an application designed to teach the ins and outs of web hacking (php-based)
always try to submit characters of a different charset
always try to submit the NULL byte
avoid passing too many parameters in the querystring (it can give away your data structure)
watch your logs
download burpsuite - you'll never look at a website the same way again
watch being chatty. mysql error messages are great for debugging, but they give away a ton of information - often times they reveal the whole query!
bottom line - if it comes from the user, it can't be trusted!
Both functions do solve a major part of the security issues regarding injections of any kind and some more problems, however, the amount of security bugs that your application can have is staggering.
If you are a security freak, then you're in for major problems, but you'll be allright by starting on checking Chris Shiftlett's website, who is one of the major authorities on PHP security around the world.
And finally you can check the OWASP web, and their Top Ten Project, where they keep track on the most common security threats and keep updates on hw to fight them,
Hope I can be of assistance.
If you're using PHP 5.2 or newer, you can use the built-in input sanitization.
For example:
$input = filter_input(INPUT_POST, 'comment', FILTER_SANITIZE_STRING);
References:
filter_input
Available filters