Commands out of sync in A correct code - php

I've the following query executed via PHP, it used to work like yesterday, and stopped working today, here's it :
SELECT
*,
(SELECT IF (pro.uid= '4342','True','False') FROM pro) AS 'uid'
FROM
Episodes, pro
ORDER BY
Episodes.id DESC
LIMIT 9
The '4342' is changed with GET param, I'm having the following error :
Commands out of sync; you can't run this command now
My PHP API is as the following ( snippets ) :
<?php
include_once "db_config.php";
DEFINE ('DB_HOST', $host);
DEFINE ('DB_USER', $user);
DEFINE ('DB_PASSWORD', $pass);
DEFINE ('DB_NAME', $database);
$mysqli = #($GLOBALS["___mysqli_ston"] = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD)) OR die ('Could not connect to MySQL');
#((bool)mysqli_query($GLOBALS["___mysqli_ston"], "USE " . constant('DB_NAME'))) OR die ('Could not select the database');
?>
<?php
if(isset($_GET['meaE'], $_GET['uid']))
{
$query="SELECT * , (SELECT IF (pro.uid= '".$_GET['uid']."','True','False') FROM pro ) AS 'uid' FROM Episodes,pro ORDER BY Episodes.id DESC LIMIT 9
";
$resouter = mysqli_query($GLOBALS["___mysqli_ston"], $query);
}
$set = array();
$total_records = mysqli_num_rows($resouter);
if($total_records >= 1){
while ($link = mysqli_fetch_array($resouter, MYSQLI_ASSOC)){
$set['APITest'][] = $link;
}
}
echo $val= str_replace('\\/', '/', json_encode($set));
?>
I want to have the following output :
TABLE A - TABLE B
ID NAME TEXT UID - Check_ID
The query I want :
Select * From Table A, Check if "134123123" is exists in B, if yes / no add a record for all the taken records from Table A with the value of checking (True/False) .
What's happening with #sagi query is :
There are 3 records in Table B, and 10 records in Table A, when the query is executed, the result is 30 records, each record in Table B has 10 records from Table A, and the "uid" record value is True where the uid is '134123123', and it's false where it's not '134123123' .

Your query seems wrong, I don't know how it worked yesterday, but right now your are cross joining with out a condition (could be correct but I doubt it) - that means each record in episodes will be joined to each record in pro . In addition, your subquery with the IF will return more then 1 record unless this table contains only 1 record (which again - I doubt it) .
Try this:
SELECT distinct t.*, IF (s.uid is null,'True','False') AS 'uid'
FROM Episodes t
Left JOIN pro s
ON(s.uid = '4342')
ORDER BY t.id DESC
LIMIT ?????
Try using a sub query instead of a join:
Select t.*,
Case when exists(select 1 from pro s where s.uid = '4342')
Then 'true' else 'false'
End as 'uid'
From episodes t
Order by t.id desc
Limit 9;

Related

PHP MySQL imbricate SELECT statements return null

