|> Home > Documentation > Latest documentation > Interchange database > Interchange search engine|
Interchange search engine
Interchange implements a search engine which will search the DefaultTables, or any other table, for items based upon user input. It uses either forms or link-based searches which are invoked using the "scan" ActionMap. The search engine provides several Interchange tags and makes use of many variables.
If the search is implemented in a link or in a form, it will always display formatted results on a separate results page, which is an Interchange page that uses some combination of the [search-region] tag, along with the [search-list], [more-list], [more] and other sub-tags, to format and display the results.
The search form
A number of <form> variables can be defined to determine which type of search will be used, which columns in a table should be searched and what the search behaviour should be.
Here is a simple search form:
When the "Search" button is pressed, Interchange will search the DefaultTables table(s) for the string entered into the "mv_searchspec" text field, and will make the results available for display on a results page.
The same search for a fixed string ("shirt", for instance) could be performed with the use of a hot link, using the special "scan" URI. For example:
This mechanism is referred to as a one-click search in this documentation.
The default is to search every column in the table. To restrict the search to a "description" column, the search specification, in the above form, could be modified to add the following:
Or, in a one-click search:
You could use checkboxes or radio button fields to let the user decide on the search parameters, as follows:
Search specifications can be stacked. If more than one checkbox is checked then all of the selected columns will be searched.
Coordinated and joined searches
Interchange can perform a complete range of tests on individual columns in the target table. To use this function, set "mv_coordinate" to "Yes" (or "co=yes" in the one-click syntax). In order to use coordinated searching, the number of search fields must equal the number of search strings.
To make sure that is the case, you can use the "mv_search_map" variable, which allows variables to be mapped to others in the search specification. For example:
The search will work even if the user leaves one of the input fields blank.
Leading/trailing whitespace is stripped from all lines in the "mv_search_map" variable, so it can be positioned as shown for convenience.
Coordinated searches may be joined with the output of another table if one of the "mv_search_field" values is set to a "table:column" pair.
The special "aq" and "tq" query operators only work if the
Text::Query Perl module is installed. This allows Altavista-style searches on columns, using "AND", "OR", "NOT" and "NEAR", with arbitrarily complex parentheses.
A useful search form, using the "aq" operator, could be written as follows:
This searches the "sku", "description", "comment" and "category" columns in the DefaultTables table(s) using the
Text::Query syntax. A valid search string could be "painters NEAR set".
Single table coordinated search example
Multiple table (joined) coordinated search examples
Note that, "nu=0" must be specified in the joined search example, even though that is the default. To avoid having to do this, use the attribute array feature. For example:
The "co=yes" is assumed when using an attribute array to create a search specification.
The multiple table search will check the product's stock status, provided there is an "inventory" table with a "quantity" column, as there is in the Interchange Standard ecommerce demo. If the "inventory" table's "quantity" column is numerically greater than or equal to 1 then the product will be selected, otherwise the product will be deemed to be out of stock and therefore not selected. The tables will be joined using their KEY column.
It always helps to have a "rm" type included in the search. This is used to pre-screen rows so that joining-table accesses only need be made for already-matching entries. If accesses must be made for every row, large searches could be quite slow.
Custom search operators (using SearchOp)
You can write your own search operator (known as a SearchOp) with Interchange's CodeDef configuration directive. For example:
The above custom operator would match "O'Reily" if the user searched for "oreily", and "12-34-56-78" if the user searched for "1234-5678" etc.
The parameters passed to the custom code are as follows:
The CodeDef routine must return a reference to a Perl subroutine. The subroutine will be passed the string to match against, and must return true if a match is found, or false if no match is found.
With the above, you can do this:
See Vend::Search::create_text_query(), in the Interchange source code, for an example of how to return a subroutine that can look into the search object for the associated search specification.
Specifying a search with SQL-style syntax
SQL syntax can be specified for Interchange searches. This is not the same as the external SQL database server search, treated separately below. The SQL-like syntax will act as a filter on the results of a select everything table dump, rather than being sent directly to the SQL server.
This syntax allows this form setup:
If the right hand side of an expression looks like a column (it is not quoted), then the appropriate form variable is substituted. If used in a one-click, the corresponding scratchpad variable is used instead. The assumption is reversed for the left-hand side; If it is a quoted string then the column name is read from the passed values. Otherwise, the column name is taken literally.
Once again, the query is not sent to the SQL server directly. Parentheses will have no effect, and "AND" and "OR" conditions will cause all conditions to be "OR". The searches above would be similar to the following:
Interchange allows a search to be passed in a URI, as described above. The earlier examples looked a little like this:
This is another way to do the same thing:
Assuming your VendURL is "www.example.com/cgi-bin/vlink", those links would translate to the following:
Each of the search specification variables long name and an abbreviated name. For example, both "mv_searchspec" and "se" are equivalent. The abbreviations help to keep the length of one-click search URIs down, while the full names are easier to read in HTML forms.
A one-click search may be specified in three different ways, as follows:
If you want to create an "OR" search URI on the category and artist columns, for the strings "Surreal" and "Gogh", while matching substrings, you could do the following:
In this method of specification, to replace a slash (/) in a file name (for the sp, bd or fi parameters etc.) you must use the shorthand of :: (i.e. sp=results::standard). This may not work for some browsers, so you should probably either put the page in the main pages directory or define the page in a search profile instead.
You can substitute & for / in the specification, and then be able to use / and quotes and spaces in the specification. For example:
Any "unsafe" characters on the resulting URI will be escaped.
You can specify parameters one per line, if you prefer, as follows:
Again, any "unsafe" characters in the resulting URI will be escaped. You may not search for trailing spaces using this method.
You can create a joined search using a parameter array.
The search routine called by the [area] tag automatically adds the other relevant search specification elements, including the "co=yes" to indicate a combined search, as appropriate.
Setting display options with mv_value
You can encode an arbitrary value into the search URI, without having to use URI arguments, by making use of the "mv_value" search parameter. The "mv_value" search specification takes an argument of "var=value".
For example, the following will set a variable that can be displayed on the search results page using [value category_name]:
As well as creating search links and forms, you may also create a search from within a page, and display the results of that search on the same page.
The [loop] tag accepts search parameters and allows you to loop through the results, using [PREFIX-*] tags to display the results. For example, to search for all products in the "Americana" and "Contemporary" categories:
Search parameters are the same as for One-click searches, above.
The advantage of the in-page search is that searches can be embedded within searches, and you can use an ordinary-looking HTML link to get to the page from any external website.
To place an in-page search with the full range of display in a normal results page, you can use the [search-region] tag. This works in the same way as the [loop] tag, above, except that sub-tags such as [search-list], [more-list] and [more] can be placed within the tag's results template. For example:
A search profile can be created in a scratchpad variable, as follows:
You can make use of the search profile by using the following, instead of a full search specification, on your search <form>:
or use the "mp" modifier in a one-click search, as follows:
The search profile is named by placing a name after a __NAME__ token, in one of the listed profile files. Multiple profiles can reside in the same file, if separated by __END__ tokens.
As an added measure of control, the specification is evaluated with the Interchange tag syntax to provide conditional setting of search parameters.
The special "mv_last" variable stops interpretation of any further search variables in the current profile, except for the "mv_dict_look" and "mv_searchspec" variables, which are interpreted in any event.