PHP Search Script

Hi all,

I’ve designed a “Name Finder” script which searches a database of names and returns the results based on the search string entered into a form.

I wanted to make a few changes but am a little stuck and hope somebody can help me.

The following is the current PHP Script:

<?php

$dbHost = '*******';
$dbUser = '*******'; 
$dbPass = '*******';
$dbDatabase = '*******';
$con = mysql_connect($dbHost, $dbUser, $dbPass) or trigger_error("Failed to connect to MySQL Server. Error: " . mysql_error());

mysql_select_db($dbDatabase) or trigger_error("Failed to connect to database {$dbDatabase}. Error: " . mysql_error());

// Set up error check and result check array
$error = array();
$results = array();

// First check if a form was submitted
if (isset($_GET['search'])) {
   $searchTerms = trim($_GET['search']);
   $searchTerms = strip_tags($searchTerms); // removes any html/javascript.
   
if (isset($_GET['searchgender'])) {
   $searchgenderTerms = trim($_GET['searchgender']);
   $searchgenderTerms = strip_tags($searchgenderTerms); // removes any html/javascript.


   if (strlen($searchTerms) < 3) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }
   
   if (strlen($searchgenderTerms) < 3) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchgenderTermDB = mysql_real_escape_string($searchgenderTerms); // Prevents sql injection.
   }
}
   // If there are no errors, search begins...
   if (count($error) < 1) {

//The Query
$searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE `name` LIKE '{$searchTermDB}' AND `gender` LIKE '{$searchgenderTermDB}' ";
      
      
      $searchResult = mysql_query($searchSQL) or trigger_error("There was an error.<br/>" . mysql_error() . "<br />SQL Was: {$searchSQL}");
      
      if (mysql_num_rows($searchResult) < 1) {
         $error[] = "Sorry, we have no record of the name<br /> {$searchTerms} ({$searchgenderTerms}).";
      }else {
         $results = array(); // And now display results...
         $i = 1;
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: <span id=\\"result\\">{$row['name']}</span><br /> Gender: <span id=\\"result\\">{$row['gender']}</span><br /> Origin: <span id=\\"result\\">{$row['origin']}</span><br /> Meaning: <span id=\\"result\\">{$row['meaning']}</span><br /><br />"; $i++;
         }
      }
   }
}

function removeEmpty($var) {
   return (!empty($var)); 
}
?>

The changes I want to make:

  1. The following part of the above script:
   if (strlen($searchTerms) < 3) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }

This prevents SQL injection. But I want to add a set of 26 links (A-Z) to allow people to click the first letter and bring up a list of names beginning with that letter. I can’t do this with the above code active because such searches would be filtered out. So how do I remove the above piece of code and still prevent SQL injections.

  1. The code which controls the form and how the results are displayed is as follows:
<html>
   <body>
      <?php echo (count($error) > 0)?"<strong>Error</strong>: <br /><span id=\\"error\\">" . implode("<br />", $error) . "</span><br /><br />":""; ?> <form method="GET" action="<?php echo $_SERVER['../../../PHP_SELF'];?>" name="searchForm"> <strong>Enter a name to find it's origin and meaning: </strong> <input type="text" name="search" value="<?php echo isset($searchTerms)?htmlspecialchars($searchTerms):''; ?>" /> <br /><br />
      <strong>Select Gender:</strong> <SELECT name="searchgender" value="<?php echo isset($searchgenderTerms)?htmlspecialchars($searchgenderTerms):''; ?>" />
      <option>Male</option>
      <option>Female</option>
      </SELECT>
      <br /><br />
         <input type="submit" name="submit" value="Search!" />
      </form>
      <?php echo (count($results) > 0)?"You searched for: <span id=\\"terms\\">{$searchTerms} ({$searchgenderTerms})</span> - Here are your results:<br /><br />" . implode("", $results):""; ?>
   </body>
</html>