I tried to execute the query, but the result was null, I executed the same query in PhpMyAdmin and returns the result.
The problem is when the query contains SELECT inside another SELECT statement (imbricate), so when the query contains only one SELECT statement, it works fine and returns the result. Here is the code:
db_config.php
<?php
$servername = "localhost";
$username = "root";
$password = "";
$dbname = "university_db";
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
get_planning.php
<?php
require 'db_config.php';
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
$sql = "SELECT cours.jour,
TIME_FORMAT(cours.heure_debut, '%H:%i') AS debut,
TIME_FORMAT(cours.heure_fin, '%H:%i') AS fin,
enseignant.nom_ens as prof, modules.nom_mod as module, salles.nom_salle as salle
FROM cours, promotion, enseignant, modules, salles
WHERE cours.id_promo = (SELECT id_promo FROM promotion WHERE promotion.niveau = '2'
AND promotion.id_speci = (SELECT id_speci FROM spécialité WHERE nom_speci = 'MGL'))
AND cours.id_promo = promotion.id_promo AND cours.id_ens = enseignant.id_ens AND cours.id_salle = salles.id_salle AND cours.id_mod = modules.id_mod
ORDER BY cours.id_cours;";
$result = $conn->query($sql);
if($result == null)
echo "Result is empty!";
Output:
Result is empty!
Information:
PHP: Version 7.3.5
Database: MySQL
Three suggestions for troubleshooting this problem:
Change your cours.id_promo = (SELECT ... to cours.id_promo IN (SELECT... and do the same to the line after it. Why? if you use = and the inner select statement returns more than one result, boom. Query fails. SQL is, at its heart, a set-processing language, and this IN that checks that this is a member of the set that.
echo your $sql value to make sure the statement in it is correct. Try running the exact statement via phpmyadmin to make sure it gives you what you expect.
You have this
if($result == null)
echo "Result is empty!";
Change it to this
if(!$result)
echo 'sql failure:', $conn->error, ': ', $sql;
The query() method only returns a falsey result if the query failed. If it succeeds but finds no matching rows, query() returns an empty result set. So anytime your $result is falsey, you made a programming error in your query. The echo I mentioned will diagnose it for you.
Pro tip Always check SQL operations for errors.
Pro tip 2. Bring your SQL skills into the 21st century. Use explicit join operations rather than old-timey comma-join operations. Change ...
SELECT cours.jour, whatever, whatever
FROM cours
JOIN promotion ON cours.id_promo = promotion.id_promo
JOIN enseignant ON cours.id_ens = enseignant.id_en
JOIN modules ON cours.id_mod = modules.id_mod
JOIN salles ON cours.id_salle = salles.id_salle
WHERE cours.id_promo IN (SELECT id_promo FROM promotion WHERE promotion.niveau = '2')
AND promotion.id_speci IN (SELECT id_speci FROM spécialité WHERE nom_speci = 'MGL')
ORDER BY cours.id_cours
The relationships between your tables are much easier to read and understand this way. And, you can change JOIN to LEFT JOIN if your application requires it.
Just a suggestion.
Instead of nested old implicit join syntax based list table, where clause and nested sub-query should use explicit join syntax.
SELECT cours.jour
, TIME_FORMAT(cours.heure_debut, '%H:%i') AS debut
, TIME_FORMAT(cours.heure_fin, '%H:%i') AS fin
, enseignant.nom_ens as prof
, modules.nom_mod as module
, salles.nom_salle as salle
FROM cours
INNER JOIN promotion ON cours.id_promo = promotion.id_promo
AND promotion.niveau = '2'
INNER JOIN enseignant ON cours.id_ens = enseignant.id_ens
INNER JOIN modules cours.id_mod = modules.id_mod
INNER JOIN salles ON cours.id_salle = salles.id_salle
ORDER BY cours.id_cours;

Convert Mysql procedure into PHP code

I have a stored procedure on my Mysql DB, but i need to change it to get it done by PHP.
I've been looking around here and i know that is possible to make a SP from PHP, but it requires Mysqli (i don't have it updated, and updating it is not possible for personal reasons) or at least that was the only way i found to do it (source).
So for me that only have Mysql, it's possible to do it from php? or should i just "translate" the procedure into PHP format? I mean not making a procedure but a function instead (php function), that actually do the same with PHP code (loops, selects, calls and so) but not storing the procedure on the DB.
This is my procedure
DELIMITER //
create procedure autor_products (in id int)
begin
update authors set authors_products=
(SELECT DISTINCT count(products_id)
FROM products
INNER JOIN authors_to_manufacturers as am ON am.manufacturers_id = products.manufacturers_id
WHERE authors_id = id)
WHERE manufacturers_id = id;
end
//
DELIMITER $$
CREATE PROCEDURE authors()
BEGIN
DECLARE a INT Default 0 ;
DECLARE manu_length int;
select max(manufacturers_id) into manu_length from authors;
simple_loop: LOOP
SET a=a+1;
call autor_products(a);
IF a >= manu_length THEN
LEAVE simple_loop;
END IF;
END LOOP simple_loop;
END $$
DELIMITER ;
commit;
I managed to do this, which is "working" for at least one update
<?php
require('includes/configure.php'); //To get the DB name, user and pass
require_once (DIR_FS_INC.'xtc_db_connect.inc.php'); //I use this to connect the DB
$conn = xtc_db_connect() or die('Unable to connect to database server!');
$manu_lenght="select max(manufacturers_id) from authors;";
for ($i = 0;$i<=$manu_lenght;$i++){ //"for" not in use nor not working if i replace 1 for $i
$update= " update authors set products_amount = (SELECT DISTINCT count(products_id)
FROM products
INNER JOIN authors_to_manufacturers as am ON am.manufacturers_id = products.manufacturers_id
WHERE authors_id = 1)
WHERE manufacturers_id = 1;";
} //will only update 1 author with authors_id = 1 so i needed to make a loop, but if i replace 1 for $i. it doesn't update at all
$retval = mysql_query( $update, $conn );
if(! $retval )
{
die('Could not update data: ' . mysql_error());
}
echo "Updated data successfully\n";
?>
How may i use the $i variable instead of a specific number? (so it would update all at once because of the loop)
Edit: My manu_lenght is not working (it doesn't show the result of the select) but i just changed that part into a number and it's still not working, any thoughts?
Edit 2: Why is this code not working? It works if it's only $a=1; but not if i loop or make a bucle of $a.
$a = 1;
do{
$update= " update authors set products_amount = (SELECT DISTINCT count(products_id)
FROM products
INNER JOIN authors_to_manufacturers as am ON am.manufacturers_id = products.manufacturers_id
WHERE authors_id =$a)
WHERE manufacturers_id =$a;";
echo $a;
$a++;
}
while($a <= 10);
What im doing wrong?
After several tries i got what i need.
This is my code:
<?php
require('includes/configure.php');
require_once (DIR_FS_INC.'xtc_db_connect.inc.php');
$conn = xtc_db_connect() or die('Unable to connect to database server!');
//getting the total amount of authors into $manu_lenght variable
$manu_lenght = mysql_query("select max(manufacturers_id) as sum from authors;" );
if(!$manu_lenght){
die("DB query failed : " . mysql_error());
$sum = "";
} //needed to fetch the result of the select query
while ( $result = mysql_fetch_assoc($manu_lenght)){
$sum = $result["sum"];
}
do{
$author_update= " update authors set products_amount = (SELECT DISTINCT count(products_id)
FROM products
INNER JOIN authors_to_manufacturers as am ON am.manufacturers_id = products.manufacturers_id
WHERE authors_id =$a)
WHERE manufacturers_id =$a;";
$a++;
//while was here, so that's why it wasn't working
$ret_author = mysql_query( $author_update, $conn );
}
while($a <= $sum); //now is correct, it sends the query now
if(!$ret_author )
{
die('Could not update data: ' . mysql_error());
}
echo "Updated authors successfully\n";
?>
What i was basically doing wrong is ending the loop too early, and not letting the mysql_query function send the query (update in this case)
Instead of calling the procedure, i did the procedure translation through PHP. Hope this is useful for anyone else.

