MySQL updating different fields based on a condition - mysql

I want the actual field updated to change depending on a condition. Existing examples I have come across only allow the value of the update to be changed, not the field. This is what I have tried:
UPDATE conversations
CASE WHEN conv_author_id = $uid THEN SET conv_viewed_author = $d
ELSE SET conv_viewed_recipient = $d END
WHERE conv_id = $id
However this gives me a syntax error.
How do I set the actual field updated to be conditional?

This should do the trick:
UPDATE conversations
SET
conv_viewed_author = IF(conv_author_id = $uid, $d, conv_viewed_author),
conv_viewed_recipient = IF(conv_author_id = $uid, conv_viewed_recipient, $d)
WHERE
conv_id = $id;

You can always do something like this:
UPDATE conversations
SET
conv_viewed_author = (
CASE conv_author_id
WHEN $uid THEN $d
ELSE conv_viewed_author
END
),
conv_viewed_recipient = (
CASE conv_author_id
WHEN $uid THEN conv_viewed_recipient
ELSE $d
END
)
WHERE conv_id = $id

Related

How to update multiple rows with SET CASE WHEN THEN with Doctrine query

I have the following code, which generates DQL queries.
When I echo my $dql and copy paste it into phpmyadmin and execute it, it works perfectly, but when trying to execute it with Doctrine I keep running into "'[Syntax Error] line 0, col 6981: Error: Unexpected 'WHERE'" error. What am I doing wrong?
$dqlStaticPartial = $dql = "UPDATE \VendorName\MyBundle\Entity\Product cp SET cp.guide_number = CASE ";
$uniqueIds = [];
$i = 0;
foreach($result as $row){
$guideNumber = $this->generateGuideNumber($param1, $param2);
$dql .= "WHEN cp.uniqid = '".$row['uniqid']."' THEN '$guideNumber' ";
$uniqueIds[] = "'".$row['uniqid']."'";
$i++;
if($i % 100 === 0){
$dql .= " END WHERE uniqid IN (".implode(',', $uniqueIds).")";
$this->entityManager->createQuery($dql)->execute();
$dql = $dqlStaticPartial;
}
}
(I know, this is not okay, i'm going to put this in a transaction and I will execute the query after every 100th iteration and I'm gonna escape inputs etc...first I want my query to work)
My guess is that you have more then 100 records and if that is the case then one of the problems you're creating is that your query ends up like this:
UPDATE cp SET cp.guide_number = CASE
WHEN cp.uniqid = '1' THEN '1234'
-- more rows ...
WHEN cp.uniqid = '99' THEN '4563'
END
WHERE uniqid IN (1,...,99)
WHEN cp.uniqid = '100' THEN '1234'
-- more rows ...
WHEN cp.uniqid = '199' THEN '4563'
END
WHERE uniqid IN (100,...,199)
etc. etc.
You should clear the allready executed part of your query and then restart building up your query once you reach ($i % 100 === 0)

update enum value from 1 to 0 mysql?

i'm trying to get this script to update my enum column 'read_message' in my 'ptb_messages' table but it just doesn't do anything. the rest of the script works fine but it's just ignoring the request to update 'read_message from 1 to 0.
can someone please show me where im going wrong? thanks
<?php
session_start();
include 'includes/_config/connection.php';
$subject = $_POST['subject'];
$message_id=$_GET['to'];
$textarea = $_POST['textarea'];
$query = mysql_query("SELECT content FROM ptb_messages WHERE id='".$message_id."'");
$results=mysql_fetch_array($query);
$result=$results['0'];
if($result && $textarea) {
$sql = mysql_query("UPDATE ptb_messages SET content ='".addslashes($textarea)."' WHERE id='".$message_id."'");
$sql = mysql_query("UPDATE ptb_messages SET date_sent = LOCALTIME WHERE id='".$message_id."'");
$query = mysql_query("SELECT suibject FROM ptb_messages WHERE id='".$message_id."'");
$sql = mysql_query("UPDATE ptb_messages SET subject = IF(subject LIKE '%:reply', subject, CONCAT(subject, ':reply')) WHERE id='".$message_id."'");
$sql = mysql_query("UPDATE ptb_messages SET read_message = '0' WHERE id=".$message_id."");
$_SESSION['message_sent']="<div class=\"message_sent\"></div>";
header("Location: {$_SERVER['HTTP_REFERER']}#confirm");
}
?>
You're hitting an edge case in MySQL. enum fields can have their values to referred to by the actual value, or their INDEX in the list of allowable values. You're trying to use 0, which MySQL is interpreting as index 0 of the list, which internally is the empty string.
e.g.
myfield ENUM('one', 'two', 'three')
myfield = 'two' => 'two'
myfield = 1 => 'one'
myfield = 0 => '', not in list, ignore...
If you just need a 0/1 value for a field, why not use an actual BIT field, which is already 0/1/null-only? Using enums for purely numeric values just runs into this value-v.s.-index problem.

Zend db update value not being set