I want to change this so that the results are displayed as links instead. For example: I will search for Chris and the results will be displayed as a list of links such as “Chris, Christopher, Christian” and the links (when clicked) provide the full details.

The script can currently be seen in action at the following URL:

I've Got Kids!: Baby Name Finder

I hope somebody can help me make these changes :slight_smile:

So how do I remove the above piece of code and still prevent SQL injections.

Simple, just remove the piece of code that checks for the length:


//if (strlen($searchTerms) < 3) { // Checks search term is longer than 3 characters.
//      $error[] = "Search terms must be longer than 3 characters.";
//   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
//   }

You can try just commenting out the lines, like I did here, or delete them entirely. However, if you want to keep the general restriction that the search has to have at least three characters, but still allow a-z searches, do this:


$atoz = range( 'a', 'z' );
if (strlen($searchTerms) < 3 and !in_array($searchTerms, $atoz)) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }

Then your a-z will still pass the first criteria and be included in the search. Alternately, you could pass it along with something other than the $searchTerms variable.

I want to change this so that the results are displayed as links instead.

This part is easy enough, though you’ll have to modify the links themselves to get them to point where you want them to:


<?php 
if (count($results) > 0)) {
   echo "You searched for: <span id=\\"terms\\">{$searchTerms} ({$searchgenderTerms})</span> - Here are your results:<br /><br />";
   foreach ( $results as $value ) {
      echo '<a href="viewMoreInfoPage.php?someRef=Ref">' . $value . '</a><br />';
   }
}
?>

Hi & Thanks.

Sorry for the delay in responding - I had moved on to other areas of the site whilst I waited for some answers to this and have only just got around to getting back to checking it.

I’ve tried the above solution and when I enter a search time, like “b” and click Search it doesn’t display any results… it redirects the page to the following URL:

http://xxxxx.com/babynames.php?search=b&searchgender=Male&submit=Search%21

But this page is completely blank.

Sorry but I’ve had to obscure the domain name because as of now this is a closed site and I have to protect my non disclosure agreement for my client until the site is ready to launch. But the full script is below:


&lt;phpcode&gt;&lt;?php

$dbHost = 'localhost';
$dbUser = 'xxxxxxxxx'; 
$dbPass = 'xxxxxxxxx';
$dbDatabase = 'xxxxxxxxxxxxx';
$con = mysql_connect($dbHost, $dbUser, $dbPass) or trigger_error("Failed to connect to MySQL Server. Error: " . mysql_error());
$params = array($_POST['name'], $_POST['gender']);

mysql_select_db($dbDatabase) or trigger_error("Failed to connect to database {$dbDatabase}. Error: " . mysql_error());

// Set up error check and result check array
$error = array();
$results = array();

// First check if a form was submitted
if (isset($_GET['search'])) {
   $searchTerms = trim($_GET['search']);
   $searchTerms = strip_tags($searchTerms); // removes any html/javascript.
   
if (isset($_GET['searchgender'])) {
   $searchgenderTerms = trim($_GET['searchgender']);
   $searchgenderTerms = strip_tags($searchgenderTerms); // removes any html/javascript.


$atoz = range( 'a', 'z' );
if (strlen($searchTerms) &lt; 3 and !in_array($searchTerms, $atoz)) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }  
   
}

   // If there are no errors, search begins...
   if (count($error) &lt; 1) {

//The Query
$searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE `name` LIKE '%{$searchTermDB}%' AND `gender` LIKE '{$searchgenderTermDB}' ";
$stmt = sqlsrv_query($conn, $searchSQL, $params);       
      
      $searchResult = mysql_query($searchSQL) or trigger_error("There was an error.&lt;br/&gt;" . mysql_error() . "&lt;br /&gt;SQL Was: {$searchSQL}");
      
      if (mysql_num_rows($searchResult) &lt; 1) {
         $error[] = "Sorry, we have no record of the name&lt;br /&gt; {$searchTerms} ({$searchgenderTerms}).";
      }else {
         $results = array(); // And now display results...
         $i = 1;
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: &lt;span id=\\"result\\"&gt;{$row['name']}&lt;/span&gt;&lt;br /&gt; Gender: &lt;span id=\\"result\\"&gt;{$row['gender']}&lt;/span&gt;&lt;br /&gt; Origin: &lt;span id=\\"result\\"&gt;{$row['origin']}&lt;/span&gt;&lt;br /&gt; Meaning: &lt;span id=\\"result\\"&gt;{$row['meaning']}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;"; $i++;
         }
      }
   }
}