sql inserting twice

Hello i have a sql statement that ranks my records and inserts the ranks into a database.
The problem i am having is that when i run the script. It deletes the old rankings. And inserts the new rankings fine, but it inserts every ranking twice. So there will be 2 rank 1's, 2 rank 2's, ect ect.
The kicker to my problem, is if i delete all the records in phpmyadmin. Then run the script. It doesnt make duplicates.
I tried just letting the script delete, to debug if the delete script is working, and it deleted all the rows fine. Hence im really confused :(
if you could look at my code and give me some insight that'd be awesome. Thank you
<?php
// Connect to the database we want to insert/update
$Server_Location = "localhost";
$Server_User_Name = "x";
$Server_Password = "y";
$Database_Name = "z";
// Create connection
$Conn_Info = mysqli_connect($Server_Location, $Server_User_Name, $Server_Password, $Database_Name);
// Check connection
if ($Conn_Info->connect_error) {
die("Connection failed: " . $Conn_Info->connect_error);
}
if($_GET['Password'] != 'q'){
die();
}
$Sql_Delete_Duplicate = "DELETE FROM ranks";
if ($Conn_Info->query($Sql_Delete_Duplicate) === TRUE) {
echo "User Deleted";
}
else {
echo "Error User Not Deleted";
echo $Conn_Info->error;
}
// Overall Games - Rankings (1000)
$Top_1000_Sql = "Select games, overall_games_user.ID as UserID, Name FROM overall_games, overall_games_user WHERE overall_games.User_ID = overall_games_user.ID AND DATE(Date_Updated) = DATE(NOW()) GROUP BY User_ID ORDER BY Games DESC LIMIT 10000";
$Top_1000_Results = $Conn_Info->query($Top_1000_Sql);
$rank = 0;
if ($Top_1000_Results->num_rows > 0) {
echo $Top_1000_Results->num_rows;
while($Top_Player = $Top_1000_Results->fetch_assoc()) {
$rank += 1;
$User_ID = $Top_Player["UserID"];
$Games_Played = $Top_Player["games"];
$Insert_Top_Player_Sql = "INSERT INTO ranks (Rank_Type,Rank, User_ID, games)
VALUES ('Total', {$rank}, {$User_ID}, {$Games_Played})";
if ($Conn_Info->query($Insert_Top_Player_Sql) === TRUE) {
echo $rank . "-";
}
else {
echo "Error User Not Added";
echo $Conn_Info->error;
}
}
}
// Yesterday Games - Rankings
// Graph Stats
/*
SELECT AVG(Games) FROM overall_games WHERE DATE(Date_Updated) = DATE(NOW()) AND User_ID IN (SELECT ID FROM overall_games_user WHERE division LIKE('%BRONZE%'));
SELECT AVG(Games) FROM overall_games WHERE DATE(Date_Updated) = DATE(NOW()) AND User_ID IN (SELECT ID FROM overall_games_user WHERE division LIKE('%SILVER%'));
SELECT AVG(Games) FROM overall_games WHERE DATE(Date_Updated) = DATE(NOW()) AND User_ID IN (SELECT ID FROM overall_games_user WHERE division LIKE('%GOLD%'));
SELECT AVG(Games) FROM overall_games WHERE DATE(Date_Updated) = DATE(NOW()) AND User_ID IN (SELECT ID FROM overall_games_user WHERE division LIKE('%PLATINUM%'));
SELECT AVG(Games) FROM overall_games WHERE DATE(Date_Updated) = DATE(NOW()) AND User_ID IN (SELECT ID FROM overall_games_user WHERE division LIKE('%DIAMOND%'));
*/
?>
You are using Group By without aggregate function so change your query to:
$Top_1000_Sql = "Select Count(games) as gameCount, overall_games_user.ID as UserID, Name FROM overall_games, overall_games_user WHERE overall_games.User_ID = overall_games_user.ID AND DATE(Date_Updated) = DATE(NOW()) GROUP BY UserID ORDER BY Games DESC LIMIT 10000";
Also note change in GROUP BY UserID in above SQL
In $Games_Played variable fetch value of count:
$Games_Played = $Top_Player["gameCount"];
Try Changing VALUES to VALUE in your query.
Also it sometimes so happens that you have an .htaccess to point every thing to the index file. Naturally the browser will request the script twice, once for the script it self, the other is for the favicon.
The fix is to Try to edit the .htaccess to prevent redirection to the index file when the browser is requesting for favicon.ico
Try these two things. I hope it would solve your problem :) Else let me know again.

