My query below updates a record using variables to identify the data in the DB. I think my syntax is correct although it might be wrong. Also, I am absolutely sure that the variables have legitimate values in them. Why won't this query work?
UPDATE `databasename`.`".$tablename."` SET `stock` = '".$f."' WHERE `myerspark`.`item_id` ='".$g."' LIMIT 1
Thanks guys. Tom, yes I have tried that and it works fine. But it is frustrating because I echo all three variables at the end of the script and they all display legitimate values.
Hamish, how do I view these errors?
Jon_Darkstar, these variables are assigned in previous lines of code. Here is my entire code block:
//variables $f, $g, and $tablename assigned from POST variables in previous lines
mysql_select_db($database_Yoforia, $Yoforia);
mysql_query("UPDATE `yoforiainventory`.`".$tablename."` SET `stock` = '".$f."' WHERE `".$tablename."`.`item_id` ='".$g."' LIMIT 1 ");
mysql_close($Yoforia);
echo ($f);
echo ($tablename);
echo ($g);
Again, when i echo these variables, they all come out with good values.
I'm kind of confused what belongs to SQL, what belongs to PHP, where that string comes from, etc. What you have might be fine (if there is a double quote in front and end that i dont see.
I'd probably write it like this:
$sql = "UPDATE databasename.$tablename SET stock = '$f' WHERE myerspark.item_id = '$g' LIMIT 1"
$res = mysql_query($sql, $conn).....
you can backtick more stuff (and/or do mysql_real_escape) for 'extra safety;, but that covers the idea.
What is myerspark? i dont see how it relates to the query, that is probably you're real meaningful error, whether there is a syntax error or not. If myerspark is a seperate table from tablename then you've got an issue here, maybe a JOIN you ought to have?
Related
I am trying to pull user data from a Cart66 table I have and put it into a shortcode in wordpress. $account is an integer pulled from session data. The code below returns nothing.
$account =Cart66Session::get(Cart66AccountId);
global $wpdb;
$fname=$wpdb->get_results("SELECT * FROM 'vfp_cart66_accounts' WHERE id = '$account', ARRAY_N");
foreach ($fname AS $row)
{
echo $row;
}
This returns "Array"
return $fname;
Ok firstly, maybe I am the only one who saw this, and it could be the source of your entire problem, but you have a misplaced double quote, at the end of your SQL line, which should live at the end of the actual SQL string, not after the requested return type:
// at the end of this line you have: '$account', ARRAY_N");
// this should be changed to: '$account'", ARRAY_N);
$fname=$wpdb->get_results("SELECT * FROM 'vfp_cart66_accounts' WHERE id = '$account', ARRAY_N");
Even the first person who answered the question did not correct you, so I am assuming he didn't see it either. Secondly, using single quotes (') to escape a table name is invalid. If it is quoted at all, use backticks (`). Single quotes indicate a string, not an database, table, or field, all three of which should only be quoted with backticks (except on utility queries like SHOW). Use this instead:
select * from `vfp_cart66_accounts` where id = '$account'
Thirdly, as your commenters point out, you could be vulnerable to SQL Injection. Make sure to use the tools that WP gives you, and do this, or similar, instead:
$fname = $wpdb->get_results(
$wpdb->prepare(
'select * from `vfp_cart66_accounts` where id = %d',
$account
),
ARRAY_N
);
Lastly, you are requesting an array from the DB, but you are trying to echo it as if it were a scalar value. This explains why printing the value of $row yields "Array". When you convert an array() to a string, by default, you get "Array", since arrays can be complex data that may not be beautifully converted to a string. As a correction of this, you can do one of two things.
First, if you need the entire resulting array that represents the entire row of the table, then you can simply change your echo code to this:
foreach ($fname as $row) {
// print the fname of the row
echo $row['fname'];
// do the other stuff you need to do with $row
...
}
OR, if you simply need the fname field out of that table, for the given id, you could use a different $wpdb function, called $wpdb->get_var(), which gets one specific field from the first entry of the resulting data from the database, coupled with some minor SQL changes:
// use the get_var() function instead
$fname = $wpdb->get_var(
$wpdb->prepare(
// 1) change the 'fields' of your sql to only get the `fname` field
// 2) also add limit 1, to reduce load by only asking for one row
// NOTE: #2 is optional really, because WP does this for you when using get_var,
// but is good practice to only ask for what you need. so do it
'select fname from `vfp_cart66_accounts` where id = %d limit 1',
$account
),
ARRAY_N
);
echo $fname; // print the value of field fname from vfp_cart66_accounts for id $account
Now. I don't have specific knowledge of Cart66. That being said, if the above changes to PHP, WordPress, and SQL syntax do not yield results, then you are probably having one of the following other problems instead:
there is a different PHP error somewhere in the code, causing this to never run
this code is never called, and thus it is never executed
you misspelled the table name, which is causing an SQL error
the table exists, but does not have a field named id
both table and field exist, but there are no entries in the table
some other random thing that is not coming to mind
DEBUG #1
For #1, you could try turning on error_reporting() and display_errors early in the code execution. In a normal, run of the mill PHP script you could add the following two lines somewhere early in the code:
error_reporting(E_ALL);
ini_set('display_errors', 1);
However, you are using WordPress, so you will need to do something like this in your wp-config.php file:
// find the line that looks like this and comment it out
// define('WP_DEBUG', false);
// add these two lines directly below it
define('WP_DEBUG', true);
ini_set('display_errors', 1);
DEBUG #2
Make sure your code is running. Don't be afraid to throw a die() statement directly above it, to make sure it is running. Something like this:
// add a die() before everything
die('I am running. Awesome!');
// revised code
$account = Cart66Session::get(Cart66AccountId);
global $wpdb;
$fname = $wpdb->get_var(
$wpdb->prepare(
'select fname from `vfp_cart66_accounts` where id = %d limit 1',
$account
),
ARRAY_N
);
echo $fname;
DEBUG #3
To debug #3, you need either access to a commandline tool for MySQL or some type of GUI interface like phpMyAdmin, so that you can run a query directly from the database. Here is the query you should run:
show tables like 'vfp_cart66_%';
This is an example of one of the only places in SQL that you should ever quote a table name in single quotes. Running this will yield a list of all the tables that start with vfp_cart66_. If you get no results, then your table name is wrong. If your results do not include vfp_cart66_accounts, then your table name is wrong. If you see vfp_cart66_accounts, you are good to go.
DEBUG #4
This one will need to be run directly from the DB or through something like phpMyAdmin also. You are trying to make sure you have the correct field name. The way you do that is:
show create table `vfp_cart66_accounts`;
Assumedly, the field you are calling id would be the auto_incremented field in the table. Thus you are looking for a line, similar to this one:
`id` bigint(20) NOT NULL AUTO_INCREMENT,
Make sure that the line that has AUTO_INCREMENT on it, begins with:
`id`
If it does not, and the name is something else other than id, then you probably have the wrong field name.
DEBUG #5
Make sure you actually have data to display. From your mysql console or phpMyAdmin, run:
select * from `vfp_cart66_accounts` limit 1;
If you bet any results, then you have data, and you are good.
DEBUG #3 - #5 (alternate methods)
Another option you have is to dump the $wpdb object, directly after you run the query, because it contains the last error you received from MySQL. You can do this like so:
$fname = $wpdb->get_var(
$wpdb->prepare(
'select fname from `vfp_cart66_accounts` where id = %d limit 1',
$account
),
ARRAY_N
);
// dump a readable version of the $wpdb object
echo '<pre>';
print_r($wpdb);
die('</pre>');
Often times, reading the MySQL error message helps narrow down the problem in your SQL syntax.
DEBUG #6
If none of this has helped at all, then you will need to use your experience to trackdown a random bug in either your plugins or theme, what could literally be anything. You may as well not even dig in core WP code because, while it does have a couple minor bugs unrelated to your problem, which are getting repaired as we speak, it is one of the most stable CMS platforms out there. It is used by more of the top 10 million sites on the internet than any other CMS, for a good reason. It works, it is up-to-date, and most of all, it is stable.
I really hope you found this helpful or at least learned something from it. Hopefully others find it useful as well.
$fname=$wpdb->get_results(
"SELECT * FROM `vfp_cart66_accounts` WHERE id = '$account'",
ARRAY_N"
);
I have just started to convert to mysqli due to the added security benefits. The main reason for converting to mysqli was the mysqli_multi_query function though. I had several long, complicated query's with a lot of JOINS in and when I found out about this function I thought I could make it simpler by breaking everything down into separate queries.
However, I have been unable to get the query to work as I want it to and the PHP manual isn't helping me.
Here's what I have so far;
$qry = "SELECT T.T_ID, T.name, T.pic, T.timestamp AS T_ts,
(SELECT COUNT(*) FROM track_plays WHERE T_ID = T.T_ID) AS plays,
(SELECT COUNT(*) FROM track_downloads WHERE T.T_ID = T_ID) AS downloads
FROM tracks T WHERE ID = '$ID';
";
$qry .= "SELECT S_ID, status, timestamp AS S_ts FROM status WHERE ID = '$ID';";
$qry .= "SELECT G_ID, gig_name, date_time, lineup, price, ticket, venue, G_pic, timestamp AS G_ts FROM gigs WHERE ID = '$ID'";
// Execute multi query
if (mysqli_multi_query($con,$qry)){
do {
// Store first result set
if ($result=mysqli_store_result($con)){
while ($row=mysqli_fetch_array($result)){
print_r($row);
}
}
}
while (mysqli_next_result($con));
}
This works fine and the array is printed as expected. However, i want to set a lot of variables for use later on. I won't list all of the variables but I have a few like this;
$S_ID = htmlspecialchars($row['S_ID']);
$T_ID = htmlspecialchars($row['T_ID']);
$G_ID = htmlspecialchars($row['G_ID']);
The variables are retrieved but due to the loop nature of the function PHP errors are given as well saying the $S_ID or $G_ID are undefined. $T_ID does not get an undefined error as it is the first query as is not looped over.
If you need any more information or I have not explained well enough just ask!
A while back ago i have had the same issues, and also for the same reason i have migrated from mysql to mysqli.
Sadly, it wasnt the best sollution for many cases, as i have realized on the way.
While implementing stuff with mysqli and multi query i still have had some issues that i had with mysql.
The solution i recommend, is to use views on your complicated querys.
it makes your coding and querys far less complicated.
I know it is not the answer you have been looking for, but give it a thought.
So far, every time I use a mysqli_multi_query, my do-while condition is:
while(mysqli_more_results($connection) && mysqli_next_result($connection));
You may like to replace your while statement and see if that helps.
If not, are you differentiating between each subsequent query when you are assigning these $S_ID, $G_ID variables? Are you inadvertently overwriting a variable with an empty $row[] value?
I also didn't see mysqli_free_result($result) in your code.
I'll even offer some error checking as a garnish.
preg_match_all("/(?:SELECT\s(.*?),\s.*?(?:;|$))/",$qry,$first_columnname);
if (mysqli_multi_query($con,$qry)){
do {
if ($result=mysqli_store_result($con)){
$query_identifier=array_shift($first_columnname[1]);
while ($row=mysqli_fetch_array($result)){
if($query_identifier)=="T.T_ID"){
//do something...
}elseif($query_identifier)=="S_ID"){
//do something...
}elseif($query_identifier)=="G_ID"){
//do something...
}
}
mysqli_free_result($result);
}
}
while(mysqli_more_results($con) && mysqli_next_result($con));
}
if($error_mess=mysqli_error($con)){echo "Error = $error_mess";}
Let me know if any of these small changes do the trick.
I am trying to track pageviews on my site whether a user is logged in or not and so I'm capturing the sessionId in my log. I only want to show tracking results for session ids that have at some point logged in and so my flow is as follows:
$pagestats = $wpdb->get_results("SELECT * FROM wp_user_stats WHERE uid=".$_GET['viewstats']);
$sessionArray = array();
foreach($pagestats as $checkSession)
{
if( !(in_array($checkSession->sessionId, $sessionArray)))
{
$sessionArray[] = $checkSession->sessionId;
}
}
Next, I am trying to gather all of the stats concerning any session Ids generated by this particular user ...
$sessions = join(',',$sessionArray);
$pagestats = $wpdb->get_results("SELECT * FROM wp_user_stats WHERE `sessionId` IN($sessions)") or die(mysql_error());
This is the part that throws the error. The error is:
Unknown column 'sjhntmqhltknks8pbhr750voe7' in 'where clause'
I don't understand why it's trying to find a column that matches the session Id instead of a result within that column.
The session IDs probably aren't getting quoted so the query looks like WHERE sessionID IN(abc, def, ...).
One way to fix that would be to change a line in the first loop:
$sessionArray[] = "'".$checkSession->sessionId."'";
Or you could create a second array with the quoted values.
The problem is that the session id is not numeric and needs to be wrapped in quotes. Something like the following would add proper quote to your $sessions string:
$sessions = "'" . implode("', '", $sessionArray) . "'";
You should also make sure you are escaping any user supplied input (e.g. $_GET['viewstats']) before using them to help avoid SQL injection attacks. It wouldn't hurt to escape $checkSession->sessionId as you are adding it to the $sessionArray array either.
If you are using a framework (it looks like you may be using WordPress) read the manual for the database component as it may provide functions to handle some of this for you.
I think you need to put quote around your session values
$sessions = "'".join("','",$sessionArray)."'";
Right now it's like WHERE IN (a,b,c) instead of WHERE IN ('a','b','c').
$pagestats = $wpdb->get_results("SELECT * FROM wp_user_stats WHERE `sessionId`=$sessions") or die(mysql_error());
This isn't an answer to the specific issue, but isn't the second SELECT statement unnecessary? If it is all stored in one table (unless there is a typo...) then SELECT * FROM wp_user_stats WHERE uid=$_GET['view_stats'] would retrieve all sessions for that user. Perhaps you need it done for multiple users? Even at that, you could simply do a GROUP BY clause.
Maybe I'm missing something though -- if so, sorry.
I'm using XMLHttpRequests to call a PHP script on my server, but the query is continuously failing. I've rewritten it several times, am I going about this the wrong way? I've researched statements and seen them written in a very similar fashion.
$query = mysql_query("UPDATE arts SET a_id=((SELECT a_id FROM logs
WHERE unique='{$_GET['unique']}') + ',' + (SELECT id
FROM mf_arts WHERE art='{$_GET['url']}'))
WHERE unique='{$_GET['id']}'");
if(!$query)
{
$fquery = mysql_query("INSERT INTO mf_arts (art,name)
VALUES('{$_GET['url']}','{$_GET['name']}');
UPDATE mf_logs SET a_id=((SELECT a_id FROM mf_logs
WHERE unique='{$_GET['id']}') + ',' + (SELECT id FROM
mf_arts WHERE art='{$_GET['url']}'))
WHERE unique='{$_GET['id']}'");
if(!$fquery) echo("ADD IMPOSSIBRU");
} else echo "1";
I feel like I'm missing a very small, but very important portion. I tried using IF EXISTS originally but I keep encountering the same problem, so I tried to simplify it to a statement after statement sort of hierarchy. Honestly, thanks for any help. StackOverflow is great.
unique is a reserved word see: dev.mysql.com/doc/refman/5.5/en/reserved-words.html
either avoid it, best option or wrap it in back ticks
Multiple queries aren't allowed in mysql_query. After sanitizing your user input, try separating them
if(!$query)
{
mysql_query("INSERT INTO mf_arts (art,name)
VALUES('{$_GET['url']}','{$_GET['name']}')")
or die("ADD IMPOSSIBRU");
mysql_query("UPDATE mf_logs SET a_id=((SELECT a_id FROM mf_logs
WHERE `unique`='{$_GET['id']}') + ',' + (SELECT id FROM
mf_arts WHERE art='{$_GET['url']}'))
WHERE `unique`='{$_GET['id']}'")
or die("ADD IMPOSSIBRU - Update");
echo "1";
}
unique is a reserved keyword, as was explained above, use (``), like:
WHERE `unique`='{$_GET['unique']}'
Use INSERT INTO ... ON DUPLICATE KEY UPDATE ...
dev.mysql.com/doc/refman/5.0/en/insert-on-duplicate
First, as has been mentioned previously, please please please sanitize your queries.
Second, within double quotes, don't use single quotes for array indices.
WHERE unique='{$_GET['unique']}'
should be
WHERE unique='{$_GET[unique]}'
I need to grab data from two tables, but I know theres a better, more tidier way to do this. Is it some kind of JOIN i need?
I'll show you my code and you'll see what I mean:
if ($rs[firearm] != "") {
$sql_result2 = mysql_query("SELECT * FROM db_firearms WHERE name='$rs[firearm]'", $db);
$rs2 = mysql_fetch_array($sql_result2);
$sql_result3 = mysql_query("SELECT * FROM items_firearms WHERE player='$id'", $db);
$rs3 = mysql_fetch_array($sql_result3);
if ($rs3[$rs2[shortname]] < 1) {
mysql_query("UPDATE mobsters SET firearm = '' WHERE id ='$id'");
}
}
This question is clear, but your code example has alot of formatting issues and I cannot give you direct answer, based on your example code.
The reason, why your example is unclear, is because.. with what are you going to join the tables? From one table you are selecting by name='$rs[firearm]' and from another by player='$id'. You have to provide the hidden data, like $rs and also $id.
You should definitely read these about mysql join and mysql left join. But I will try to give you an example based on your code, with fixed syntax. (Keep in mind, that I'm no mysql join expert, I did not test this code and also I do not know the joining conditions.) And also, the system structure is unclear.
As I understood, this what your tables do, correct?
mobsters - Users table
items_firearms - Links from users table to items table
db_firearms - Items table
So basically, my example does this: It will have preloaded $rs value, from the users table. It will check, if there is a entry inside the links table and hook the result with them items table. However, if the links table or even the items table can return multiple entries, then this doesn't work and you need to loop your results in much more smarter way.
// I can only assume, that $id is the ID of the player
$id = 2;
// Since I dont know the $rs value, then Im going to make some up
$rs = array(
'id' => 33,
'firearm' => 'famas'
);
if ($rs['firearm']) {
$result = mysql_fetch_array(mysql_query("SELECT ifa.*, dbfa.* FROM `items_firearms` AS `ifa` LEFT JOIN `db_firearms` AS `dbfa` ON `ifa.shortname` = `dbfa.shortname` WHERE `ifa.player` = '$id'"));
if ($result['id']) {
mysql_query("UPDATE `mobsters` SET `firearm` = '' WHERE `id` = '$id'", $db);
}
}
It is pretty clear, that you are new to PHP and mysql.. So I think you should probably edit your question and talk about your higher goal. Briefly mention, what your application are you building..? What are you trying to do with the mysql queries..? Maybe provide the table structure of your mysql tables..? I'm sure, that you will get your questions votes back to normal and also we can help you much better.
NOTES
You have to quote these types of variables: $rs[firearm] -> $rs['firearm']
If you want to check if your $rs['firearm'] equals something, then there is a better way then $rs[firearm] != "". The most simple is if ($rs['firearm']) {echo 'foo';}, but will produce a notice message, when all errors reporting mode. You can use isset() and empty(), but keep in mind, that isset() checks whether the variable has been set.. Meaning, even if its false, then it has been set. empty() reacts to undefined and empty variable the same, without any messages.
Also, "" means NULL, so if you even need to use "", then use NULL instead...much neater way..
I strongly recommend to use mysql class. You can understand the basics behind that idea from this answer. This is gonna make things much more easier for you. Also, mysql class is a must-have when dealing with dynamic applications.
if ($rs3[$rs2[shortname]] < 1) { .. makes no sense.. Do you want to check if the value is empty? Then (simple): if (!$rs3[$rs2[shortname]]) { .. and a very strict standard: if (empty($rs3[$rs2[shortname]])) { ..
Also you have to quote your sql queries, see my examples above.
Is the last mysql query missing $db?