function removeEmpty($var) {
   return (!empty($var)); 
}
?&gt;

&lt;?php echo (count($error) &gt; 0)?"&lt;strong&gt;Error&lt;/strong&gt;: &lt;br /&gt;&lt;span id=\\"error\\"&gt;" . implode("&lt;br /&gt;", $error) . "&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;":""; ?&gt; &lt;form method="GET" action="&lt;?php echo $_SERVER['../../../PHP_SELF'];?&gt;" name="searchForm"&gt; &lt;strong&gt;Enter a name to find it's origin and meaning: &lt;/strong&gt; &lt;input type="text" name="search" value="&lt;?php echo isset($searchTerms)?htmlspecialchars($searchTerms):''; ?&gt;" /&gt; &lt;br /&gt;&lt;br /&gt;
      &lt;strong&gt;Select Gender:&lt;/strong&gt; &lt;SELECT name="searchgender" value="&lt;?php echo isset($searchgenderTerms)?htmlspecialchars($searchgenderTerms):''; ?&gt;" /&gt;
      &lt;option&gt;Male&lt;/option&gt;
      &lt;option&gt;Female&lt;/option&gt;
      &lt;/SELECT&gt;
      &lt;br /&gt;&lt;br /&gt;
         &lt;input type="submit" name="submit" value="Search!" /&gt;
      &lt;/form&gt;
      &lt;?php echo (count($results) &gt; 0)?"You searched for: &lt;span id=\\"terms\\"&gt;{$searchTerms} ({$searchgenderTerms})&lt;/span&gt; - Here are your results:&lt;br /&gt;&lt;br /&gt;" . implode("", $results):""; ?&gt;
	  

Could someone help me sort this out please?

A blank page suggests a coding error. What is your error reporting set to? Your script should be putting something on the screen, even with an empty result. If you don’t know, add this line to the top of the script:

error_reporting( -1 );

I do see one change you should make, if you want to get every name that starts with a letter, like “b”:

$searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE name LIKE ‘{$searchTermDB}%’ AND gender LIKE ‘{$searchgenderTermDB}’ ";

I removed the first % from $searchTermDB, because that signals that you want it to start with that term, otherwise you would get all names that have a “b” in them.

Also, if you are not using the wildcard in the gender term, you should probably change that from LIKE to =.

Without setting up a database with values, I don’t know what might be going wrong after a search. I would suggest upping your error reporting level and see what it says.

I see a couple of things.

$con = mysql_connect($dbHost, $dbUser, $dbPass)
$stmt = sqlsrv_query($conn, $searchSQL, $params);
$searchResult = mysql_query($searchSQL)

Why are we executing 2 queries, on 2 entirely different database connections, and doing absolutely nothing with one of them?
Is sqlsrv_query defined somewhere? Because it’s not a normal function.

Hey Cute Think,

Thanks for pointing out the wildcard issue - I had intended to have it at the end only so I’ve changed that. I’ve also changed the LIKE for Gender to an = as per your suggestion.

I ran the script again once more after I made these changes and I no longer get a blank page. I do, however, still get an error for anything under 3 letters even if it is within the specified range of A-Z.

StarLion, I have commented out the line of code you brought to light. It doesn’t seem to have any effect on the script so I assume I must have put it there in error. The script does the same thing with or without it.

