I'm trying to do a search based on
<select multiple=multiple name="chkUnr[]">
I'm getting out the values from select by running code:
for($i=0;$i<count($_POST["chkUnr"]);$i++)
{
if($_POST["chkUnr"][$i] != "")
{
$search_country = $_POST["chkUnr"][$i];
}
$query = "";
$query .= "SELECT users.* FROM users";
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " LEFT JOIN online ON online.user_id = users.id";
}
$query .= " WHERE";
if (isset($_POST['vip']) ? $_POST['vip'] : 0 == 1) {
$query .= " users.vip = 1 AND";
}
if (isset($_POST['profile_image']) ? $_POST['profile_image'] : 0 == 2) {
$query .= " users.profile_image = '2' AND";
}
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " online.is_online = 1 AND";
}
$query .= " (id NOT IN (SELECT user_id FROM users_blocked WHERE blocked_id = '$user_id')) AND";
$query .= " (users.user_age >= '$age_from' AND users.user_age <= '$age_to') AND";
$query .= " (users.gender = '$gender_search') AND";
$query .= " users.country IN ('$search_country')";
$search_query = mysql_query($query);
}
And i can print out the values but the problem comes when i do the SQL search.
It only pick up the first value in this case im using countries:
So when i select Sweden, Germany, Usa i can print them all out but when trying to do a SQL query only Sweden is being picked up.
I've tried with this code but still same result.
The problem here (and with the other answer) is that the in clause was surrounded by quotes, so that will not yield the result that we want. We need to effectively pass in an array to the query. Also your code is vulnerable to sql injection. I would strongly suggest moving to PDO/prepared statements. I added a slight protection to the countries, but that is not foolproof by any means.
function prepareForSql($value, $key) {
return addslashes($value);
}
array_walk($_POST["chkUnr"], "prepareForSql");
$search_country = "'" . implode("','", $_POST["chkUnr"]) . "'";
$query = "";
$query .= "SELECT users.* FROM users";
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " LEFT JOIN online ON online.user_id = users.id";
}
$query .= " WHERE";
if (isset($_POST['vip']) ? $_POST['vip'] : 0 == 1) {
$query .= " users.vip = 1 AND";
}
if (isset($_POST['profile_image']) ? $_POST['profile_image'] : 0 == 2) {
$query .= " users.profile_image = '2' AND";
}
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " online.is_online = 1 AND";
}
$query .= " (id NOT IN (SELECT user_id FROM users_blocked WHERE blocked_id = '$user_id')) AND";
$query .= " (users.user_age >= '$age_from' AND users.user_age <= '$age_to') AND";
$query .= " (users.gender = '$gender_search') AND";
$query .= " users.country IN ($search_country)";
$search_query = mysql_query($query);
Try
$search_country = implode(',',array_unique($_POST["chkUnr"]));
$query = "";
$query .= "SELECT users.* FROM users";
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " LEFT JOIN online ON online.user_id = users.id";
}
$query .= " WHERE";
if (isset($_POST['vip']) ? $_POST['vip'] : 0 == 1) {
$query .= " users.vip = 1 AND";
}
if (isset($_POST['profile_image']) ? $_POST['profile_image'] : 0 == 2) {
$query .= " users.profile_image = '2' AND";
}
if (isset($_POST['singles_online']) ? $_POST['singles_online'] : 0 == 1) {
$query .= " online.is_online = 1 AND";
}
$query .= " (id NOT IN (SELECT user_id FROM users_blocked WHERE blocked_id = '$user_id')) AND";
$query .= " (users.user_age >= '$age_from' AND users.user_age <= '$age_to') AND";
$query .= " (users.gender = '$gender_search') AND";
$query .= " users.country IN ('$search_country')";
$search_query = mysql_query($query);
Related
I am trying to build search logic that uses multiple form fields and adjusts the MySQL search accordingly. My main area of issue is when dealing with multiple checkboxes. The below gets me close but I get multiple "OR" at the end for some reason. The below gives me (nema = '1' OR OR nema = '12' OR OR nema = '4' OR OR ) for example. More OR's are added for each checkbox. What am I missing or not doing correctly?
$rating = mysqli_real_escape_string($db, implode(',', $_POST['rating']));
$q = "SELECT * FROM lekker WHERE height BETWEEN 20 AND 30 ";
if (!empty($rating)) {
$var = explode(',',$rating);
$rating_count = count($var);
if($rating_count > 1) {
$q .= "AND (";
foreach($var as $test) {
$q .= "nema = '$test'";
for($i=0;$i<$rating_count;$i++) {
if($i!=$rating_count-1) {
$q .= " OR ";
}
}
}
$q .= " )";
} else {
$q .= "nema = '$rating'";
}
}
$q .= " ORDER BY `part` ASC";
This is the Select I am trying to achieve:
SELECT * FROM lekker WHERE height BETWEEN 20 AND 22 AND (nema = '1' OR nema = '12') ORDER BY part ASC
I removed the second loop and always add OR, then you can remove the last one at the end
$rating = mysqli_real_escape_string($db, implode(',', $_POST['rating']));
$q = "SELECT * FROM lekker WHERE height BETWEEN 20 AND 30 ";
if (!empty($rating)) {
$var = explode(',',$rating);
$rating_count = count($var);
if($rating_count > 1) {
$q .= "AND (";
foreach($var as $test) {
$q .= "nema = '$test' OR ";
}
$q=substr($q, 0,-4);
$q .= " )";
} else {
$q .= "nema = '$rating'";
}
}
$q .= " ORDER BY `part` ASC";
Instead of worrying about whether or not you need to add an OR simply add it each time through your foreach then trim off the trailing OR after you are done with the foreach.
if ($rating_count > 1) {
$q .= "AND (";
foreach($var as $test) {
$q .= "nema = '$test' OR ";
}
$q .= rtrim($q,' OR ') . ' )';
} else {
$q .= "nema = '$rating'";
}
Currently I'm developing a search form so my SQL query needs to change with user input. Please see the below code sample.
$sqlSearch = "SELECT * FROM seafarers WHERE ";
if ($dateS != "") {
$sqlSearch .= "add_date = '" . changeDateSlashToHypen($dateS) . "' and ";
}
if ($cdcS != "") {
$sqlSearch .= "cdc = '" . $cdcS . "' and ";
}
if ($ppS != "") {
$sqlSearch .= "passport LIKE '%$ppS%' and ";
}
if ($surnameS != "") {
$sqlSearch .= "surname LIKE '" . $surnameS . "%' and ";
In order to execute this statement the user must select all the options; the statement will not work if the user selects one or two options.
Don't patch your query together like this. Use Prepared Statements. Example:
SELECT *
FROM seafarers
WHERE (:dt is null or add_date = :dt)
and (:cdc is null or cdc = :cdc)
You have to fill the parameters of the query before execution.
Start out with a placeholder like 1=1 which will always be true, and then use AND as a prefix instead of a suffix.
$sqlSearch = "SELECT * FROM seafarers WHERE 1=1 ";
if ($dateS != "") {
$sqlSearch .= " AND add_date = '" . changeDateSlashToHypen($dateS) . "'";
}
...
But as pointed out in the other answer you need to use prepared statements. So, assuming you're using mysqli, which everyone seems to do for some reason:
$sqlSearch = "SELECT * FROM seafarers WHERE 1=1 ";
$types = "";
$parameters = [];
if ($dateS != "") {
$sqlSearch .= " AND add_date = ?";
$types .= "s";
$parameters[] = changeDateSlashToHypen($dateS);
}
if ($cdcS != "") {
$sqlSearch .= " AND cdc = ?";
$types .= "s";
$parameters[] = $cdcS;
}
if ($ppS != "") {
$sqlSearch .= " AND passport LIKE ?";
$types .= "s";
$parameters[] = "%$ppS%";
}
if ($surnameS != "") {
$sqlSearch .= " AND surname LIKE ?";
$types .= "s";
$parameters[] = "$surnameS%";
}
$stmt = $db->prepare($sqlSearch);
if (count($parameters) {
$stmt->bind_param($types, ...$parameters);
}
$stmt->execute();
$result = $stmt->get_result();
while ($row = $result->fetch_assoc()) {
...
}
I've got below snippet where $filter_xx values are extracted from a dropdown basis user choice.
I'm trying to query the mySQL database with what the user chose to query the database with via dropdown selection.
You will see that there are 4 $filter_xx variables and how many of them are set in a given instance is completely random.
The issue is when I use && in the query it checks if all four parameters are true and then throws and output. (Well I know && is suppose to work that way!). I tried replacing all && operators with || and had no luck.
How do I search the database with only options selected by the user?
if(isset($filter_brand) || isset($filter_year) || isset($filter_month) || isset($filter_status))
{
$query = "SELECT * FROM targets WHERE brand='$filter_brand' && startyear='$filter_year' && startmonth='$filter_month' && status='$filter_status' ORDER BY createdon DESC";
} else {
$query = "SELECT * FROM targets ORDER BY createdon DESC";
}
When you have several values that must work in a similar manner, use an array together with loop. I am supposing, you are using mysqli, change quoting for PDO if needed.
$mysqli = new mysqli("localhost", "user", "pass", "test");
//...
//SQL attr name => name of POST parameter
$filter = array('brand' => 'brand', 'startyear' => 'year',
'startmonth' => 'month', 'status' => 'status');
//here we'll store SQL conditions
$sql_filter = array();
foreach($filter as $key => $value)
{
if (isset($_POST[$value]))
{
//use your library function to quote the variable before using it in SQL
$sql_filter[] = $key . '="'. $mysqli->escape_string($_POST[$value]) . '"';
}
}
$query = "SELECT * FROM targets ";
if(isset($sql_filter[0]))
{
$query .= 'WHERE ' . implode(' AND ', $sql_filter) . ' ';
}
$query .= 'ORDER BY createdon DESC';
Try By This
$join = "";
//TAKE ONE BLANK VARIBLE THAT JOIN IF VALUE IS SET
if(isset($filter_brand)){
//IF VALUE ISSET THAN IT ADDED TO QUERY
$join .= " AND brand='$filter_brand'";
}
if(isset($filter_year){
$join .= " AND startyear='$filter_year'";
}
$query = "SELECT * FROM targets WHERE id != '' $join ORDER BY createdon DESC";
You can do something like this:
$query = 'SELECT * FROM targets';
$flag = 0;
if(isset($filter_brand) )
{
$query = "SELECT * FROM targets WHERE brand='$filter_brand'";
$flag = 1;
}
if(isset($filter_year)) {
if($flag==1)
$query .= " &&";
$query .= " startyear='$filter_year'";
$flag = 1;
}
if(isset($filter_month)) {
if($flag==1)
$query .= " &&";
$query = " startmonth='$filter_month'";
$flag = 1;
}
if(isset($filter_status)){
if($flag==1)
$query .= " &&";
$query = " status='$filter_status'";
$flag = 1;
}
if($flag == 1){
$query .= " ORDER BY createdon DESC";
} else {
$query = "SELECT * FROM targets ORDER BY createdon DESC";
}
Try this:
$query = "SELECT * FROM targets WHERE 1 ";
$query = isset($filter_brand) ? $query . " AND brand = '".$filter_brand."'" : $query;
$query = isset($filter_year) ? $query . " AND startyear = '".$filter_year."'" : $query;
$query = isset($filter_month) ? $query . " AND startmonth = '".$filter_month."'" : $query;
$query = isset($filter_status) ? $query . " AND status = '".$filter_status."'" : $query;
$query .= " ORDER BY createdon DESC";
Unlike How do I perform an IF…THEN in an SQL SELECT?
, I'm asking about a PHP variable.
I'm trying to create a SQL SELECT statement on my PHP file which can select all person or single person.
if ( $watch_person == "all") {
$sql = "SELECT WORK_RECORD
FROM worklist
";
} else {
$sql = "SELECT WORK_RECORD
FROM worklist
WHERE PERSON_NO = '".$watch_person."'
";
}
Is there a way to do this in one SQL statement?
Here's how I would do it:
$sql = "SELECT WORK_RECORD FROM worklist";
if($watch_person != "all"){
$sql .= " WHERE PERSON_NO = '$watch_person'";
}
You can optimize your coding as below.
$sql = "SELECT WORK_RECORD
FROM worklist WHERE ";
if ( $watch_person == "all") {
$sql .= " 1=1";
} else {
$sql .= " PERSON_NO = '".$watch_person."' ";
}
OR
$sql = "SELECT WORK_RECORD
FROM worklist WHERE ". ($watch_person == "all" ? "1=1" : "PERSON_NO = '".$watch_person."'");
you can have the where statement in the if else.
$sql = "SELECT WORK_RECORD
FROM worklist ".
($watch_person == "all" ? "" : "WHERE PERSON_NO = '".$watch_person."'");
It will be more easy to extend where condition.
.
$sql = "SELECT WORK_RECORD
FROM worklist WHERE 1=1 ";
if ( $watch_person != "all")
$sql .= " and PERSON_NO = '".$watch_person."' ";
if ( $watch_person2 != "another")
$sql .= " and example = '".$watch_person2."' ";
I have code like this:
function search_keyword(){
$keyword = trim($_POST['keyword']);
$search_explode = explode(" ", $keyword);
$x = 0;
$sql = " ( SELECT name AS type FROM global_info WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) UNION ALL ";
$sql .= " ( SELECT name AS type FROM person WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) UNION ALL ";
$sql .= "( SELECT name AS type FROM event WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) ";
$q = $this->db->query($sql);
return $q = $q->num_rows() == 0 ? FALSE : $q->result();
}
The function is working. What I don't know is how to know which data is from which table, and then to show the results on the page?
Perhaps, adding a field to the results of each SELECT.
function search_keyword(){
$keyword = trim($_POST['keyword']);
$search_explode = explode(" ", $keyword);
$x = 0;
$sql = " ( SELECT name AS type, \"table_global_info\" as mytable FROM global_info WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) UNION ALL ";
$sql .= " ( SELECT name AS type, \"person\" as mytable FROM person WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) UNION ALL ";
$sql .= "( SELECT name AS type, \"event\" as mytable FROM event WHERE ";
foreach($search_explode as $each){
$x++;
if($x == 1){
$sql .= " name LIKE '%$each%'";}
else {
$sql .= " name LIKE '%$each%' ";
}
}
$sql .= " ) ";
$q = $this->db->query($sql);
return $q = $q->num_rows() == 0 ? FALSE : $q->result();
}
Regards!
In select statement insert anew column that identifies the table:
SELECT name AS type, 'tab_x' as from_table FROM global_info WHERE
....
SELECT name AS type, 'tab_x1' as from_table FROM global_info WHERE
when you use the returned values check the "from_table" field to see the orginal table the result come from