Page 1 of 2

Search with wildcards

Posted: Mon Sep 01, 2008 12:11 pm
by GDS
Using wildcards in search

This little modification on the search module makes it possible to use the wildcards % and _  in search phrases, where % replaces zero or more charactes, and _ replaces one character.

action.dosearch on line 27:

# $ary[] = "word = " . $db->qstr($word);
$ary[] = "word LIKE " . $db->qstr($word);


No other modifications seems to be needed. (except documentation)

GDS

Re: Search with wildcards

Posted: Tue Sep 02, 2008 1:11 pm
by GDS
I suppose I should have posted this in the Tips and Tricks section?

_ and % are the usual wildcards for mySQL, but it would be relatively
easy to replace _ and % with the more common wildcards ? and *
if preferred.

GDS

Re: Search with wildcards

Posted: Wed Sep 03, 2008 7:17 am
by Russ
Or just set a button on the form for 'fuzzy' search or normal ? and then pick that up? You could then apply the '%' in code?

Re: Search with wildcards

Posted: Thu Sep 04, 2008 8:04 am
by GDS
This might be implemented by using a new parameter searchmode, like this:

{search searchmode="fuzzy" submit="submit fuzzy search"}

Parameters:
(optional) searchmode = "default" - Other values can be "wildcards" or "fuzzy" . Wildcars mode uses wildcards in searchstring, where  % replaces zero or more characters, and _ replaces a single character. Fuzzy inserts a % wildcard  at the end of each word in the searchstring.




GDS

Re: Search with wildcards

Posted: Thu Sep 04, 2008 8:18 am
by Russ
Or put % at the beginning AND the end of the word - very fuzzy?

Re: Search with wildcards

Posted: Sun Sep 07, 2008 1:41 pm
by GDS
I am now testing out a implementation of wildcards, as discussed above.
Here are the changes i have made:


# action:.default.php, Line 45
# GDS:
if(!isset($params['searchmode']))
{
$params['searchmode']='default';
}
$this->smarty->assign('searchmode',$params['searchmode']);
# end


# action.dosearch.php, Line 19: 
  # GDS:
  echo $this->Lang('searchmode').'='.$this->Lang($params['searchmode']);
  #end
if ($nb_words > 0)
{
$ary = array();
foreach ($words as $word)
{
$word = trim($word);
      # GDS:
      # $ary[] = "word = " . $db->qstr($word);         
      switch($params['searchmode']){
       case 'wildcards': {
  $ary[] = "word LIKE " . $db->qstr($word);
}break;
case 'fuzzy': {
  $ary[] = "word LIKE " . $db->qstr($word.'%');
}break;
case 'veryfuzzy': {
  $ary[] = "word LIKE " . $db->qstr('%'.$word.'%');
}break;
       default:{
  $ary[] = "word = " . $db->qstr($word);
       }
      }
      #end
}
$searchphrase = implode(' OR ', $ary);
}


# Search.module.php, Line 172:
  # GDS:
  function GetSearchHtmlTemplate()
  {
    return '{$startform}
    {$searchprompt}: 
   
       
   
{if isset($hidden)}{$hidden}{/if}
{$endform}';
#Added by GDS above (apply this also in custom templates):
  }
  #end


   
# nb_NO.php:
#GDS:
$lang['param_searchmode'] = 'Velg søkemodus: 'default' | 'wildcards' | 'fuzzy' | 'veryfuzzy'    . ';
$lang['searchmode']='søkemodus';
$lang['default']='standard';
$lang['wildcards']='jokertegn';
$lang['fuzzy']='omtrentlig';
$lang['veryfuzzy']='svært omtrentlig';
$lang['help'] = $lang['help'].'Hvordan bruker jeg jokertegn?
Ved hjelp av parametret searchmode kan du endre søkets nøyaktighet:

default - Ingen jokertegn.
wildcard - Bruk jokertegnene % og _ hvor som helst i søketeksten.
(Jokertegnet _ matcher ett tegn, mens % matcher null eller flere tegn.)
fuzzy - Automatisk jokertegn, tilsvarer søkeord%
veryfuzzy - Automatisk jokertegn, tilsvarer %søkeord%
';
#end


# en_US.php:
#GDS:
$lang['param_searchmode'] = 'Select searchmode: 'default' | 'wildcards' | 'fuzzy' | 'veryfuzzy'    . ';
$lang['searchmode']='searchmode';
$lang['default']='default';
$lang['wildcards']='wildcards';
$lang['fuzzy']='fuzzy';
$lang['veryfuzzy']='very fuzzy';
$lang['help'] = $lang['help'].'How do I use wildjards?
You can change the accuracy of the search by using the parameter searchmode:

default - No wildjards.
wildcard - Use the wildcards % and _ anywhere in the searchstring.
(The wildcard _ matches one token, while % matches zero or more tokens.)
fuzzy - A wildcard % is applied automatically, as if writing searchword%
veryfuzzy - Wildcards is applied automatikally on both sides of searcwords, as if writing %searchword%
';
#end