You can try the script for yourself at http://ivegotkids.com/babynames.php - I’ve been given permission to disclose this on here.

So… Now the blank page issue is gone - any idea why my A-Z isn’t working?

Here is the up to date code:

&lt;?php

$dbHost = 'xxxxxxxx';
$dbUser = 'xxxxxxxx'; 
$dbPass = 'xxxxxxxx';
$dbDatabase = 'xxxxxxxx';
$con = mysql_connect($dbHost, $dbUser, $dbPass) or trigger_error("Failed to connect to MySQL Server. Error: " . mysql_error());
$params = array($_POST['name'], $_POST['gender']);

mysql_select_db($dbDatabase) or trigger_error("Failed to connect to database {$dbDatabase}. Error: " . mysql_error());

// Set up error check and result check array
$error = array();
$results = array();

// First check if a form was submitted
if (isset($_GET['search'])) {
   $searchTerms = trim($_GET['search']);
   $searchTerms = strip_tags($searchTerms); // removes any html/javascript.
   
if (isset($_GET['searchgender'])) {
   $searchgenderTerms = trim($_GET['searchgender']);
   $searchgenderTerms = strip_tags($searchgenderTerms); // removes any html/javascript.


$atoz = range( 'a', 'z' );
if (strlen($searchTerms) &lt; 3 and !in_array($searchTerms, $atoz)) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }  
   
}

   // If there are no errors, search begins...
   if (count($error) &lt; 1) {

//The Query
$searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE `name` LIKE '{$searchTermDB}%' AND `gender` = '{$searchgenderTermDB}' ";
//$stmt = sqlsrv_query($conn, $searchSQL, $params);       
      
      $searchResult = mysql_query($searchSQL) or trigger_error("There was an error.&lt;br/&gt;" . mysql_error() . "&lt;br /&gt;SQL Was: {$searchSQL}");
      
      if (mysql_num_rows($searchResult) &lt; 1) {
         $error[] = "Sorry, we have no record of the name&lt;br /&gt; {$searchTerms} ({$searchgenderTerms}).";
      }else {
         $results = array(); // And now display results...
         $i = 1;
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: &lt;span id=\\"result\\"&gt;{$row['name']}&lt;/span&gt;&lt;br /&gt; Gender: &lt;span id=\\"result\\"&gt;{$row['gender']}&lt;/span&gt;&lt;br /&gt; Origin: &lt;span id=\\"result\\"&gt;{$row['origin']}&lt;/span&gt;&lt;br /&gt; Meaning: &lt;span id=\\"result\\"&gt;{$row['meaning']}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;"; $i++;
         }
      }
   }
}

function removeEmpty($var) {
   return (!empty($var)); 
}
?&gt;

&lt;?php echo (count($error) &gt; 0)?"&lt;strong&gt;Error&lt;/strong&gt;: &lt;br /&gt;&lt;span id=\\"error\\"&gt;" . implode("&lt;br /&gt;", $error) . "&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;":""; ?&gt; &lt;form method="GET" action="&lt;?php echo $_SERVER['../../../PHP_SELF'];?&gt;" name="searchForm"&gt; &lt;strong&gt;Enter a name to find it's origin and meaning: &lt;/strong&gt; &lt;input type="text" name="search" value="&lt;?php echo isset($searchTerms)?htmlspecialchars($searchTerms):''; ?&gt;" /&gt; &lt;br /&gt;&lt;br /&gt;
      &lt;strong&gt;Select Gender:&lt;/strong&gt; &lt;SELECT name="searchgender" value="&lt;?php echo isset($searchgenderTerms)?htmlspecialchars($searchgenderTerms):''; ?&gt;" /&gt;
      &lt;option&gt;Male&lt;/option&gt;
      &lt;option&gt;Female&lt;/option&gt;
      &lt;/SELECT&gt;
      &lt;br /&gt;&lt;br /&gt;
         &lt;input type="submit" name="submit" value="Search!" /&gt;
      &lt;/form&gt;
      &lt;?php echo (count($results) &gt; 0)?"You searched for: &lt;span id=\\"terms\\"&gt;{$searchTerms} ({$searchgenderTerms})&lt;/span&gt; - Here are your results:&lt;br /&gt;&lt;br /&gt;" . implode("", $results):""; ?&gt;
	  