I'm not sure what's missing with this update call, here's my code:
$table = new Application_Model_DbTable_ProductContaminant();
$db = $table->getAdapter();
$db->getProfiler()->setEnabled(true);
$data = array('value' => '999');
$where[] = $db->quoteInto('product_id = ?', $q['product_id']);
$where[] = $db->quoteInto('contaminant_id = ?', $k);
$table->update($data, $where);
print $db->getProfiler()->getLastQueryProfile()->getQuery();
And the profiler output is:
UPDATE `product_contaminants` SET `value` = ? WHERE (product_id = '4802') AND (contaminant_id = 69)
Why isn't 'value' being populated??
Value isn't populated because getQuery will only return a prepared statement with parameter placeholders. If you want the parameters used when it updates try this:
$db->getProfiler()->getLastQueryProfile()->getQueryParams()
More info here.

Trouble Inserting An Array of Information into a MySQL Database

I am having an issue with inserting an array of information into a mysql database. Basically I built a sortable gallery similar to Facebook's photo albums that can be arranged by moving the div to a new spot with jquery's sortable function.
I am using Ajax to call a php file which will inser the new order of the div's into the DB. The information is being passed correctly, it is just not being inserted correctly.
The error I am receiving is:
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 'Array' at line 1
The Php code is:
foreach ($_GET['listItem'] as $position => $item) {
if ($item >= 1) {
$sql[] = "UPDATE table SET order = '{$position}' WHERE id = '{$item}'";
mysql_query($sql) or die(mysql_error());
}
}
If I remove the mysql_query function and just do a print_r, I get:
Array
(
[0] => UPDATE table SET order = '0' WHERE id = '2'
[1] => UPDATE table SET order = '1' WHERE id = '4'
[2] => UPDATE table SET order = '2' WHERE id = '3'
[3] => UPDATE table SET order = '3' WHERE id = '1'
[4] => UPDATE table SET order = '4' WHERE id = '5'
[5] => UPDATE table SET order = '5' WHERE id = '6'
)
This is the first time I have tried to do something like this. Any help would be great.
Thank you in advance for the help!
In mysql_query($sql) $sql is an array, therefore it's value is simply Array. When you assign $sql[] = "UPDATE table SET order = '{$position}' WHERE id = '{$item}'"; simply make this line $sql = "UPDATE table SET order = '{$position}' WHERE id = '{$item}'";. That should solve your problem.
EDIT:
You can leave the [] and simply remove the mysql_query from where it is. After your foreach list item, add this:
foreach($sql as $query) {
mysql_query($query);
}
Sounds like there is some confusion about what the [] operator does. You use [] when you want to append an element to the end of an existing array.
For example:
$sql = array();
$sql[] = 'UPDATE table SET order = "0" WHERE id = "2"';
mysql_query($sql); // this will produce the error you are seeing
Versus:
$sql = 'UPDATE table SET order = "0" WHERE id = "2"';
mysql_query($sql); // this will work
You should rewrite your code as such:
foreach ($_GET['listItem'] as $position => $item) {
if ($item >= 1) {
$sql = "UPDATE table SET order = '{$position}' WHERE id = '{$item}'";
mysql_query($sql) or die(mysql_error());
}
}
That will do what you are intending. However, this is still not a good idea, since you are passing untrusted $_GET data directly to the database. I could, for example, call your script with a string like:
http://yoursite.com/yourscript.php?listItem=1'%3B%20DROP%20TABLE%20yourtable%3B
Since the value of listItem is going directly to the database -- and the $item >= 1 check is insufficient, since PHP will evaluate a string as an integer if it begins with numeric data -- all I have to do is add a single quote to terminate the previous query, and I am then free to inject whatever SQL command I'd like; this is a basic SQL injection attack. Whenever you write database-touching code, you should cleanse any input that might be going to the database. A final version of your code might look like:
foreach ($_GET['listItem'] as $position => $item) {
if ($item >= 1) { // this check may or may not be needed depending on its purpose
$sql = 'UPDATE table SET order = "' . mysql_real_escape_string($position) . '" WHERE id = "' . mysql_real_escape_string($item) . '"';
mysql_query($sql) or die(mysql_error());
}
}
There are other ways to cleanse input data as well, that is just one of them. Hope that helps.

Value becomes empty in sql command?

busy for several hours now, to find out what i am doing wrong.
In an update sql value becomes empty??
if(ctype_digit($_POST['id'])
AND
$_SESSION['captain'] == 1
AND
$_SESSION['team'] == $_POST['id'])
{
$teamtekst = $_POST['value'];
// update text
$q = "UPDATE teams
SET
teamtekst = '".mysql_real_escape_string($teamtekst)."'
WHERE
team_id = '".$_POST['id']."'
LIMIT 1";
$exec = mysql_query($q);
if(mysql_affected_rows($exec) == 1)
echo'ok';
else
echo $q.' '.$_POST['value'];
}
else
{
echo 'Fout in gegevens? Tekst niet opgeslagen!'; // faultmessage
}
It echo's: UPDATE teams SET teamtekst = '' WHERE team_id = '29' LIMIT 1 test
so test is the real value of $_POST['value'] but does not show up in sql statement?
thanks in advance for any help!
its not an sql error , $_POST['value'] is not set
use var_dump($_POST) to know what's inside the $_POST array and check if the $_POST['value'] is already set before