GDS

Re: Search with wildcards

Posted: Mon Sep 08, 2008 8:15 am
by Russ
Whilst I appreciate you doing it this way... {search searchmode="fuzzy" submit="submit fuzzy search"} I still think it would be better to let the user or searcher to have the choice of search types. We, or even the developer, cannot know what people will want to search for or how! So I think it should be in the search form, default to a normal search but have radio buttons for fuzzy search etc.

What does everyone think, it won't make much change to the code and only small changes to the form. Doing it this way a simple or fuzzy search box could be used.

Russ

Re: Search with wildcards

Posted: Tue Sep 16, 2008 3:49 pm
by GDS
Hi Russ,
will this do what you want?
(I personally prefere the solution in the first post, it is simple and powerful)

GDS

# Search.module.php, Line 25:
#GDS
class Mode {
var $value='default';
function IsChecked($X){
  if($this->value==$X) return 'checked';
  else return '';
}
}
#end


# Search.module.php Line 151:   
#GDS:
    $this->CreateParameter('searchmode','default',$this->Lang('param_searchmode'));
    $this->SetParameterType('searchmode',CLEAN_STRING);
   
    $this->CreateParameter('mode','default',$this->Lang('param_searchmode'));
    $this->SetParameterType('mode',CLEAN_STRING);
#end


# Search.module.php, Line 186:
  function GetSearchHtmlTemplate()
  {
    return '{$startform}
    {$searchprompt}: 
   
  # GDS:     
{literal}
  function expand(a){
   switch(a.nextSibling.style.display){
    case "none" : a.nextSibling.style.display="block";break;
    default     : a.nextSibling.style.display="none";
   }
  }
{/literal}
  »
    IsChecked("default")} >{$default}
    IsChecked("fuzzy")} >{$fuzzy}
    IsChecked("veryfuzzy")} >{$veryfuzzy}
    IsChecked("wildcards")} >{$wildcards}
   
{$use_wildcards}   
   
  #end
   
{if isset($hidden)}{$hidden}{/if}
{$endform}';
  }



# action:.default.php, Line 45
//GDS:
if(!isset($params['mode']))
{
$params['mode']='default';
}
$mode= new Mode;
$mode->value=($params['mode']);
$this->smarty->assign('mode',$mode);
$this->smarty->assign('advanced',$this->Lang('advanced'));
$this->smarty->assign('default',$this->Lang('default'));
$this->smarty->assign('veryfuzzy',$this->Lang('veryfuzzy'));
$this->smarty->assign('fuzzy',$this->Lang('fuzzy'));
$this->smarty->assign('wildcards',$this->Lang('wildcards'));
$this->smarty->assign('use_wildcards',$this->Lang('use_wildcards'));


if(!isset($params['searchmode']))
{
$params['searchmode']='default';
}
$this->smarty->assign('searchmode',$params['searchmode']);
//end



# action.dosearch.php, Line 19: 
# GDS:
echo $this->Lang('searchmode').'='.$this->Lang($params['searchmode']);
if ($nb_words > 0)
{
$ary = array();
foreach ($words as $word)
{
$word = trim($word);
   switch($params['searchmode']){
    case 'wildcards': {
  $ary[] = "word LIKE " . $db->qstr($word);
}break;
case 'fuzzy': {
  $ary[] = "word LIKE " . $db->qstr($word.'%');
}break;
case 'veryfuzzy': {
  $ary[] = "word LIKE " . $db->qstr('%'.$word.'%');
}break;
    default:{
  $ary[] = "word = " . $db->qstr($word);
    }
   }   
}
$searchphrase = implode(' OR ', $ary);
}
#end


   
# nb_NO.php:
#GDS:
$lang['param_searchmode'] = 'Velg søkemodus: 'default' | 'wildcards' | 'fuzzy' | 'veryfuzzy'. ';
$lang['searchmode']='søkemodus';
$lang['default']='eksakt søk';
$lang['fuzzy']='omtrentlig';
$lang['veryfuzzy']='svært omtrentlig';
$lang['wildcards']='bruk jokertegn';
$lang['help']=  $lang['help'].'Hvordan bruker jeg jokertegn?
Ved hjelp av parametret searchmode kan du endre søkets nøyaktighet:

default - Eksakt søk.
fuzzy - Automatisk jokertegn, tilsvarer søkeord%
veryfuzzy - Automatisk jokertegn, tilsvarer %søkeord%
wildcard - Bruk jokertegnene % og _ hvor som helst i søketeksten.
(Jokertegnet _ matcher ett tegn, mens % matcher null eller flere tegn.)
';

$lang['advanced']='avansert søk';
$lang['use_wildcards']='Hvordan bruke jokertegn:_  = 1 tegn% = 0 eller flere tegneksempler: a_ba matcher abbaekvi% matcher ekvivalent';
#end



