Blame templates/html/search_functions.php

Packit Service 50c9f2
<script language="PHP">
Packit Service 50c9f2
require_once "search_config.php";
Packit Service 50c9f2
Packit Service 50c9f2
function end_form($value)
Packit Service 50c9f2
{
Packit Service 50c9f2
  global $config;
Packit Service 50c9f2
  global $translator;
Packit Service 50c9f2
  if ($config['DISABLE_INDEX'] == false)
Packit Service 50c9f2
  {
Packit Service 50c9f2
  echo "            <input type=\"text\" id=\"MSearchField\" name=\"query\" value=\"$value\" size=\"20\" accesskey=\"S\" onfocus=\"searchBox.OnSearchFieldFocus(true)\" onblur=\"searchBox.OnSearchFieldFocus(false)\"/>\n            </form>\n          
\n \n \n \n \n\n";
Packit Service 50c9f2
  }
Packit Service 50c9f2
  if ($config['GENERATE_TREEVIEW'])
Packit Service 50c9f2
  {
Packit Service 50c9f2
    echo $translator['split_bar'];
Packit Service 50c9f2
  }
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function end_page()
Packit Service 50c9f2
{
Packit Service 50c9f2
  echo "</body></html>";
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function search_results()
Packit Service 50c9f2
{
Packit Service 50c9f2
  global $translator;
Packit Service 50c9f2
  return $translator['search_results_title'];
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function matches_text($num)
Packit Service 50c9f2
{
Packit Service 50c9f2
  global $translator;
Packit Service 50c9f2
  $string = $translator['search_results'][($num>2)?2:$num];
Packit Service 50c9f2
  // The eval is used so that translator strings can contain $num.
Packit Service 50c9f2
  eval("\$result = \"$string\";");
Packit Service 50c9f2
  return $result;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function report_matches()
Packit Service 50c9f2
{
Packit Service 50c9f2
  global $translator;
Packit Service 50c9f2
  return $translator['search_matches'];
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function readInt($file)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $b1 = ord(fgetc($file)); $b2 = ord(fgetc($file));
Packit Service 50c9f2
  $b3 = ord(fgetc($file)); $b4 = ord(fgetc($file));
Packit Service 50c9f2
  return ($b1<<24)|($b2<<16)|($b3<<8)|$b4;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function readString($file)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $result="";
Packit Service 50c9f2
  while (ord($c=fgetc($file))) $result.=$c;
Packit Service 50c9f2
  return $result;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function readHeader($file)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $header =fgetc($file); $header.=fgetc($file);
Packit Service 50c9f2
  $header.=fgetc($file); $header.=fgetc($file);
Packit Service 50c9f2
  return $header;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function computeIndex($word)
Packit Service 50c9f2
{
Packit Service 50c9f2
  // Simple hashing that allows for substring search
Packit Service 50c9f2
  if (strlen($word)<2) return -1;
Packit Service 50c9f2
  // high char of the index
Packit Service 50c9f2
  $hi = ord($word{0});
Packit Service 50c9f2
  if ($hi==0) return -1;
Packit Service 50c9f2
  // low char of the index
Packit Service 50c9f2
  $lo = ord($word{1});
Packit Service 50c9f2
  if ($lo==0) return -1;
Packit Service 50c9f2
  // return index
Packit Service 50c9f2
  return $hi*256+$lo;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function search($file,$word,&$statsList)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $index = computeIndex($word);
Packit Service 50c9f2
  if ($index!=-1) // found a valid index
Packit Service 50c9f2
  {
Packit Service 50c9f2
    fseek($file,$index*4+4); // 4 bytes per entry, skip header
Packit Service 50c9f2
    $index = readInt($file);
Packit Service 50c9f2
    if ($index) // found words matching the hash key
Packit Service 50c9f2
    {
Packit Service 50c9f2
      $start=sizeof($statsList);
Packit Service 50c9f2
      $count=$start;
Packit Service 50c9f2
      fseek($file,$index);
Packit Service 50c9f2
      $w = readString($file);
Packit Service 50c9f2
      while ($w)
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $statIdx = readInt($file);
Packit Service 50c9f2
        if ($word==substr($w,0,strlen($word)))
Packit Service 50c9f2
        { // found word that matches (as substring)
Packit Service 50c9f2
          $statsList[$count++]=array(
Packit Service 50c9f2
              "word"=>$word,
Packit Service 50c9f2
              "match"=>$w,
Packit Service 50c9f2
              "index"=>$statIdx,
Packit Service 50c9f2
              "full"=>strlen($w)==strlen($word),
Packit Service 50c9f2
              "docs"=>array()
Packit Service 50c9f2
              );
Packit Service 50c9f2
        }
Packit Service 50c9f2
        $w = readString($file);
Packit Service 50c9f2
      }
Packit Service 50c9f2
      $totalHi=0;
Packit Service 50c9f2
      $totalFreqHi=0;
Packit Service 50c9f2
      $totalFreqLo=0;
Packit Service 50c9f2
      for ($count=$start;$count
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $statInfo = &$statsList[$count];
Packit Service 50c9f2
        $multiplier = 1;
Packit Service 50c9f2
        // whole word matches have a double weight
Packit Service 50c9f2
        if ($statInfo["full"]) $multiplier=2;
Packit Service 50c9f2
        fseek($file,$statInfo["index"]); 
Packit Service 50c9f2
        $numDocs = readInt($file);
Packit Service 50c9f2
        $docInfo = array();
Packit Service 50c9f2
        // read docs info + occurrence frequency of the word
Packit Service 50c9f2
        for ($i=0;$i<$numDocs;$i++)
Packit Service 50c9f2
        {
Packit Service 50c9f2
          $idx=readInt($file); 
Packit Service 50c9f2
          $freq=readInt($file); 
Packit Service 50c9f2
          $docInfo[$i]=array("idx"  => $idx,
Packit Service 50c9f2
                             "freq" => $freq>>1,
Packit Service 50c9f2
                             "rank" => 0.0,
Packit Service 50c9f2
                             "hi"   => $freq&1
Packit Service 50c9f2
                            );
Packit Service 50c9f2
          if ($freq&1) // word occurs in high priority doc
Packit Service 50c9f2
          {
Packit Service 50c9f2
            $totalHi++;
Packit Service 50c9f2
            $totalFreqHi+=$freq*$multiplier;
Packit Service 50c9f2
          }
Packit Service 50c9f2
          else // word occurs in low priority doc
Packit Service 50c9f2
          {
Packit Service 50c9f2
            $totalFreqLo+=$freq*$multiplier;
Packit Service 50c9f2
          }
Packit Service 50c9f2
        }
Packit Service 50c9f2
        // read name and url info for the doc
Packit Service 50c9f2
        for ($i=0;$i<$numDocs;$i++)
Packit Service 50c9f2
        {
Packit Service 50c9f2
          fseek($file,$docInfo[$i]["idx"]);
Packit Service 50c9f2
          $docInfo[$i]["name"]=readString($file);
Packit Service 50c9f2
          $docInfo[$i]["url"]=readString($file);
Packit Service 50c9f2
        }
Packit Service 50c9f2
        $statInfo["docs"]=$docInfo;
Packit Service 50c9f2
      }
Packit Service 50c9f2
      $totalFreq=($totalHi+1)*$totalFreqLo + $totalFreqHi;
Packit Service 50c9f2
      for ($count=$start;$count
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $statInfo = &$statsList[$count];
Packit Service 50c9f2
        $multiplier = 1;
Packit Service 50c9f2
        // whole word matches have a double weight
Packit Service 50c9f2
        if ($statInfo["full"]) $multiplier=2;
Packit Service 50c9f2
        for ($i=0;$i
Packit Service 50c9f2
        {
Packit Service 50c9f2
          $docInfo = &$statInfo["docs"];
Packit Service 50c9f2
          // compute frequency rank of the word in each doc
Packit Service 50c9f2
          $freq=$docInfo[$i]["freq"];
Packit Service 50c9f2
          if ($docInfo[$i]["hi"])
Packit Service 50c9f2
          {
Packit Service 50c9f2
            $statInfo["docs"][$i]["rank"]=
Packit Service 50c9f2
              (float)($freq*$multiplier+$totalFreqLo)/$totalFreq;
Packit Service 50c9f2
          }
Packit Service 50c9f2
          else
Packit Service 50c9f2
          {
Packit Service 50c9f2
            $statInfo["docs"][$i]["rank"]=
Packit Service 50c9f2
              (float)($freq*$multiplier)/$totalFreq;
Packit Service 50c9f2
          }
Packit Service 50c9f2
        }
Packit Service 50c9f2
      }
Packit Service 50c9f2
    }
Packit Service 50c9f2
  }
Packit Service 50c9f2
  return $statsList;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function combine_results($results,&$docs)
Packit Service 50c9f2
{
Packit Service 50c9f2
  foreach ($results as $wordInfo)
Packit Service 50c9f2
  {
Packit Service 50c9f2
    $docsList = &$wordInfo["docs"];
Packit Service 50c9f2
    foreach ($docsList as $di)
Packit Service 50c9f2
    {
Packit Service 50c9f2
      $key=$di["url"];
Packit Service 50c9f2
      $rank=$di["rank"];
Packit Service 50c9f2
      if (isset($docs[$key]))
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $docs[$key]["rank"]+=$rank;
Packit Service 50c9f2
      }
Packit Service 50c9f2
      else
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $docs[$key] = array("url"=>$key,
Packit Service 50c9f2
            "name"=>$di["name"],
Packit Service 50c9f2
            "rank"=>$rank
Packit Service 50c9f2
            );
Packit Service 50c9f2
      }
Packit Service 50c9f2
      $docs[$key]["words"][] = array(
Packit Service 50c9f2
               "word"=>$wordInfo["word"],
Packit Service 50c9f2
               "match"=>$wordInfo["match"],
Packit Service 50c9f2
               "freq"=>$di["freq"]
Packit Service 50c9f2
               );
Packit Service 50c9f2
    }
Packit Service 50c9f2
  }
Packit Service 50c9f2
  return $docs;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function filter_results($docs,&$requiredWords,&$forbiddenWords)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $filteredDocs=array();
Packit Service 50c9f2
  while (list ($key, $val) = each ($docs)) 
Packit Service 50c9f2
  {
Packit Service 50c9f2
    $words = &$docs[$key]["words"];
Packit Service 50c9f2
    $copy=1; // copy entry by default
Packit Service 50c9f2
    if (sizeof($requiredWords)>0)
Packit Service 50c9f2
    {
Packit Service 50c9f2
      foreach ($requiredWords as $reqWord)
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $found=0;
Packit Service 50c9f2
        foreach ($words as $wordInfo)
Packit Service 50c9f2
        { 
Packit Service 50c9f2
          $found = $wordInfo["word"]==$reqWord;
Packit Service 50c9f2
          if ($found) break;
Packit Service 50c9f2
        }
Packit Service 50c9f2
        if (!$found) 
Packit Service 50c9f2
        {
Packit Service 50c9f2
          $copy=0; // document contains none of the required words
Packit Service 50c9f2
          break;
Packit Service 50c9f2
        }
Packit Service 50c9f2
      }
Packit Service 50c9f2
    }
Packit Service 50c9f2
    if (sizeof($forbiddenWords)>0)
Packit Service 50c9f2
    {
Packit Service 50c9f2
      foreach ($words as $wordInfo)
Packit Service 50c9f2
      {
Packit Service 50c9f2
        if (in_array($wordInfo["word"],$forbiddenWords))
Packit Service 50c9f2
        {
Packit Service 50c9f2
          $copy=0; // document contains a forbidden word
Packit Service 50c9f2
          break;
Packit Service 50c9f2
        }
Packit Service 50c9f2
      }
Packit Service 50c9f2
    }
Packit Service 50c9f2
    if ($copy) $filteredDocs[$key]=$docs[$key];
Packit Service 50c9f2
  }
Packit Service 50c9f2
  return $filteredDocs;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function compare_rank($a,$b)
Packit Service 50c9f2
{
Packit Service 50c9f2
  if ($a["rank"] == $b["rank"]) 
Packit Service 50c9f2
  {
Packit Service 50c9f2
    return 0;
Packit Service 50c9f2
  }
Packit Service 50c9f2
  return ($a["rank"]>$b["rank"]) ? -1 : 1; 
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function sort_results($docs,&$sorted)
Packit Service 50c9f2
{
Packit Service 50c9f2
  $sorted = $docs;
Packit Service 50c9f2
  usort($sorted,"compare_rank");
Packit Service 50c9f2
  return $sorted;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function report_results(&$docs)
Packit Service 50c9f2
{
Packit Service 50c9f2
  echo "
";
Packit Service 50c9f2
  echo "  
\n";
Packit Service 50c9f2
  echo "    

".search_results()."

\n";
Packit Service 50c9f2
  echo "  \n";
Packit Service 50c9f2
  echo "\n";
Packit Service 50c9f2
  echo "
\n";
Packit Service 50c9f2
  echo "\n";
Packit Service 50c9f2
  $numDocs = sizeof($docs);
Packit Service 50c9f2
  if ($numDocs==0)
Packit Service 50c9f2
  {
Packit Service 50c9f2
    echo "  \n";
Packit Service 50c9f2
    echo "    ".matches_text(0)."\n";
Packit Service 50c9f2
    echo "  \n";
Packit Service 50c9f2
  }
Packit Service 50c9f2
  else
Packit Service 50c9f2
  {
Packit Service 50c9f2
    echo "  \n";
Packit Service 50c9f2
    echo "    ".matches_text($numDocs);
Packit Service 50c9f2
    echo "\n";
Packit Service 50c9f2
    echo "    \n";
Packit Service 50c9f2
    echo "  \n";
Packit Service 50c9f2
    $num=1;
Packit Service 50c9f2
    foreach ($docs as $doc)
Packit Service 50c9f2
    {
Packit Service 50c9f2
      echo "  \n";
Packit Service 50c9f2
      echo "    $num.";
Packit Service 50c9f2
      echo     "".$doc["name"]."\n";
Packit Service 50c9f2
      echo "  \n";
Packit Service 50c9f2
      echo "    ".report_matches()." ";
Packit Service 50c9f2
      foreach ($doc["words"] as $wordInfo)
Packit Service 50c9f2
      {
Packit Service 50c9f2
        $word = $wordInfo["word"];
Packit Service 50c9f2
        $matchRight = substr($wordInfo["match"],strlen($word));
Packit Service 50c9f2
        echo "$word$matchRight(".$wordInfo["freq"].") ";
Packit Service 50c9f2
      }
Packit Service 50c9f2
      echo "    \n";
Packit Service 50c9f2
      echo "  \n";
Packit Service 50c9f2
      $num++;
Packit Service 50c9f2
    }
Packit Service 50c9f2
  }
Packit Service 50c9f2
  echo "\n";
Packit Service 50c9f2
  echo "\n";
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function run_query($query)
Packit Service 50c9f2
{
Packit Service 50c9f2
  if(strcmp('4.1.0', phpversion()) > 0) 
Packit Service 50c9f2
  {
Packit Service 50c9f2
    die("Error: PHP version 4.1.0 or above required!");
Packit Service 50c9f2
  }
Packit Service 50c9f2
  if (!($file=fopen("search/search.idx","rb"))) 
Packit Service 50c9f2
  {
Packit Service 50c9f2
    die("Error: Search index file could NOT be opened!");
Packit Service 50c9f2
  }
Packit Service 50c9f2
  if (readHeader($file)!="DOXS")
Packit Service 50c9f2
  {
Packit Service 50c9f2
    die("Error: Header of index file is invalid!");
Packit Service 50c9f2
  }
Packit Service 50c9f2
  $results = array();
Packit Service 50c9f2
  $requiredWords = array();
Packit Service 50c9f2
  $forbiddenWords = array();
Packit Service 50c9f2
  $foundWords = array();
Packit Service 50c9f2
  $word=strtok($query," ");
Packit Service 50c9f2
  while ($word) // for each word in the search query
Packit Service 50c9f2
  {
Packit Service 50c9f2
    if (($word{0}=='+')) { $word=substr($word,1); $requiredWords[]=$word; }
Packit Service 50c9f2
    if (($word{0}=='-')) { $word=substr($word,1); $forbiddenWords[]=$word; }
Packit Service 50c9f2
    if (!in_array($word,$foundWords))
Packit Service 50c9f2
    {
Packit Service 50c9f2
      $foundWords[]=$word;
Packit Service 50c9f2
      search($file,strtolower($word),$results);
Packit Service 50c9f2
    }
Packit Service 50c9f2
    $word=strtok(" ");
Packit Service 50c9f2
  }
Packit Service 50c9f2
  fclose($file);
Packit Service 50c9f2
  $docs = array();
Packit Service 50c9f2
  combine_results($results,$docs);
Packit Service 50c9f2
  // filter out documents with forbidden word or that do not contain
Packit Service 50c9f2
  // required words
Packit Service 50c9f2
  $filteredDocs = filter_results($docs,$requiredWords,$forbiddenWords);
Packit Service 50c9f2
  // sort the results based on rank
Packit Service 50c9f2
  $sorted = array();
Packit Service 50c9f2
  sort_results($filteredDocs,$sorted);
Packit Service 50c9f2
  return $sorted;
Packit Service 50c9f2
}
Packit Service 50c9f2
Packit Service 50c9f2
function main()
Packit Service 50c9f2
{
Packit Service 50c9f2
  $query = "";
Packit Service 50c9f2
  if (array_key_exists("query", $_GET))
Packit Service 50c9f2
  {
Packit Service 50c9f2
    $query=$_GET["query"];
Packit Service 50c9f2
  }
Packit Service 50c9f2
  $sorted = run_query($query);
Packit Service 50c9f2
  // Now output the HTML stuff...
Packit Service 50c9f2
  // End the HTML form
Packit Service 50c9f2
  end_form(preg_replace("/[^a-zA-Z0-9\-\_\.\x80-\xFF]/i", " ", $query ));
Packit Service 50c9f2
  // report results to the user
Packit Service 50c9f2
  report_results($sorted);
Packit Service 50c9f2
  end_page();
Packit Service 50c9f2
}
Packit Service 50c9f2
</script>