I have a Table structure as
id, trackid, table_name, operation,
oldvalue, newvalue, field,
changedonetime
Now if I have 3 rows for the same "trackid" same "field", then how can i select the latest out of the three?
i.e. for e.g.:
id = 100 trackid = 152 table_name
= jos_menu operation= UPDATE oldvalue = IPL newvalue = IPLcccc
field = name live = 0 changedonetime =
2010-04-30 17:54:39
and
id = 101 trackid = 152 table_name =
jos_menu operation= UPDATE oldvalue
= IPLcccc newvalue = IPL2222 field = name live = 0 changedonetime =
2010-04-30 18:54:39
As u can see above the secind entry is the latest change,
Now what query I should use to get the only one and Latest row out of many such rows...
$distupdqry = "select DISTINCT trackid,table_name from jos_audittrail where live = 0 AND operation = 'UPDATE'";
$disupdsel = mysql_query($distupdqry);
$t_ids = array();
$t_table = array();
while($row3 = mysql_fetch_array($disupdsel))
{
$t_ids[] = $row3['trackid'];
$t_table[] = $row3['table_name'];
//$t_table[] = $row3['table_name'];
}
//echo "<pre>";print_r($t_table);echo "<pre>";
//exit;
for($n=0;$n<count($t_ids);$n++)
{
$qupd = "SELECT * FROM jos_audittrail WHERE operation = 'UPDATE' AND trackid=$t_ids[$n] order by changedone DESC ";
$seletupdaudit = mysql_query($qupd);
$row4 = array();
$audit3 = array();
while($row4 = mysql_fetch_array($seletupdaudit))
{
$audit3[] = $row4;
}
$updatefield = '';
for($j=0;$j<count($audit3);$j++)
{
if($j == 0)
{
if($audit3[$j]['operation'] == "UPDATE")
{
//$insqry .= $audit2[$i]['operation']." ";
//echo "<br>";
$updatefield .= "UPDATE `".$audit3[$j]['table_name']."` SET ";
}
}
if($audit3[$j]['operation'] == "UPDATE")
{
$updatefield .= $audit3[$j]['field']." = '".$audit3[$j]['newvalue']."', ";
}
}
/*echo "<pre>";
print_r($audit3);
exit;*/
$primarykey = "SHOW INDEXES FROM `".$t_table[$n]."` WHERE Key_name = 'PRIMARY'";
$prime = mysql_query($primarykey);
$pkey = mysql_fetch_array($prime);
$updatefield .= "]";
echo $updatefield = str_replace(", ]"," WHERE ".$pkey['Column_name']." = '".$t_ids[$n]."'",$updatefield);
}
In the above code I am fetching ou the distinct IDs in which update operation has been done, and then accordingly query is fired to get all the changes done on different fields of the selected distinct ids...
Here I am creating the Update query by fetching the records from the initially described table which is here mentioned as audittrail table...
Therefore I need the last made change in the field so that only latest change can be selected in the select queries i have used...
please go through the code.. and see how can i make the required change i need finally..
This is another question of the greatest-n-per-group category, which comes up several times per week on Stack Overflow.
Here's how I'd solve it in your case:
SELECT j1.*
FROM jos_audittrail j1 LEFT OUTER JOIN jos_audittrail j2
ON (j1.trackid = j2.trackid AND j1.field = j2.field
AND j1.changedonetime < j2.changedonetime)
WHERE j2.id IS NULL;
Related
i am trying to update a table column which same column from same table select.
Here is the code (updated)
public function UpdateStockIn($id, $subUnitValue) {
$query = "UPDATE BRAND_LIST SET CURRENT_STOCK_BOTTLE = (SELECT CURRENT_STOCK_BOTTLE FROM BRAND_LIST WHERE ID = ?) + '.$subUnitValue.' WHERE ID = ? ";
$success = 0;
try {
$stmt = $this->conn->prepare($query);
$stmt->bindParam(1, $id);
$stmt->bindParam(2, $id);
$stmt->execute();
$success = 1;
} catch (PDOException $ex) {
echo $ex->getMessage();
}
return $success;
}
it Show error like this
You can't specify target table 'BRAND_LIST' for update in FROM clause
Try run these 2 sqls, The first one will store a value into mysql local variable then use into 2nd sql.
SELECT #old_subUnitValue := GROUP_CONCAT(table1.CURRENT_STOCK_BOTTLE) FROM BRAND_LIST AS table1 WHERE table1.ID=2;
UPDATE BRAND_LIST AS table2 SET table2.CURRENT_STOCK_BOTTLE = #old_subUnitValue + '.$subUnitValue.' WHERE table2.ID=2;
Use the below query
$query = "UPDATE BRAND_LIST SET CURRENT_STOCK_BOTTLE = CURRENT_STOCK_BOTTLE + ".$subUnitValue." WHERE ID = ?";
$query_sub = "SELECT * FROM `product_mappings` LEFT JOIN `product_list` ON `product_mappings`.ID_PRODUCT =`product_list`.ID WHERE ID_USER='" . $row{'ID'} . "'";
$result_sub = mysql_query($query_sub);
if ($result_sub && mysql_num_rows($result_sub) > 0)
{
$data_products = array();
while ($row_sub = mysql_fetch_array($result_sub))
{
$data_sub = array();
$data_sub["ID"] = $row_sub{'ID'};
$data_sub["product"] = $row_sub{'PRODUCT'};
$query_sub_unactive = "SELECT * FROM `product_list` WHERE ID != '" . $row_sub{'ID'} . "' ";
$result_sub_unactive = mysql_query($query_sub_unactive);
if ($result_sub_unactive && mysql_num_rows($result_sub_unactive) > 0)
{
$data_products_unactive = array();
while ($row_sub_unactive = mysql_fetch_array($result_sub_unactive))
{
$data_sub_unactive = array();
$data_sub_unactive["ID"] = $row_sub_unactive{'ID'};
$data_sub_unactive["productss"] = $row_sub_unactive{'PRODUCT'};
array_push($data_products_unactive, $data_sub_unactive);
}
$data_current["productsUnactive"] = $data_products_unactive;
}
array_push($data_products, $data_sub);
}
$data_current["products"] = $data_products;
Hi guys ! This is query where I should select only products that are not already in main query. I am checking if ID is the same as you can see. For example I load 4 products (of 15) with main query and unactive should load 11 of items in this case.. but loads 14 items.. so it "removes" just one product from list. Any clue?
Thanks !
SELECT * FROM `product_list` WHERE ID != '" . $row_sub{'ID'} . "' ";
This query is checking 1 ID at a time and is always going to return the other 14 rows. What you need is a "NOT IN" query like this:
SELECT * FROM `product_list` WHERE ID NOT IN ("id1","id2","id3","id4");
my $result and $result2 is correct but why this warning occurs "mysql_fetch_array() expects parameter 1 to be resource, boolean given in..."
HELP ME TO SOLVE THIS PROBLEM.
This is my coding:
//capture input
<?php
//capture input
$destination_name = $_POST['destination_name'];
$num_of_passenger = $_POST['num_of_passenger'];
$reserve_to = $_POST['reserve_to'];
$venue = $_POST['venue'];
$day = $_POST['day'];
$DepDate = $_POST['DepartureDate'];
$DepartureTime = $_POST['DepartureTime'];
$ReDate = $_POST['ReturnDate'];
$ReturnTime = $_POST['ReturnTime'];
STEP 3 : SQL Statement (INSERT UPDATE DELETE VIEW)
$result = mysql_query("INSERT INTO location (destination_code, destination_name) VALUES ('','$destination_name')");
$new_row_id1 = mysql_insert_id();
while($row=mysql_fetch_array($result))
{
$destination_name = $row['destination_name'];
}
$result2 = mysql_query("INSERT INTO reservation (reservation_id, num_of_passenger, reserve_to, venue, day, DepartureDate, DepartureTime, ReturnDate, ReturnTime, destination_code, user_id) VALUES('','$num_of_passenger','$reserve_to','$venue','$day','$DepDate','$DepartureTime','$ReDate','$ReturnTime','$new_row_id1','$_SESSION[user_id]')");
while($row2=mysql_fetch_array($result2))
{
$num_of_passenger = $row2['num_of_passenger'];
$reserve_to = $row2['reserve_to'];
$venue = $row2['venue'];
$day = $row2['day'];
$DepDate = $row2['DepartureDate'];
$DepartureTime = $row2['DepartureTime'];
$ReDate = $row2['ReturnDate'];
$ReturnTime = $row2['ReturnTime'];
}
if (!$result2)
{
die ("Cannot Execute Query".mysql_error());
}
else
{
print "Reservation Complete";
}
?>
See Docs: http://php.net/manual/en/function.mysql-query.php
For other type of SQL statements, INSERT, UPDATE, DELETE, DROP, etc, mysql_query() returns TRUE on success or FALSE on error.
So your code while($row2 = mysql_fetch_array($result2)), $result2 is a boolean indicating true/false. You'll need to use a different query (SELECT) to get results to iterate over.
I'm trying to figure out how to build a query using Yii's CDbCriteria that would be equivalent to the following:
SELECT
*
FROM
user u
JOIN (
SELECT *
FROM skill_assessment s
WHERE s.skill = 'HTML'
AND s.score >= 80
) b ON
(u.id = b.userId)
JOIN (
SELECT *
FROM skill_assessment s
WHERE s.skill = 'CSS3'
AND s.score >= 80
) c ON
(u.id = c.userId);
etc...
Here's what I have so far, that isn't working:
$criteria = new CDbCriteria();
$criteria->alias = "u";
$criteria->select = "*";
$criteria->join = "JOIN skill_assessment s ON (u.id=s.userId)";
for($i = 0; $i < count($skill_filters); $i++) {
$criteria->addCondition("s.skill='".$skill_filters[$i]->skill."' AND s.score >= ".$skill_filters[$i]->level);
}
$users = UserModel::model()->findAll($criteria);
Any help would be greatly appreciated.
Thanks in advance.
EDIT:
I was able to build out the sql query as a string and use findAllBySql, which returned the correct UserModels that matched my search criteria, the problem is that I haven't been able to get it to return the related SkillAssessmentModels. They don't come back either with the initial query, like this:
$users = UserModel::model()->with('skill_assessments')->findAllBySql($sql);
nor if I get the results like this:
$users = UserModel::model->findAllBySql($sql);
foreach($users as $user)
{
$user->skill_assessments = $user->getRelated('skill_assessments');
}
Any thoughts on how I can get those related models?
The strange thing is that elsewhere in my application, I CAN get the related models if I do this:
$user = UserModel::model->findByPk($id);
$user->skill_assessments->getRelated('skill_assessments');
Second param for addCondition is by default 'AND'. Is this what you are looking for? May be you should define 'OR' for $operator and add braces around condition.
But in your case addCondition will by applied to the user table, not to the JOIN.
I think that this should work for you:
$criteria = new CDbCriteria();
$criteria->alias = "u";
$criteria->together= "skill_assessment";
$where = array();
for($i = 0; $i < count($skill_filters); $i++) {
$where[] = "(s.skill='".$skill_filters[$i]->skill."' AND s.score >= ".$skill_filters[$i]->level . ')';
}
$criteria->join = 'JOIN skill_assessment s ON (u.id=s.userId' . ( $where ? ( ' AND (' . join( ' OR ', $where ) . ')' ) : '') . ')';
$users = UserModel::model()->findAll($criteria);
Fetch _skill_assessment_ like this:
foreach( $users->skill_assessment as $skill_assessment )
{
echo $skill_assessment->userId;
}
At this level keep it simple:
$sql="select * from mytable where id = :id";
$cmd = Yii::app()->db->createCommand($sql)->bindParam("id", $res_id);
$cmd->execute();
Thanks a lot to Boris Belenski!
What you suggested wasn't quite what I needed, but it did get me to what I needed. Here is what I ended up with that works:
$str = "abcdefghijklmnopqrstuvwxyz";
$idxs = str_split($str);
$criteria = new CDbCriteria();
$criteria->alias = "u";
$joins = array();
for($i = 0; $i < count($skill_filters); $i++)
{
$joins[] = " JOIN (SELECT * FROM skill_assessment s WHERE s.skill = '" . $skill_filters[$i]->skill ."' AND s.score >= " . $skill_filters[$i]->level . ") " . $idxs[$i] . " ON (u.id = " . $idxs[$i] . ".userId) ";
}
$criteria->join = join(' ', $joins);
$users = UserModel::model()->findAll($criteria);
foreach($users as $user)
{
$user->skill_assessments = $user->getRelated('skill_assessments');
}
The really key part is that $joins array.
This will allow you to get all the users that match ALL the criteria for row matches in the skill_assessments table.
Also, I could probably lazily load the skill assessments in the View in a normal view, but I need to get all the skill_assessments for each user now in order to pass them back in an ajax response with the user.
I have a Table structure as
id, trackid, table_name, operation, oldvalue, newvalue, field, changedonetime
Now if I have 3 rows for the same "trackid" same "field", then how can i select the latest out of the three?
i.e. for e.g.:
id = 100 trackid = 152 table_name
= jos_menu operation= UPDATE oldvalue = IPL newvalue = IPLcccc
field = name live = 0 changedonetime =
2010-04-30 17:54:39
and
id = 101 trackid = 152 table_name =
jos_menu operation= UPDATE oldvalue
= IPLcccc newvalue = IPL2222 field = name live = 0 changedonetime =
2010-04-30 18:54:39
As u can see above the secind entry is the latest change,
Now what query I shoud use to get the only one and Latest row out of many such rows...
UPDATED
$distupdqry = "select DISTINCT trackid,table_name from jos_audittrail where live = 0 AND operation = 'UPDATE'";
$disupdsel = mysql_query($distupdqry);
$t_ids = array();
$t_table = array();
while($row3 = mysql_fetch_array($disupdsel))
{
$t_ids[] = $row3['trackid'];
$t_table[] = $row3['table_name'];
//$t_table[] = $row3['table_name'];
}
//echo "<pre>";print_r($t_table);echo "<pre>";
//exit;
for($n=0;$n<count($t_ids);$n++)
{
$qupd = "SELECT * FROM jos_audittrail WHERE operation = 'UPDATE' AND trackid=$t_ids[$n] order by changedone DESC ";
$seletupdaudit = mysql_query($qupd);
$row4 = array();
$audit3 = array();
while($row4 = mysql_fetch_array($seletupdaudit))
{
$audit3[] = $row4;
}
$updatefield = '';
for($j=0;$j<count($audit3);$j++)
{
if($j == 0)
{
if($audit3[$j]['operation'] == "UPDATE")
{
//$insqry .= $audit2[$i]['operation']." ";
//echo "<br>";
$updatefield .= "UPDATE `".$audit3[$j]['table_name']."` SET ";
}
}
if($audit3[$j]['operation'] == "UPDATE")
{
$updatefield .= $audit3[$j]['field']." = '".$audit3[$j]['newvalue']."', ";
}
}
/*echo "<pre>";
print_r($audit3);
exit;*/
$primarykey = "SHOW INDEXES FROM `".$t_table[$n]."` WHERE Key_name = 'PRIMARY'";
$prime = mysql_query($primarykey);
$pkey = mysql_fetch_array($prime);
$updatefield .= "]";
echo $updatefield = str_replace(", ]"," WHERE ".$pkey['Column_name']." = '".$t_ids[$n]."'",$updatefield);
}
Here I am creating the Update query by fetching the records from the initially described table which is here mentioned as audittrail table... please go throught the code.. and see how can i make the required change i need finally..
select * from TableName order by id DESC LIMIT 1
EDITED. YEs you can if you want to order by "changedonetime" USE.
select * from TableName order by changedonetime DESC LIMIT 1