MySQLi , declare variable and using math to count a median - php

I am trying to do some math in this SQL query. I'm not used to this syntax. Trying to count a median for line 3 in the query.
-?- = Can I put a variable here?
-??- = Can I make this line a variable some how?
This is the code I have done:
if(!isset($_SESSION["username"])):
$sql_art_sum = "SELECT (SELECT count(*) FROM post WHERE user_id = ?), **-?-**
(SELECT count(*) FROM comment),
(SELECT count(*)/ **-??-** FROM comment)";
if($stmt = $mysqli->prepare($sql_art_sum)) {
$stmt->bind_param('i', $_SESSION['id']);
$stmt->execute();
$stmt->bind_result($art_sum, $comment_sum, $comment_median);
$stmt->fetch();
$stmt->close();
}

When creating new variables in mysql you need to use 'AS' so for example:
SELECT x, y,
(SELECT SUM(x) - sum(y)
FROM tablename
WHERE b <= c
) as z
FROM tablename
Hope this is the answer you are searching for

Related

PHP/MYSQL subquery causing undefined index error

I am trying to do a subquery using PDO:
$stmt = $pdo->prepare("SELECT sum(ros_ranking) FROM (SELECT ros_ranking FROM players WHERE teamid = 1 and positionid = 1 ORDER BY ros_ranking ASC LIMIT 1) AS totalrankings");
$stmt->execute();
$row = $stmt->fetch(PDO::FETCH_ASSOC);
$num_rows= $stmt->rowCount();
echo "tqr= ".$row['totalrankings'];
I keep getting Notice: Undefined index: totalrankings in ...
ros_ranking is definitely a field with numbers in it in my Players table and a teamid of 1 and positionid of 1 definitely exist.
Does anyone see what I'm doing wrong here? FYI, if I do just the subquery as the main query, it works. So something must be wrong with SELECT sum(ros_ranking) FROM or AS totalrankings but they seem pretty straightforward.
Wrong alias use/position
you need a column name alias for totalrankings (not a table name alias as you have done)
$stmt = $pdo->prepare("SELECT sum(t.ros_ranking) totalrankings
FROM (SELECT ros_ranking
FROM players
WHERE teamid = 1
AND positionid = 1
ORDER BY ros_ranking ASC LIMIT 1) t");
$stmt->execute();
$row = $stmt->fetch(PDO::FETCH_ASSOC);
$num_rows= $stmt->rowCount();
echo "tqr= ".$row['totalrankings'];
total_rankings is an alias for the subquery, it's not an alias for the column. You need to put AS totalrankings after the SUM() expression.
$stmt = $pdo->prepare("
SELECT sum(ros_ranking) AS totalrankings
FROM (
SELECT ros_ranking
FROM players
WHERE teamid = 1 and positionid = 1
ORDER BY ros_ranking ASC
LIMIT 1) AS subquery");
But LIMIT 1 in the subquery means you're not going to get a sum of anything. The subquery just returns 1 row, and the sum of one thing is just that value.
Though you can fix it, by giving the selected column the right alias, there is no need to fetch an array if your query returns only one column. Use fetchColumn() instead:
$stmt = $pdo->prepare("SELECT ...");
$stmt->execute();
$totalrankings = $stmt->fetchColumn();
$num_rows= $stmt->rowCount();
echo "tqr= ".$totalrankings;

PHP MySQLi get columns from foreign key

I have the following tables:
'auktionen'
id|uid|typ(FK)|min|max|menge|...
'typen'
id|typ
1|Hack
2|Schredder
where typ in typen is just a textutal representation, which I would like to get.
$prep_stmt = "SELECT anzeigentyp, typ, holzart,
qualitaet, rinde, min, max, menge FROM auktionen WHERE uid = ?";
$stmt = $mysqli->prepare($prep_stmt);
$stmt->bind_param('i', $user_id);
$stmt->execute();
$stmt->bind_result($anzeigentyp, $typ, $holzart, $qualitaet, $rinde, $min, $max, $menge);
$stmt->store_result();
So when fetching all my results I want to get "Hack" instead of the referencing id (in case it is 1). I guess it needs some JOIN to be achieved and I tried it like this without success:
$prep_stmt = "SELECT anzeigentyp, typen.typ, holzart,
qualitaet, rinde, min, max, menge FROM auktionen WHERE uid = ?
JOIN typen ON auktionen.typ = typen.typ";
What is the proper way to do it?
You must move the where clause to the end and join the corresponding columns typen.id and auktionen.typ
select a.anzeigentyp, t.typ, a.holzart, a.qualitaet, a.rinde, a.`min`, a.`max`, a.menge
from auktionen a
join typen t on t.id = a.typ
where ...

Query works on Sequel Pro but not on my php script

This query works fine on Sequel Pro:
SELECT t1.* FROM `erapido_messages` t1
LEFT OUTER JOIN `erapido_messages` t2 ON `t1.sender_id` = `t2.sender_id`
AND (`t1.msg_date` < `t2.msg_date` OR `t1.msg_date` = `t2.msg_date` AND `t1.sender_id` != `t2.sender_id`)
WHERE `t2.sender_id` IS NULL AND `t1.sender_id`!= `0` AND `t1.receiver_id`= 28
ORDER BY `t1.msg_date` DESC;
When I use it on my php script it returns an error. This is the complete query in php:
$query = "SELECT t1.* FROM `erapido_messages` t1
LEFT OUTER JOIN `erapido_messages` t2 ON `t1.sender_id` = `t2.sender_id`
AND (`t1.msg_date` < `t2.msg_date` OR `t1.msg_date` = `t2.msg_date` AND `t1.sender_id` != `t2.sender_id`)
WHERE `t2.sender_id` IS NULL AND `t1.sender_id`!= `0` AND `t1.receiver_id`= ?
ORDER BY `t1.msg_date` DESC";
//$sql is my connection and it works fine on other queries
$statement = $sql->prepare($query);
//bind parameters for markers: s = string, i = integer, d = double, b = blob
$statement->bind_param('i', $receiver_id);//$receiver_id is defined
//execute query
$statement->execute();
//store the results; allows to count the rows
$statement->store_result();
//bind result variables
$statement->bind_result($id, $receiver_name, $receiver_img, $receiver_email, $sender_id, $sender_name, $sender_email, $sender_img, $subject, $message, $msg_date);
This is the error:
Fatal error: Call to a member function bind_param() on boolean in /messages.php on line 53
I understand that this statement may return 'false' if the query fails:
$statement = $sql->prepare($query);
However, I can't see what is wrong in the query. Any help is welcome!
Thanks much.
Your prepare statement is returning false due to not valid query string. Change your query like the one below. Currently you are escaping your column names because they are in back-tick which results in an error while preparing it
$query = "select * from `dbname` table where `table`.column= ?
ORDER BY `table`.column DESC LIMIT 2 ";
That should fix this error.

MySQL get rows where corresponding row in same table exists

I'm trying to get rows from a table according to some basic where clauses, and now I want to include an "AND EXISTS" clause on the end. My code is the following:
$stmt = $mysqli->prepare("SELECT object_id FROM ".
$db_table_prefix."user_events
WHERE LPAD(start_timestamp,15,'0') < LPAD(?,15,'0')
AND event_id = ?
AND EXISTS (
SELECT * FROM ".$db_table_prefix."user_events
WHERE LPAD(start_timestamp,15,'0') > LPAD(?,15,'0')
AND event_id = ? )
");
The problem I'm having is that I don't know how to specify a column value from the main query within the AND EXISTS subquery.
I'm looking for a way to tack on this bit into the subquery:
AND object_id = **object_id from main query**
Any help appreciated
Also, added an alias to the subquery's table to avoid confusion
$stmt = $mysqli->prepare("SELECT object_id FROM ".
$db_table_prefix."user_events
WHERE LPAD(start_timestamp,15,'0') < LPAD(?,15,'0')
AND event_id = ?
AND EXISTS (
SELECT * FROM ".$db_table_prefix."user_events AS u
WHERE LPAD(u.start_timestamp,15,'0') > LPAD(?,15,'0')
AND u.object_id = " .$db_table_prefix.".object_id
AND u.event_id = ? )
");
Rather than EXISTS, you might find a self-join syntax is clearer here, I cannot deduce exactly what you want from your code, but to get object_id for an event that started before a specific time, and was also started again later:
SELECT ue1.object_id
FROM user_events ue1 join user_events ue2
WHERE ue1.event_id = ue2.event_id AND
ue1.object_id = ue2.object_id AND
ue1.event_id = ? AND
LPAD(ue1.start_timestamp, 15, '0') < LPAD(ue2.start_timestamp, 15, '0') AND
LPAD(ue1.start_timestamp, 15, '0') < LPAD(?, 15, '0')
and object_id in (select object_id from ...

bindParam is not completing the sql query

I'm new to PDO statements and so far I've managed to work with it, use prepared statements and many things, until today.
I have two querys, the first retrieve some data, store the results and then the second query uses that data to retrieve the final data. I'm working on a bad designed DB, that's why I have to do weird things.
The first query gets the year of start and the year of end of a sport league. Then, the year is passed to the second query to get data between those years (WHERE).
The problem is that bindParam seems to not work, it doesn't bind the parameter, shows a ?, and then the SQL throws the following exception:
Connection failed: SQLSTATE[42000]: Syntax error or access violation:
1064 You have an error in your SQL syntax; check the manual that corresponds
to your MySQL server version for the right syntax to use
near ''0701' AND ?'0630' ORDER BY e.FECHA DESC' at line 5
The SQL:
$sqlQueryAuxiliar = "SELECT ano_inicio, ano_fin
FROM TEMPORADAS
ORDER BY ano_inicio DESC
LIMIT 1;";
$sqlQuery = "SELECT e.id, e.JORNADA, DATE_FORMAT(e.FECHA, '%Y-%m-%d'),
e.HORA, c1.nombre_temporada, c2.nombre_temporada
FROM ENCUENTROS AS e
JOIN CLUBS AS c1 ON (e.COD_EQUIL = c1.siglas)
JOIN CLUBS AS c2 ON (e.COD_EQUIV = c2.siglas)
WHERE e.FECHA BETWEEN :anoInicio'0701' AND :anoFinal'0630'
ORDER BY e.FECHA DESC;";
And this is the PHP code:
$this->_db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$stmtAux = $this->_db->prepare($sqlQueryAuxiliar);
$stmtAux->execute();
$fetched = $stmtAux->fetchAll();
$stmtAux = null;
$stmt = $this->_db->prepare($sqlQuery);
$stmt->bindParam(':anoInicio', $fetched[0][0], PDO::PARAM_STR, 12);
$stmt->bindParam(':anoFinal', $fetched[0][1], PDO::PARAM_STR, 12);
$stmt->execute();
while ($row = $stmt->fetch()) {
$partidos[] = $row;
}
$stmt = null;
You cannot concatenate strings in your query this way. Change your query to
SELECT e.id, e.JORNADA, DATE_FORMAT(e.FECHA, '%Y-%m-%d'), e.HORA, c1.nombre_temporada, c2.nombre_temporada
FROM ENCUENTROS AS e
JOIN CLUBS AS c1 ON (e.COD_EQUIL = c1.siglas)
JOIN CLUBS AS c2 ON (e.COD_EQUIV = c2.siglas)
WHERE e.FECHA BETWEEN :anoInicio AND :anoFinal
ORDER BY e.FECHA DESC
and the bindParams to
$stmt->bindValue(':anoInicio', $fetched[0][0] . '0701', PDO::PARAM_STR);
$stmt->bindValue(':anoFinal', $fetched[0][1] . '0630', PDO::PARAM_STR);
Stands to reason, you're building invalid sql:
WHERE e.FECHA BETWEEN :anoInicio'0701' AND :anoFinal'0630'
would be built as basically
WHERE e.FETCHA BETWEEN foobar'0701' AND barbaz'0630'
which is a syntax error.
You probably want
WHERE e.FETCH BETWEEN concat(:anoInicio, '0701') AND concat(:anoFinal, '0630')
instead.
If you are using bound parameters you should not also be passing in a hard-coded value in your query..
"SELECT e.id, e.JORNADA, DATE_FORMAT(e.FECHA, '%Y-%m-%d'), e.HORA, c1.nombre_temporada, c2.nombre_temporada
FROM ENCUENTROS AS e
JOIN CLUBS AS c1 ON (e.COD_EQUIL = c1.siglas)
JOIN CLUBS AS c2 ON (e.COD_EQUIV = c2.siglas)
WHERE e.FECHA BETWEEN :anoInicio AND :anoFinal
ORDER BY e.FECHA DESC;";

Categories