I want to add an edit button for a script called spiral url, but the problem is that I can't get the URL id. This is what I've tried:
/** get url id **/
$id = isset($_GET['id']) ? $_GET['id'] : '';
#mysql_query("UPDATE short_urls SET long_url = 'test' WHERE url_id = '".$id."' LIMIT 1");
What am I doing wrong?
Also I emailed the author and his response:
"I recommend you post on Stackoverflow - https://stackoverflow.com/.
I would love to help you but I don't see what you are doing wrong. I'm still learning PHP as well."
You're wide open to SQL injection attacks.
You're supressing errors with the # operator. NEVER suppress errors
You're not checking the return value of mysql_query(), which returns a boolean FALSE on failure.
Scrap that code and use this:
if (!isset($_GET['id'])) {
die("missing query parameter");
}
$id = intval($_GET['id']);
if ($id === '') {
die("Invalid query parameter");
}
$sql = "UPDATE short_urls SET long_url = 'test' WHERE url_id=$id LIMIT 1";
$result = mysql_query($sql);
if ($result === FALSE) {
die("Mysql error: " . mysql_error() . $sql);
}
Note that I'm assuming that the id parameter is numeric. If it's not, then remove the intval() stuff.
Make sure the value of $_GET['id'] actually has a value. Your URL will look something like http://myurl.com/index.phtml?id=yourvalue. You can do this by doing a:
print "id=".$_GET['id'];
Also, whenever doing a query, please be sure to escape any and all variables that can be manipulated by the user. Without doing this, you're opening yourself up to SQL injection attacks.
mysql_real_escape_string - http://php.net/manual/en/function.mysql-real-escape-string.php
#mysql_query("UPDATE short_urls SET long_url = 'test' WHERE url_id = '".mysql_real_escape_string($id)."' LIMIT 1");
If the url is like this: domain.com/something.php?id=65
$_GET['id'] should be equal to 65
if there is no id there then when you try to access $_GET['id'] you will get an error.
Also try removing the # symbol (that suppresses PHP warning).
And you are waaaay open to bobby-tables
Also (side note), get a new developer who knows what they are doing ;-)
Have you checked the url
http://www.somewebsite.com?id=56&other_car=test
specifically for the "?" after the end of the url and also check all the parts are broken up by the ampersand.
failing that you can view all of your available get array variables by
print_r($_GET);
Related
I am checking if the ID input is a not string and not null. Here is the code:
$id = $_POST["id"];
if(!is_string($id) && !empty($id)) {
$delete = mysqli_query($connect,"DELETE from users WHERE ID=$id");
$_SESSION["succMsg"] = "User have been successfully removed";
Header("Location:login_update.php");
} else {
$_SESSION["succMsg"] = "Unable to execute the query.";
Header("Location:login_update.php");
}
It somehow decides to not accept the query that I run. And I have no trouble when I remove the if statement. Though I want to check beforehand.
The issue is, that $_POST["id"]; always is a string - indeed all elements of the $_POST-array are - so is_string($id) of course returns true. What you really mean to do is to check, if it only consists of digits! ctype_digit($id) does this for example.
If your purpose is to migitate injection attacks, the easiest would probably be to cast it to an integer:
$id = (int) $_POST["id"];
Then it should work as you expect. The is_string($id) is of course unnecessary now. The is_empty() check should be performed before this assignment now (directly on $_POST["id"]). Maybe isset() is even more appropriate here, this eliminates for example a warning if id wasn't set as a parameter:
if (isset($_POST["id"])) {
$id = (int) $_POST["id"];
// Do your query....
}
I have the following PHP code where I want to return the number of rows based on the previous SQL statement, however, $num doesn't doesn't seem to be returning anything.
$ipAddress = $_SERVER['REMOTE_ADDR'];
if ($result = $mysqli->query("SELECT * FROM whovisit WHERE ipAddress = ".$ipAddress."")) {
$num = $result->num_rows;
}
echo $num; // <-- not showing up on my page
if ($num > 0) {
$sqlupdate = $mysqli->query("UPDATE whovisit SET visitCount = visitCount + 1 WHERE ipAddress = ".$ipaddress."");
}
else {
$sqlupdate = $mysqli->query("INSERT INTO whovisit values ('".$_SERVER['REMOTE_ADDR']."', '1')");
}
Any ideas? Thanks
Ensure that you have a $ infront of ipaddress
$ipaddress = $_SERVER['REMOTE_ADDR'];
As the IP address is a string it should be put in single quotes.
if ($result = $mysqli->query("SELECT * FROM whovisit WHERE ipAddress = '".$ipAddress."';")) {
$num = $result->num_rows;
}
If you are unsure if the query is running correctly you could also add an else to the above if statment and output any mysql error messages.
}else{
echo "QueryError: ".$mysqli->error
}
Similar post:
php switching to mysqli: num_rows issue
In PHP v 5.2 mysqli::num_rows is not set before fetching data rows from the query result.
If you get nothing on the page, this means $num must not be being set. Given the code you have, that would mean the if block is not being executed - i.e. $result is a falsey value. Which means your query is failing.
And unfortunately this one's pretty easy if you examine the generated query. Following what happens step-by-step, we see you're injecting the contents of the server variable REMOTE_ADDR, which is presumably going to be an IPv4 address in a dotted-decimal format, into the query string. So you'll have a SQL statement like, which fails to parse at the second .:
SELECT * FROM whovisit WHERE ipAddress = 127.0.0.94
Oops.
Since the IP address is a string, you need to enclose it in single quotes:
"SELECT * FROM whovisit WHERE ipAddress = '".$ipAddress."'"
Which will result in the queries in the following form:
SELECT * FROM whovisit WHERE ipAddress = '127.0.0.94'
Or better yet, use a parameterized query and you don't have to worry about quoting and escaping. $_SERVER['REMOTE_ADDR'] is probably relatively safe as far as SQL injection attacks go, but 1)it's easier to use parameters than a concatenated string, and 2)you never truly can trust a value you didn't generate yourself.
I am using php and sql to check user information from the database. I need to check if the username and password is correct and the account is active. I have this sql query, but it does not work. What is the method to do it?
SELECT * FROM foo WHERE (name='foo' AND password='foo') AND active=1
for me
SELECT * FROM foo WHERE (name="foo" AND password="foo") AND active=1
should be same as
SELECT * FROM foo WHERE name="foo" AND password="foo" AND active=1
the above query assumes that field active is of family type int In case its varchar or char you r query should be like this
SELECT * FROM foo WHERE name="foo" AND password="foo" AND active='1'
and the query should work and i assume you are taking care of SQL injections from php
Where you say, "When I remove AND active=1 part, it works fine. Any ideas?"
Try changing it to AND active<>1 to see if the issue lies in that field. It's possible 'active' may be null or some other value. Try outputting the value (try var_dump($var) in PHP) to see what is returned for the 'active' field. If the value is 0, a blanck string, or null, then you've isolated your problem.
The query looks correct (assuming columns name, password, and active exist in table foo), but if you're using it in PHP you might be running into trouble with the double quotes if they're inside a string you're declaring. You might need to escape them or use single quotes.
My query returns 0 row and I am sure that I have that fields in the database and typing the correct information. When I remove AND active=1 part, it works fine. Any ideas?
Yes.
The idea is very simple. Just check if a record with name='foo' and password='foo' has active=1. Then correct mistake and your data
Hint: a programmer cannot be sure when the logic says he is wrong.
First of all, use mysql_real_escape_string() or a PDO method to escape your input. You do not want people messing around in your database.
A simplified version of what I normally do is
SELECT main.id,
main.isActive,
(SELECT count(sub.id)
FROM users AS sub
WHERE sub.id = main.id
AND sub.credential = 'md5password'
LIMIT 1
) AS credentialMatches
FROM users AS main
WHERE main.identity = 'username'
Grab your result:
$result = mysql_query($sql);
$data = array();
if (false !== $result) {
while ($row = mysql_fetch_assoc($result)) {
$data[] = $row;
}
}
Handle your result:
if (count($data) < 1) {
// username not found
} else if (count($data) > 1) {
// multiple rows with the same username, bad thing
} else {
$row = $data[0]
if (false === (boolean) $row['isActive']) {
// user not active
} else if (true === (boolean) $row['credentialMatches']) {
// SUCCESS
// valid user and credential
}
}
Also note: ALWAYS store password at least as an MD5 hash like so WHERE credential = MD5('password'). Same when you are inserting: SET credential = MD5('password'). This way, when someone else will ever read you database, user passwords won't be revealed so easily.
An even better is to add an additional salt to hash, but that might be going to far for now.
You could debug your sql like this in php:
$sql = "SELECT * FROM foo WHERE (name='foo' AND password='foo') AND active=1";
$result = mysql_query($sql) or die (mysql_error());
This "or die (mysql_error())" will give you the exact error of that query, maybe the DB isn't selected if that happened use mysql?query($sql, $db)...
Hope it helps
I am trying to delete a record in my db based on the unique id ($id). Is there something wrong with this code? Probably a simple one for you php pro's.
function delAccount(){
mysql_query("DELETE FROM accounts WHERE id=".$id."LIMIT 1");
}
I get a :
Fatal error: Can't use function return value in write context in
/home/content/53/7311353/html/cca/accounts/include/processAct.php on line 15
My Class that I have powering everything:
class Accounts
{
function Accounts(){
if (isset($_POST['addacct'])){
$this->addAccount();
}elseif(isset($_POST['editacct'])){
$this->editAccount();
}elseif(isset($_POST['delacct'])){
$this->delAccount();
}else{
// redirect if loaded without a POST value set
header("Location: ../index.php?o=illegal&t=nodata");
}
}
You should, first of all, put a space between ".$id." and LIMIT so:
mysql_query("DELETE FROM accounts WHERE id=".$id." LIMIT 1");
Secondly, the $id is NOT available within this function by default. Either do this:
function delAccount($id) {
mysql_query("DELETE FROM accounts WHERE id=".$id." LIMIT 1");
}
and use delAccount($id_parameter); in your script to send the ID along with the function. Or try this:
function delAccount() {
global $id;
mysql_query("DELETE FROM accounts WHERE id=".$id." LIMIT 1");
}
then you can call this function after you set the value of $id somewhere else in your code.
First: is the value for $id actually an id in the database? Second you need a space before "LIMIT", ie:
" LIMIT 1".
Are you sure $id is set?
If $id should be sent to the function as an argument, try this:
function delAccount($id) {
mysql_query("DELETE FROM accounts WHERE id=" . $id . " LIMIT 1");
}
EDIT: You missed a space character between the ID and the LIMIT.
Added some small improvements to the form of the query string:
function delAccount($id) {
mysql_query("DELETE FROM `accounts` WHERE `id` = " . $id . " LIMIT 1");
}
EDIT:
The error you get doesn't come from MySQL itself. Have you checked the returned value. It might return another error, or the returned value might be correct, but used in an erroneous way in later code.
Your error is from the PHP compiler. Are you doing something like this on line 15:
if (delAccount(...) = false) { ... }
? If so, change to ==.
Some hints on how to debug stuff like this.
If you suspect something is wrong, the first thing to do is to output the generated query. Like so:
$query = "DELETE FROM accounts WHERE id=".$id."LIMIT 1";
echo $query; // for debugging
That will show you that at least one thing is wrong with your query: You have a space missing before LIMIT.
mysql_query() returns false if it encounters an error. You can check for that, and output it using mysql_error(). Like so:
$result = mysql_query($query);
if(!$result) trigger_error("Database error!: ".mysql_error());
If $id comes from outside, like the $_GET array, make sure you have tested whether it is an integer before using it in a query to avoid SQL injection.
Sorry if this question may seem easy to some but i cannot seem to figure it out. i was told that i could come here because the guys here are very helpful. i am having problem with the following code. when the uid is call into the url for example page.php?uid=5 i get "some code" if i do page.php?uid=letters i get redirected to page.php?uid=1. that works fine. but if a user should enter page.php?uid=1letters i get this error..Unknown column '1gh' in 'where clause'
Warning: mysql_fetch_array() expects parameter 1 to be resource, boolean given in C:\wamp\www\page.php on line 173.
i only get this error if the user enters unwanted characters at the end of get url id. How can i prevent this from happen how can i have it redirect to page.php?uid=1... see code below
$id = mysql_real_escape_string(#$_GET['uid']);
$query = mysql_query("SELECT user.* FROM user WHERE id = '$id'");
if ((mysql_num_rows($query)==0)) {
header("location:page.php?uid=1");
die();
}
else {
while($rows = mysql_fetch_array($query)){
$foo = $row['foo'];
echo "some code";
mysql_query returns false on error. You should check what it returns:
$query = "SELECT user.* FROM user WHERE id = '$id'"
$result = mysql_query($query);
if ($result === false) {
die($query.'<br/>'.mysql_error());
}
Then you can understand why it failed. I've added the query to the die() statement so you can try the query manually as well.
The error given is unknown column of a string, which suggests you are not enclosing the value with single quotes in the SQL query, even though the code in the question does.
In production you should be taking all steps you can to ensure errors are handled gracefully. In this case you will probably want the same behaviour as not finding a user:
header("location:page.php?uid=1");