# en_US.php:
#GDS:
$lang['param_searchmode'] = 'Select searchmode: 'default' | 'wildcards' | 'fuzzy' | 'veryfuzzy'    . ';
$lang['searchmode']='searchmode';
$lang['default']='exact';
$lang['fuzzy']='fuzzy';
$lang['veryfuzzy']='very fuzzy';
$lang['wildcards']='wildcards';
$lang['help'] = $lang['help'].'How do I use wildcards?
You can change the accuracy of the search by using the parameter searchmode:

default - No wildcards.
wildcard - Use the wildcards % and _ anywhere in the searchstring.
(The wildcard _ matches one token, while % matches zero or more tokens.)
fuzzy - A wildcard % is applied automatically, as if writing searchword%
veryfuzzy - Wildcards is applied automatikally on both sides of searcwords, as if writing %searchword%
';

$lang['advanced']='advanced search';
$lang['use_wildcards']='How do I use wildcards:_  = 1 token% = 0 or more tokensexamples: a_ba matches abbaekvi% matches ekvivalence';
#end

Re: Search with wildcards

Posted: Wed Sep 17, 2008 10:22 am
by Russ
Hi GDS, sorry to take so long to get back to you, feeling a bit under the weather...

That all seems to work pretty well, although maybe you need a few changes for your form? I would not have the javascript hide / display for radio buttons. I don't see the point, if people do not want to use the search options they can leave them out of their templates? Also not sure why you had this (you may have a very good reason?)

Code: Select all

<input type="radio" name="{$search_actionid}searchmode" value="default" {$mode->IsChecked("default")} ><span title="word" >{$default}</span><br/>
When I would have expected a fieldset and legend, something like....

Code: Select all

<fieldset>
<legend>Search Options</legend>
<input type="radio" name="{$search_actionid}searchmode" value="default" {$mode->IsChecked("default")} />
<label for=”{$search_actionid}searchmode”>{$default}</label><br/>
... etc ...
{$use_wildcards}   
</fieldset>
As well as the wild cards, perhaps some more explanation to the use of the search options fuzzy and very fuzzy...?
What do you think?

Re: Search with wildcards

Posted: Wed Sep 17, 2008 12:45 pm
by GDS
Hi Russ,
the javascript/hide is ment to keep the options out of way  until the user needs them.

Your knowledge on forms seems to be better than mine.
I ageree that the fuzzy and veryfuzzy could need some explanation,
what text would you suggest?

GDS

Re: Search with wildcards

Posted: Wed Sep 17, 2008 1:32 pm
by Russ
Hi GDS, I think it is better for accessibility to show all options. Also no Javascript to go wrong. This is your "advanced" search form, it is not the one you are going to have at the top of each screen ;-)

OK, to make this even better I think remove fuzzy and use very fuzzy (%word%) - but call it fuzzy.
So we have only three options
* Default
* Fuzzy
* Wildcard

You can change the scope of the search:
Default - normal exact search for word 'Abba', finds 'Abba'
Fuzzy - more fuzzy search for word 'bb',  finds 'Abb' and 'Abba' or 'bba'
Wildcard - Use the wildcards % and _ anywhere in the search string. The wildcard '_' matches one characters, while '%' matches zero or more characters.

What do you think?

Re: Search with wildcards

Posted: Fri Sep 19, 2008 9:56 am
by denli
Hi all,

I am looking for the fuzzy search I only want the search box + search button to show nothing else.
Can you guys show me how I can do this.

Fuzzy - more fuzzy search for word 'bb',  finds 'Abb' and 'Abba' or 'bba'

Thanks
dejo

Re: Search with wildcards

Posted: Fri Sep 19, 2008 10:34 am
by Russ
I think you will find that is what we are playing with above? If you just want to do fuzzy search without altering your form then you will have to alter the action.dosearch.php for fuzzy instead of default as indicated in the GDS code a few posts previous? Is this what you want?

Re: Search with wildcards

Posted: Mon Oct 20, 2008 2:29 pm
by rodeto
I have been trying to implement this option into my search module. But when I upload the changed files I get errors and the site is no longer accessible.
Can one of you guys please help me to implement the fuzzy search option into my site by giving me some more info on how to change the mentioned files, where to add the extra info and what has to go of the original code ?
I would like to have the fuzzy search option as default.

I have a new install CMSMS 1.4.1 and Search Module 1.5.1

Kind regards

Re: Search with wildcards

Posted: Sat Oct 25, 2008 9:52 am
by GDS
Hi Rodeto, if all you want is fuzzy search,
the you need to change action.dosearch on line 27:

# $ary[] = "word = " . $db->qstr($word);
$ary[] = "word LIKE " . $db->qstr($word.'%');


This is a development discussion, these ideas are not quality tested or approved.


GDS