Multiple query on PHP dows not work

Consider this simple PHP page:
<?php
$db = new mysqli("localhost", "myuser", "mypwd", "mydb");
if ($db->connect_error)
// Dying sequence;
// Executing query
$qres = $db->multi_query("SET #rank = -1; SELECT * FROM (SELECT #rank := #rank + 1 as rank, field1, field2 FROM mytable WHERE field1 = 'value') AS T1 WHERE rank = 2;");
$db->commit();
if (!qres) {
// Problems in query
// Dying
$db->close();
return;
}
if (!($qres->num_rows == 1)) {
// Error fetched
$numrows = $qres->num_rows;
$db->close();
// Dying
return;
}
// Returning
echo "ALLOK";
$db->close();
?>
Well, this does not work.
either if I use query or multi_query
Can you help me?
It looks like you just want to select the 3rd row from some table. Though the rank will be nondeterministic since you don't specify an ORDER BY clause for that inner query.
You don't need this variable and multiple queries to do that.
Use an offset in the LIMIT clause, along with an ORDER BY clause, instead.
SELECT field1, field2 FROM mytable WHERE field1 = 'value' ORDER BY something LIMIT 2,1

MySQL query returns rows in mysql but empty set in PHP

The following MySQL query runs in PHP without errors, but the resultset is empty. Directly outputting the query string to a file and running the query in the MySQL client using 'source [filename]' returns several rows of results, as expected.
Is there something that would cause this query not to work with PHP? categorylinks.cl_to and smw_spec2.value_string are both varbinary(255). Show create table indicates engine=InnoDB and default charset=binary.
Things I have tried without success:
$sql = preg_replace("/[\n\t]+/", " ", $sql);
Changing '_wpg' and 'Derp' to CAST('_wpg' AS BINARY(255))
Changing '_wpg' and 'Derp' to BINARY '_wpg'
I am using the MediaWiki DatabaseMysql class to execute the query and fetch rows, but it's a very thin abstraction, and I'm certain it's not the problem (see below).
SELECT
prop.name AS prop_name, prop.count AS prop_count, prop.type AS prop_type,
val.value AS val_value, val.unit AS val_unit, val.count AS val_count
FROM
(
SELECT
s_id, name, type, COUNT(foo.name) AS count
FROM (
(
SELECT
cl.cl_to AS cat_name, s.smw_id AS s_id, s.smw_sortkey AS name, spec.value_string AS type
FROM `smw_ids` s
INNER JOIN (`categorylinks` cl, `page` p, `smw_ids` s2, `smw_atts2` a)
ON (cl.cl_from = p.page_id AND
p.page_title = s2.smw_title AND
s2.smw_id = a.s_id AND
a.p_id = s.smw_id)
LEFT JOIN `smw_spec2` spec ON s.smw_id = spec.s_id
)
UNION ALL
(
SELECT
cl.cl_to AS cat_name, s.smw_id AS s_id, s.smw_sortkey AS name, '_wpg' AS type
FROM `smw_ids` s
INNER JOIN (`categorylinks` cl, `page` p, `smw_ids` s2, `smw_rels2` a)
ON (cl.cl_from = p.page_id AND
p.page_title = s2.smw_title AND
s2.smw_id = a.s_id AND
a.p_id = s.smw_id)
)
) AS foo
WHERE foo.cat_name = 'Derp'
GROUP BY name
ORDER BY count DESC
LIMIT 10
) AS prop
INNER JOIN
(
SELECT
bar.p_id AS p_id, bar.value AS value, bar.unit AS unit, COUNT(bar.value) AS count,
IF( #prev != p_id, #rownum := 1, #rownum := #rownum+1 ) AS rank,
#prev := p_id
FROM (
(SELECT a.p_id AS p_id, a.value_xsd AS value, a.value_unit AS unit FROM `smw_atts2` a)
UNION ALL
(SELECT r.p_id AS p_id, s.smw_sortkey AS value, NULL AS unit
FROM `smw_rels2` r INNER JOIN `smw_ids` s ON r.o_id = s.smw_id)
) AS bar
GROUP BY value, unit
ORDER BY count DESC
) AS val
ON prop.s_id = val.p_id
WHERE val.rank <= 50
ORDER BY prop_count DESC, prop_name, val_count DESC, val_value
Edit: The following test script outputs nothing. query.sql contains exactly the query above, written to file immediately preceding the mysql_query() call in MediaWiki's database class.
$db = mysql_connect('localhost', 'root', '');
mysql_select_db('mediawiki', $db);
$res = mysql_query(file_get_contents("query.sql"), $db);
while ($row = mysql_fetch_assoc($res)) {
var_dump($row);
}
echo mysql_error($db);
Edit: I imported a huge database dump and afterwards, when I loaded the PHP page, there was a noticeable wait that seemed to indicate that the query was running, but still no results showed. I ended up reworking the query, and I no longer have this problem.
Try this to detect and report errors better:
$db = mysql_connect('localhost', 'root', '');
mysql_select_db('mediawiki', $db);
$res = mysql_query(file_get_contents("query.sql"), $db);
if (!$res) {
print "SQL Error ".mysql_errno().":".mysql_error().", from query: '".file_get_contents("query.sql")."'";
} else {
while ($row = mysql_fetch_assoc($res)) {
var_dump($row);
}
}
Try this after mysql_connect:
mysql_query('SET NAMES utf8;');

Categories