I see that it is coming back with an empty result. Try echoing your query out and running it through phpmyadmin or whatever other database administration system you have and see what happens.

Also, it looks like you have a couple other unnecessary lines:
$params = array($_POST[‘name’], $_POST[‘gender’]);

function removeEmpty($var) {
return (!empty($var));
}

And you have some odd {} pairings. It looks like you open a set with if (isset($_GET[‘search’])) { and it doesn’t close until right before function removeEmpty($var) {

Perhaps if you clean that up a bit, it will be easier to track down where the problem lies.

Hi CT

I’ve removed the unnecessary lines of code you pointed out but I don’t know about the odd {} pairings. I’ve tried a few combinations but whatever I change it to it seems to produce the “Search term must be at least 3 characters” error as soon as the page loads before anything is even entered into the box.

Perhaps you could give me a clue as to how to tidy it up a bit?

Here is the most up to date code once more:

$dbHost = '********';
$dbUser = '********'; 
$dbPass = '********';
$dbDatabase = '********';
$con = mysql_connect($dbHost, $dbUser, $dbPass) or trigger_error("Failed to connect to MySQL Server. Error: " . mysql_error());


mysql_select_db($dbDatabase) or trigger_error("Failed to connect to database {$dbDatabase}. Error: " . mysql_error());

// Set up error check and result check array
$error = array();
$results = array();

// First check if a form was submitted
if (isset($_GET['search'])) {
   $searchTerms = trim($_GET['search']);
   $searchTerms = strip_tags($searchTerms); // removes any html/javascript.
   
if (isset($_GET['searchgender'])) {
   $searchgenderTerms = trim($_GET['searchgender']);
   $searchgenderTerms = strip_tags($searchgenderTerms); // removes any html/javascript.


$atoz = range( 'a', 'z' );
if (strlen($searchTerms) &lt; 3 and !in_array($searchTerms, $atoz)) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   }  
   
}

   // If there are no errors, search begins...
   if (count($error) &lt; 1) {

//The Query
$searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE `name` LIKE '{$searchTermDB}%' AND `gender` = '{$searchgenderTermDB}' ";

      
      $searchResult = mysql_query($searchSQL) or trigger_error("There was an error.&lt;br/&gt;" . mysql_error() . "&lt;br /&gt;SQL Was: {$searchSQL}");
      
      if (mysql_num_rows($searchResult) &lt; 1) {
         $error[] = "Sorry, we have no record of the name&lt;br /&gt; {$searchTerms} ({$searchgenderTerms}).";
      }else {
         $results = array(); // And now display results...
         $i = 1;
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: &lt;span id=\\"result\\"&gt;{$row['name']}&lt;/span&gt;&lt;br /&gt; Gender: &lt;span id=\\"result\\"&gt;{$row['gender']}&lt;/span&gt;&lt;br /&gt; Origin: &lt;span id=\\"result\\"&gt;{$row['origin']}&lt;/span&gt;&lt;br /&gt; Meaning: &lt;span id=\\"result\\"&gt;{$row['meaning']}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;"; $i++;
         }
      }
   }
}

?&gt;

