PHP issue [message #438943] |
Fri, 05 November 2010 16:24 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
I started learning PHP about 2 weeks ago and have gotten as far as small database things..
I decided as a first project I would make some sort of system for my school library, however I can't see what is wrong with this code. The page shows up blank (I had a "or die()" after the mysql_connect function) with no info on it.
<?php
$var = $_POST['bookid'];
if(isset($var)) {
$con = mysql_connect("localhost","root","1234");
mysql_select_db("library");
$bookinfo = mysql_query("SELECT * FROM books WHERE bookid = $_POST['bookid']");
while($row = mysql_fetch_array($bookinfo))
{
echo $row['bookid'] . $row['id'];
}
}
echo "Test echo";
?>
The form sending the POST data sends <input type="text" name="bookid"/>
I am able to connect to the mysql db as I have tried with another page (which simply shows text on it from a db).
The "Test echo" does not show.
Anybody able to shed some light on this?
|
|
|
Re: PHP issue [message #438944 is a reply to message #438943] |
Fri, 05 November 2010 16:46 |
|
Omar007
Messages: 1711 Registered: December 2007 Location: Amsterdam
Karma: 0
|
General (1 Star) |
|
|
I did do PHP but I think it has become a bit rusty
My SQL is pretty good though
Try this.
<?php
$var = $_POST['bookid'];
if(isset($var)) {
$con = mysql_connect("localhost","root","1234");
mysql_select_db("library");
$bookinfo = mysql_query("SELECT * FROM books WHERE bookid='$var';");
while($row = mysql_fetch_array($bookinfo))
{
echo $row['bookid'] . "-" . $row['id'];
}
}
echo "Test echo";
?>
$row['id'] -> Do you have both 'bookid' and 'id?? :S'
[Updated on: Fri, 05 November 2010 17:13] Report message to a moderator
|
|
|
|
|
Re: PHP issue [message #438948 is a reply to message #438943] |
Fri, 05 November 2010 17:18 |
|
Crimson
Messages: 7429 Registered: February 2003 Location: Phoenix, AZ
Karma: 0
|
General (5 Stars) ADMINISTRATOR |
|
|
The problem was that you need to put curly braces around an array reference when it's in a string like that.
"SELECT * FROM books WHERE bookid = {$_POST['bookid']}"
The curly braces tell the PHP parser where the variable starts and ends because when you start adding symbols, it gets confused.
The $var way works, too, but it creates messier, harder-to-read code.
(Of course, since you're a beginner, I won't point out the XSS flaws.)
I'm the bawss.
|
|
|
Re: PHP issue [message #438964 is a reply to message #438943] |
Sat, 06 November 2010 03:03 |
|
danpaul88
Messages: 5795 Registered: June 2004 Location: England
Karma: 0
|
General (5 Stars) |
|
|
Actually I disagree Crimson, protecting database inputs against injection attacks is something you should learn as early as possible so that it becomes second nature when coding in PHP.
cnc95fan, consider what would happen if I submitted your search form with the following;
$_POST['bookid'] = '0; DROP TABLE books';
Based on your current code, this would result in the following query being run;
SELECT * FROM books WHERE bookid=0; DROP TABLE books;
Obviously this is a huge security problem, however there is a simple solution: Run anything from POST or GET which will go into a database through functions to verify it is valid. For numerical (int, float) values use something like;
function prepare_db_number($number)
{
if ( is_numeric($number) )
{
return $number;
}
return 0;
}
This is an extremely simple function which checks the input is numeric and returns it if it is. If it is NOT numeric it returns 0, preventing any SQL injection attacks through that variable.
For strings you can use something a bit like this;
function prepare_db_string( $string, $encode_html_entities = FALSE )
{
// If magic quotes are enabled then strip the existing slashes from the string first
if(get_magic_quotes_gpc())
$result = stripslashes(trim($string));
else
$result = trim($string);
// Encode HTML entities if required
if ( $encode_html_entities === TRUE )
$result = htmlentities($result);
// Return MySQL safe string
return mysql_real_escape_string($result);
}
This function does several things - firstly it trims whitespace from around the input string (ie: spaces or tabs before or after any actual content) and, if magic quotes are enabled, it removes the slashes (otherwise you would end up with some things double escaped). Secondly, it optionally converts special characters to their HTML entities, this is useful if you know the string is going to be output directly to HTML and you need to ensure there are no HTML tags inside of it, for example a forum post.
Finally it uses mysql_real_escape_string to escape any character sequences which could be used to break out of the string and inject an additional query.
[Updated on: Sat, 06 November 2010 03:04] Report message to a moderator
|
|
|
|
|
Re: PHP issue [message #439272 is a reply to message #438943] |
Thu, 11 November 2010 12:15 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
$con = mysql_connect("localhost","root","1234");
mysql_select_db("test");
$regnum = rand(100000,999999);
mysql_query("INSERT INTO USERS ('id','user','password') VALUES ('$regnum','$_POST['user']','$_POST['pass']')");
mysql_close($con);
echo "test";
I can't see anything in there that would cause this to not work.. any ideas anyone?
|
|
|
Re: PHP issue [message #439274 is a reply to message #439272] |
Thu, 11 November 2010 12:37 |
|
danpaul88
Messages: 5795 Registered: June 2004 Location: England
Karma: 0
|
General (5 Stars) |
|
|
cnc95fan wrote on Thu, 11 November 2010 19:15 |
mysql_query("INSERT INTO USERS ('id','user','password') VALUES ('$regnum','$_POST['user']','$_POST['pass']')");
|
You can't use things like $_POST['pass'] directly in a string, you have to either put curly braces around the variables;
mysql_query("INSERT INTO USERS ('id','user','password') VALUES ('{$regnum}','{$_POST['user']}','{$_POST['pass']}')");
Or concatenate them with the string
mysql_query("INSERT INTO USERS ('id','user','password') VALUES ('".$regnum."','".$_POST['user']."','".$_POST['pass']."')");
My personal preference is the second method (concatenation), but it really doesnt matter which you use. The first variable ($regnum) is actually OK without these, but its good practice to follow the same method for all variables as it makes it clear what you were intending to do.
For more information;
http://www.php.net/manual/en/language.types.string.php#language.types.string.par sing
[Updated on: Thu, 11 November 2010 12:42] Report message to a moderator
|
|
|
Re: PHP issue [message #439275 is a reply to message #438943] |
Thu, 11 November 2010 12:43 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
Yeah that seems to have done the trick; on some other registration forms I was messing about with I have never had to do that before though, I always seemed to have gotten away with '$_POST['x']' :s
|
|
|
Re: PHP issue [message #439276 is a reply to message #438943] |
Thu, 11 November 2010 12:48 |
|
danpaul88
Messages: 5795 Registered: June 2004 Location: England
Karma: 0
|
General (5 Stars) |
|
|
$_POST[x] would have worked, $_POST['x'] wouldn't have done, unless you used one of the two methods outlined above. However it is always good practice to use quotes around array indexes which are strings, otherwise you could find that a constant you define in one place screws up a load of other scripts which used the name of that constant as an unquoted string array index.
EDIT;
Interestingly, I notice Crimson already mentioned using curly braces around array indexes in strings about 4 or 5 posts into this topic...
[Updated on: Thu, 11 November 2010 12:50] Report message to a moderator
|
|
|
|
|
Re: PHP issue [message #439497 is a reply to message #438943] |
Sun, 14 November 2010 12:40 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
if($_POST['user'] != "" && $_POST['pwd'] != "")
{
$con = mysql_connect("localhost","root","1234");
mysql_select_db("test");
$regnum = rand(100000,999999);
$sqlone = mysql_query("SELECT * FROM users");
$sqlfetch = mysql_fetch_array($sqlone);
while($sqlone['id'] == $regnum)
{
$regnum = rand(100000,9999999);
}
$regtitle = mysql_query("INSERT INTO titles (id) VALUES ('".$regnum."')");
$reguser = mysql_query("INSERT INTO users (id,login,password) VALUES ('".$regnum."','".$_POST['user']."','".$_POST['pwd']."')");
if($reguser)
{
header("Location: index.php");
exit;
}
else
{
echo "SQL QUERY NOT COMPLETED.";
}
mysql_close($con);
}
else
{
header("Location: register.php?login=failed&cause=".urlencode('Insert all values please'));
exit;
}
This one has puzzled me. I have messed about commenting out parts to see where the problem is but I cannot find it.
I'm aware that the while loop is probably not the best way to go about doing something like that but this is just a small project I'm doing to learn PHP.. Any ideas?
Edit: It goes to the else "SQL QUERY NOT COMPLETED"
[Updated on: Sun, 14 November 2010 14:21] Report message to a moderator
|
|
|
|
Re: PHP issue [message #439636 is a reply to message #438943] |
Tue, 16 November 2010 15:09 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
It will be the weekend before I get at the box again.
Out of curiosity though, how do functions work?
What does the return 0 in this function you wrote above do?
function prepare_db_number($number)
{
if ( is_numeric($number) )
{
return $number;
}
return 0;
}
|
|
|
|
|
|
Re: PHP issue [message #439799 is a reply to message #438943] |
Sat, 20 November 2010 13:51 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
I have yet another really weird issue, I've tried rewriting this thing about 4 times.
Basically, inside a DB there is for arguments sake, 3 tables.
The first table is an index, which contains 2 columns, id (as in some id in the URL) and a name.
The page is supposed to select from the index where $_GET['id'] is equal to id in the index, then look up the name in the same row. After getting the name it is then supposed to add on a postfix (such as x or y, so where the name would be renegade, the variable I assigned to the next task would be renegadex).
$pid = $_GET['id'];
$index = mysql_query("SELECT * FROM index where id = '".$pid."'") or die(mysql_error());
$row = mysql_fetch_array($index);
$thisvar = $row['name'];
$x = "x";
$query = mysql_query("SELECT * FROM ".$thisvar . $x." where uid = '".$_SESSION['id']."'") or die(mysql_error());
$row1 = mysql_fetch_array($query);
$uid = $row1['id'];
echo $uid;
The echo returns nothing so I'm assuming that one of the mysql_querys is failing somewhere...
|
|
|
|
Re: PHP issue [message #439809 is a reply to message #438943] |
Sat, 20 November 2010 16:07 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
I rewrote this 4 times, and in between made adjustments to them so I tried the $row['name'] . $x; aswell. I didn't test to see if it was working in that sense but I ended up changing $row['name'] var to the actual table name (excluding the $x).
The table does indeed exist
|
|
|
Re: PHP issue [message #439853 is a reply to message #438943] |
Sun, 21 November 2010 15:25 |
|
danpaul88
Messages: 5795 Registered: June 2004 Location: England
Karma: 0
|
General (5 Stars) |
|
|
In your query your checking if uid is equal to something, but then you try to echo id, do you have both a uid and id field in that table?
You might want to do something like this to check what results your actually getting back;
$query = mysql_query("SELECT * FROM table"); // Query here
echo "Query returned ".mysql_num_rows($query)." results;<br/><pre>"; // Output number of results
while ( $result = mysql_fetch_assoc($query) ) // Iterate through each result row
{
print_r($result); // Dump contents of current result row
echo "<br/><br/>"; // Leave a gap between each result row
}
echo "</pre><br/>End of results<br/>";
mysql_data_seek($query,0); // Reset results pointer
FYI: The mysql_data_seek() call at the end just tells PHP to set the results pointer back to the first row so you can still process the results in the code which follows that block of code.
[Updated on: Sun, 21 November 2010 15:28] Report message to a moderator
|
|
|
Re: PHP issue [message #439858 is a reply to message #438943] |
Sun, 21 November 2010 16:14 |
cnc95fan
Messages: 1261 Registered: July 2007
Karma: 0
|
General (1 Star) |
|
|
Thanks dp88;
Seemed to have fixed it. Just curious, I took up your suggestion there on learning security from the begining, so I'm inserting data using htmlspecialchars(), what would be the best way of printing that data on a page without those characters appearing (& etc).
Also is there any sites you know of that talk about security, as w3schools do not seem to
|
|
|