0

Here is the page I am asking about:

http://rdavidbeales.com/archiveprototype/advancedsearch.php

I've gotten the query to ignore NULL variables by doing some searching using the terms from constructive criticism to the original post.

The only problem now is that I cannot include AND statements in the definitions of the $where variable, because if only one field is selected, then I get an error for a meaningless AND statement.

  • So how can I edit the new code to to include AND when necessary?

Using this link Possible to have PHP MYSQL query ignore empty variable in WHERE clause? I've come up with the code below:

$anf = $_POST["artistnameform"];
$df = $_POST["decadeform"];
$stf = $_POST["subjecttermform"];
$ptf = $_POST["phototitleform"];
$where = "WHERE";

if(!empty($ptf)){
$where .= " P.PhotoTitle='$ptf '";
}
if(!empty($anf)){
$where .= " PE.idPeople = '$anf '";
}
if(!empty($stf)){
$where .= " S.idSubjectTerm = '$stf '";
}
if(!empty($df)){
$where .= " P.PhotoCreatedDate LIKE CONCAT ('%', '$df ', '%')";
}

And here is the query that uses $where:

$query = "
   SELECT P.PhotoTitle, 
          P.PhotoURL, 
          P.PhotoCaption, 
          PE.FirstName, 
          PE.LastName 
     FROM Photo P
LEFT JOIN People_has_Photo PHP 
       ON idPhoto=PHP.Photo_idPhoto
LEFT JOIN People PE 
       ON idPeople=People_idPeople
LEFT JOIN SubjectTerm_has_Photo SHP 
       ON idPhoto=SHP.Photo_idPhoto
LEFT JOIN SubjectTerm S 
       ON idSubjectTerm=SubjectTerm_idSubjectTerm
$where
GROUP BY P.PhotoFileName";
$result = mysql_query($query);
Community
  • 1
  • 1
David Beales
  • 295
  • 4
  • 18
  • You could pass a specific string value instead of empty string (eg: ) so you can interpret that string ("myNull") as no filter server side, so compose the final query – Luca Iaco May 01 '14 at 21:02
  • Now I don't get returns, because instead of the field not being null, I don't get returns because the field does not contain 'mynull'. This is because I am not filtering it on the server side which you mentioned. How is that accomplished exactly? Thanks for the ideas and quick responses!! I'm self-taught here, so my naming conventions, and vague language, will get better as I improve. Thanks for your help. – David Beales May 01 '14 at 21:08
  • 1
    Your naming policy leaves something to be desired. I mean, why assign an alias if you don't then use it !?!?! Actually, there's so much wrong here, it's a little difficult to know where to begin :-~ – Strawberry May 01 '14 at 21:11
  • If I enter the artist, decade, title, and subject term that all apply to one document. I get that document's record. But what I want it to do is leave two form fields blank, and still return records for documents that have the other two fields. Does that make more sense? – David Beales May 01 '14 at 21:11
  • "mynull" was just a default value alternative to actual Null but is does not solve the problem. Changed to mysqli. – David Beales May 01 '14 at 21:20
  • I guess what I am asking is how to omit the two null values in the query, without writing a dozen different queries for every possible combination. What php code is there for, if $var=null, then keep it out of the query? Thanks for you help and patience – David Beales May 01 '14 at 21:23
  • Is this the kind of thing I should be doing. http://stackoverflow.com/questions/12339587/possible-to-have-php-mysql-query-ignore-empty-variable-in-where-clause `SELECT * FROM moth_sightings WHERE user_id = '$username' AND (location = '$value1' OR location IS NULL OR location = '') AND english_name = $value2 ";` – David Beales May 01 '14 at 21:27
  • sorry but u have to start from scratch, u can not just jump from mysql to mysqli its not that simple, 'mynull' is completely opposite to NULL, I realy dont know where to start... get the basics of PHP and MYSQL first, good luck – bart May 01 '14 at 21:27
  • start here great book : Peachpit.Press.PHP.6.and.MySQL.5.for.Dynamic.Web.Sites.Dec.2007.eBook-BBL – bart May 01 '14 at 21:43

1 Answers1

1

Use an array of conditions, then concatenate them with ' AND ' between

$wheres = array();

if(!empty($ptf)){
    $wheres[] = " P.PhotoTitle='$ptf '";
}
if(!empty($anf)){
    $wheres[] = " PE.idPeople = '$anf '";
}
if(!empty($stf)){
    $wheres[] = " S.idSubjectTerm = '$stf '";
}
if(!empty($df)){
    $wheres[] = " P.PhotoCreatedDate LIKE '%{$df} %')";
}

$where = implode(' AND ', $wheres);

I also got rid of your CONCAT function, since it was redundant.

Also:

  1. Check if you really need that space after each value. I think you don't.
  2. Use specialized DateTime functions in MySQL, and not LIKE. Searching for time values can be quick if indexed, but such a LIKE operator kills all the performance.
  3. The script is vulnerable to SQL Injection. Escape the quotes, or, even better, use parametrized queries in MySQLi or PDO.
  4. Don't use mysql_... functions. They are deprecated and will be removed in the future.
  5. When writing SQL queries, with multiple tables, ALWAYS prefix the field with the table name or alias. You will avoid A LOT of errors in the future by following this simple rule.
Alex
  • 14,338
  • 5
  • 41
  • 59
  • Thanks for the help, this worked perfectly. I will look up the SQL datetime functions and I will be moving this function to a stored procedure once I get it working right, and I will do some reading on escaping user input. I would up vote, but I can't yet! – David Beales May 02 '14 at 03:10
  • I wouldn't do stored procedures if I were you. If you don't know DateTime functions yet, you probably just started working with databases. Stored procedures are a bit complicated to build on MySQL, and I never ever saw any system that used them with MySQL. They are there, but nobody really uses them. It's different for other database engines though. – Alex May 02 '14 at 10:26