&lt;?php echo (count($error) &gt; 0)?"&lt;strong&gt;Error&lt;/strong&gt;: &lt;br /&gt;&lt;span id=\\"error\\"&gt;" . implode("&lt;br /&gt;", $error) . "&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;":""; ?&gt; &lt;form method="GET" action="&lt;?php echo $_SERVER['../../../PHP_SELF'];?&gt;" name="searchForm"&gt; &lt;strong&gt;Enter a name to find it's origin and meaning: &lt;/strong&gt; &lt;input type="text" name="search" value="&lt;?php echo isset($searchTerms)?htmlspecialchars($searchTerms):''; ?&gt;" /&gt; &lt;br /&gt;&lt;br /&gt;
      &lt;strong&gt;Select Gender:&lt;/strong&gt; &lt;SELECT name="searchgender" value="&lt;?php echo isset($searchgenderTerms)?htmlspecialchars($searchgenderTerms):''; ?&gt;" /&gt;
      &lt;option&gt;Male&lt;/option&gt;
      &lt;option&gt;Female&lt;/option&gt;
      &lt;/SELECT&gt;
      &lt;br /&gt;&lt;br /&gt;
         &lt;input type="submit" name="submit" value="Search!" /&gt;
      &lt;/form&gt;
      &lt;?php echo (count($results) &gt; 0)?"You searched for: &lt;span id=\\"terms\\"&gt;{$searchTerms} ({$searchgenderTerms})&lt;/span&gt; - Here are your results:&lt;br /&gt;&lt;br /&gt;" . implode("", $results):""; ?&gt;

Here is a quick tidy of it and I’ll tell you what I did to get it a little more clean:


&lt;?php
$dbHost = '********';
$dbUser = '********';
$dbPass = '********';
$dbDatabase = '********';
$con = mysql_connect($dbHost, $dbUser, $dbPass) or trigger_error("Failed to connect to MySQL Server. Error: " . mysql_error());
 
 
mysql_select_db($dbDatabase) or trigger_error("Failed to connect to database {$dbDatabase}. Error: " . mysql_error());
 
// Set up error check and result check array
$error = array();
$results = array();
$searchTerms = '';
$searchgenderTerms = '';
 
// First check if a form was submitted

if (isset($_GET['search']) and isset($_GET['searchgender'])) {

   $searchTerms = trim($_GET['search']);
   $searchTerms = strip_tags($searchTerms); // removes any html/javascript.
   
   $searchgenderTerms = trim($_GET['searchgender']);
   $searchgenderTerms = strip_tags($searchgenderTerms); // removes any html/javascript. 
 
   $atoz = range( 'a', 'z' );
   if (strlen($searchTerms) &lt; 3 and !in_array($searchTerms, $atoz)) { // Checks search term is longer than 3 characters.
      $error[] = "Search terms must be longer than 3 characters.";
   }  
   else {
      $searchTermDB = mysql_real_escape_string($searchTerms); // Prevents sql injection.
   } 
		
   // If there are no errors, search begins...
   if (count($error) &lt; 1) {
	 
      //The Query
      $searchSQL = "SELECT name, gender, meaning, origin FROM names WHERE `name` LIKE '{$searchTermDB}%' AND `gender` = '{$searchgenderTermDB}' ";
	 
      $searchResult = mysql_query($searchSQL) or trigger_error("There was an error.&lt;br/&gt;" . mysql_error() . "&lt;br /&gt;SQL Was: {$searchSQL}");
		  
      if (mysql_num_rows($searchResult) &lt; 1) {
         $error[] = "Sorry, we have no record of the name&lt;br /&gt; {$searchTerms} ({$searchgenderTerms}).";
      }
		
      else {
		
         // And now display results...
         $i = 1;
			
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: &lt;span id=\\"result\\"&gt;{$row['name']}&lt;/span&gt;&lt;br /&gt; " .
               "Gender: &lt;span id=\\"result\\"&gt;{$row['gender']}&lt;/span&gt;&lt;br /&gt; " .
               "Origin: &lt;span id=\\"result\\"&gt;{$row['origin']}&lt;/span&gt;&lt;br /&gt; " .
               "Meaning: &lt;span id=\\"result\\"&gt;{$row['meaning']}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;"; 
					
            $i++;
         }

      }
		
   }

}
?&gt;
 
&lt;?php echo (count($error) &gt; 0)?"&lt;strong&gt;Error&lt;/strong&gt;: &lt;br /&gt;&lt;span id=\\"error\\"&gt;" . implode("&lt;br /&gt;", $error) . "&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;":""; ?&gt; 
&lt;form method="GET" action="&lt;?php echo $_SERVER['../../../PHP_SELF'];?&gt;" name="searchForm"&gt; 
&lt;strong&gt;Enter a name to find it's origin and meaning: &lt;/strong&gt; 
&lt;input type="text" name="search" value="&lt;?php echo htmlspecialchars($searchTerms); ?&gt;" /&gt; &lt;br /&gt;&lt;br /&gt;
&lt;strong&gt;Select Gender:&lt;/strong&gt; 
&lt;SELECT name="searchgender" value="&lt;?php echo htmlspecialchars($searchgenderTerms); ?&gt;" /&gt;
&lt;option&gt;Male&lt;/option&gt;
&lt;option&gt;Female&lt;/option&gt;
&lt;/SELECT&gt;&lt;br /&gt;&lt;br /&gt;
&lt;input type="submit" name="submit" value="Search!" /&gt;
&lt;/form&gt;
&lt;?php echo (count($results) &gt; 0)?"You searched for: &lt;span id=\\"terms\\"&gt;{$searchTerms} ({$searchgenderTerms})&lt;/span&gt; - Here are your results:&lt;br /&gt;&lt;br /&gt;" . implode("", $results):""; ?&gt;

First I established $searchTerms and $searchgenderTerms as blank strings before even checking if the form was submitted, then you don’t have to worry if the variables exist.

Then I combined the two isset() checks for the $_GET variables so it will only process the search if they both exist (you had it this way too, but this is a little cleaner and easier to read with how I have done the tabs). If you indent for each if statement, then you can read the processing order a little better. You did this somewhat, but it was hard to see that the search process was under the first if statement. I hope it doesn’t come through too messed up, because I use Notepad++ and it tabs instead of using spaces and sometimes it displays differently.

I broke up some of your lines to make it a little easier to see all of the code without having to scroll left and right. This is just my preference, but I find it helps in the long run.

I did test part of your script and it should properly allow a-z, but nothing else less than 3 letters. At this point, if you are still getting an error that there are no results, then you should echo $searchSQL and copy it into phpmyadmin (or whatever database administration setup you use) and see what results you get. If you get the results there, then there’s a different error on your page and we can try to track it down.

Hi CT,

Thanks again for continuing to help.

I’ve made the changes you’ve suggested. I no longer get the “must be over 3 characters” error message when the search is in the range of a-z which is good… I do, however, get an error stating there are no results even if I enter a full name exactly as it is stored in the database.

I have run the SQL command “SELECT name, gender, meaning, origin FROM names WHERE name LIKE ‘{$searchTermDB}%’ AND gender = '{$searchgenderTermDB}” directly in phpmyadmin, replacing the {$searchTermDB} and {$searchgenderTermDB} with a name and gender and it works perfectly so the problem is somewhere in this script.

I suspect it has something to do with this part of it:

if (mysql_num_rows($searchResult) < 1) {
         $error[] = "Sorry, we have no record of the name<br /> {$searchTerms} ({$searchgenderTerms}).";
      }
        
      else {
        
         // And now display results...
         $i = 1;
            
         while ($row = mysql_fetch_assoc($searchResult)) {
            $results[] = "Name: <span id=\\"result\\">{$row['name']}</span><br /> " .
               "Gender: <span id=\\"result\\">{$row['gender']}</span><br /> " .
               "Origin: <span id=\\"result\\">{$row['origin']}</span><br /> " .
               "Meaning: <span id=\\"result\\">{$row['meaning']}</span><br /><br />"; 
                    
            $i++;
         }

      }
        
   }

}
?>

I understand this opens with first checking if the number of results is less than 1 and if so it displays the error and then the “else” should continue with the script if the results are equal to or greater than 1… it seems it’s preferring the error message over all.

That’s why I say to echo the query on your page itself. You need to know what your page is sending to the database and maybe you’ll notice something is not quite right about it.

This is what I get when I echo the search.

SELECT name, gender, meaning, origin FROM names WHERE name LIKE ‘A%’ AND gender = ‘’ Error:
Sorry, we have no record of the name
A (Male).

Fixed it…

Changed {searchgenderTermDB} to {searchgenderTerms} and it works :slight_smile:

Thanks for all your help.

Moving on now…

I’m on to the part where I change how the results are displayed so that they are displayed as links rather than a huge list…

I’ve got your code from your first reply:

<?php 
if (count($results) > 0)) {
   echo "You searched for: <span id=\\"terms\\">{$searchTerms} ({$searchgenderTerms})</span> - Here are your results:<br /><br />";
   foreach ( $results as $value ) {
      echo '<a href="viewMoreInfoPage.php?someRef=Ref">' . $value . '</a><br />';
   }
}
?>

I don’t want to load a new page… I want the results to be displayed in place of the list of links with a “back to results” link to go back to the list if they want to once they have read the details.

Does this make sense?

I think so. What you will need to do then is pass the search choices along with the link to the details and then build the search link on the next page:


echo '<a href="viewMoreInfoPage.php?searchTerms=' . $searchTerms . '&amp;searchgenderTerms=' . $searchgenderTerms . '&amp;name=' . $value . '">' . $value . '</a><br />';

That will pass everything to the next page. Then your link back will have to be careful to submit exactly the same variables names, otherwise your search won’t recognize the results:


echo '<a href="yoursearchpage.php?search=' . $_GET['searchTerms'] . '&amp;searchgender=' . $_GET['searchgender'] . '">Back to results</a>';

If that’s not what you were thinking of, let me know.

Hi CT,

I’ve done as you suggested.

It still lists them all out in their complete format instead of just the names as links. Only now the whole thing becomes a link and when clicked, it just resets the search form.

This is the code:

<?php 
if (count($results) > 0) {
   echo "You searched for: <span id=\\"terms\\">{$searchTerms} ({$searchgenderTerms})</span> - Here are your results:<br /><br />";
   foreach ( $results as $value ) {
      echo '<a href="babynames.php?searchTerms=' . $searchTerms . '&amp;searchgenderTerms=' . $searchgenderTerms . '&amp;name=' . $value . '">' . $value . '</a><br />';
   }
}
?>

And you can see what it does here:

http://ivegotkids.com/babynames.php

The links aren’t closing. If you look at the HTML produced, you can see that the name is a long value covering all of the result parts. We need to make a small adjustment to how the link is made.

If we change the result array a bit:


while ($row = mysql_fetch_assoc($searchResult)) {
            $results[$row['name']] = "Name: <span id=\\"result\\">{$row['name']}</span><br /> " .
               "Gender: <span id=\\"result\\">{$row['gender']}</span><br /> " .
               "Origin: <span id=\\"result\\">{$row['origin']}</span><br /> " .
               "Meaning: <span id=\\"result\\">{$row['meaning']}</span><br /><br />"; 

Then we can do this:


foreach ( $results as $key => $value ) {
      echo '<a href="babynames.php?searchTerms=' . $searchTerms . '&amp;searchgenderTerms=' . $searchgenderTerms . '&amp;name=' . $key . '">' . $value . '</a><br />';
   } 

That assumes that you would pass the name to the next page to get whatever other information that you want to view. That should clean up the page a little.

Something is bemusing me here, how many “gender terms” are there?

is it not just male/female ?

[ot]

Hermaphrodite? :shifty:
Gender-less? [/ot]

Off Topic:

Or even tax collectors.