Highlight Search Results
-
When making a Full-Text Search query,
in addition to retrieving documents that contain the searched terms in the results,
you can also request to get a list of text fragments that highlight the searched terms. -
The highlighted terms can enhance user experience when searching for documents with specific content.
-
This article shows highlighting search results when making a dynamic-query.
For highlighting search results when querying a static-index see highlight index search results.
Highlight - basic example
// Make a full-text search dynamic query:
// ======================================
List<Employee> employeesResults = session
// Make a dynamic query on 'Employees' collection
.Query<Employee>()
// Search for documents containing the term 'sales' in their 'Notes' field
.Search(x => x.Notes, "sales")
// Request to highlight the searched term by calling 'Highlight'
.Highlight(
x => x.Notes, // The document-field name in which we search
35, // Max length of each text fragment
4, // Max number of fragments to return per document
out Highlightings salesHighlights) // An out param for getting the highlighted text fragments
// Execute the query
.ToList();
// Make a full-text search dynamic query:
// ======================================
List<Employee> employeesResults = await asyncSession
// Make a dynamic query on 'Employees' collection
.Query<Employee>()
// Search for documents containing the term 'sales' in their 'Notes' field
.Search(x => x.Notes, "sales")
// Request to highlight the searched term by calling 'Highlight'
.Highlight(
x => x.Notes, // The document-field name in which we search
35, // Max length of each text fragment
4, // Max number of fragments to return per document
out Highlightings salesHighlights) // An out param for getting the highlighted text fragments
// Execute the query
.ToListAsync();
// Make a full-text search dynamic DocumentQuery:
// ==============================================
List<Employee> employeesResults = session.Advanced
// Make a dynamic documentQuery on 'Employees' collection
.DocumentQuery<Employee>()
// Search for documents containing the term 'sales' in their 'Notes' field
.Search(x => x.Notes, "sales")
// Request to highlight the searched term by calling 'Highlight'
.Highlight(
x => x.Notes, // The document-field name in which we search
35, // Max length of each text fragment
4, // Max number of fragments to return per document
out Highlightings salesHighlights) // An out param for getting the highlighted text fragments
// Execute the documentQuery
.ToList();
from "Employees"
where search(Notes, "sales")
include highlight(Notes, 35, 4)
// Process results:
// ================
// 'employeesResults' contains all Employee DOCUMENTS that have 'sales' in their 'Notes' field.
// 'salesHighlights' contains the text FRAGMENTS that highlight the 'sales' term.
StringBuilder builder = new StringBuilder().AppendLine("<ul>");
foreach (var employee in employeesResults)
{
// Call 'GetFragments' to get all fragments for the specified employee Id
string[] fragments = salesHighlights.GetFragments(employee.Id);
foreach (var fragment in fragments)
{
builder.AppendLine(
$"<li>Doc: {employee.Id} Fragment: {fragment}</li>");
}
}
string fragmentsHtml = builder.AppendLine("</ul>").ToString();
// The resulting fragmentsHtml:
// ============================
// <ul>
// <li>Doc: employees/2-A Fragment: company as a <b style="background:yellow">sales</b></li>
// <li>Doc: employees/2-A Fragment: promoted to <b style="background:yellow">sales</b> manager in</li>
// <li>Doc: employees/2-A Fragment: president of <b style="background:yellow">sales</b> in March 1993</li>
// <li>Doc: employees/2-A Fragment: member of the <b style="background:yellow">Sales</b> Management</li>
// <li>Doc: employees/3-A Fragment: hired as a <b style="background:yellow">sales</b> associate in</li>
// <li>Doc: employees/3-A Fragment: promoted to <b style="background:yellow">sales</b> representativ</li>
// <li>Doc: employees/5-A Fragment: company as a <b style="background:yellow">sales</b> representativ</li>
// <li>Doc: employees/5-A Fragment: promoted to <b style="background:yellow">sales</b> manager in</li>
// <li>Doc: employees/5-A Fragment: <b style="background:yellow">Sales</b> Management." </li>
// <li>Doc: employees/6-A Fragment: for the <b style="background:yellow">Sales</b> Professional.</li>
// </ul>
Highlight tags
-
By default, the highlighted term is wrapped with the following html:
<b style="background:yellow">term</b>
-
When requesting to highlight multiple terms,
the background color returned for each different term will be in the following order:- yellow,
- lawngreen,
- aquamarine,
- magenta,
- palegreen,
- coral,
- wheat,
- khaki,
- lime,
- deepskyblue,
- deeppink,
- salmon,
- peachpuff,
- violet,
- mediumpurple,
- palegoldenrod,
- darkkhaki,
- springgreen,
- turquoise,
- powderblue
-
The html tags that wrap the highlighted terms can be customized to any other tags.
See customize tags below.
Highlight results in Studio
View highlighted fragments in the Query View
-
Auto-Index
This is the auto-index that was created by the server to serve the dynamic-query. -
Results tab
The results tab contains the resulting documents that match the provided RQL query. -
Highlight tab
The highlight tab shows the resulting fragments that were included in the query result.
Highlight - customize tags
- The html tags that wrap the highlighted terms can be customized to any other tags.
// Define customized tags to use for highlighting the searched terms
// =================================================================
HighlightingOptions tagsToUse = new HighlightingOptions
{
// Provide strings of your choice to 'PreTags' & 'PostTags', e.g.:
// the first term searched for will be wrapped with '+++'
// the second term searched for will be wrapped with '<<<' & '>>>'
PreTags = new[] { "+++", "<<<" },
PostTags = new[] { "+++", ">>>" }
};
// Make a full-text search dynamic query:
// ======================================
List<Employee> employeesResults = session
.Query<Employee>()
// Search for:
// * documents containing the term 'sales' in their 'Notes' field
// * OR for documents containing the term 'manager' in their 'Title' field
.Search(x => x.Notes, "sales")
.Search(x => x.Title, "manager")
// Call 'Highlight' for each field searched
// Pass 'tagsToUse' to OVERRIDE the default tags used
.Highlight(x => x.Notes, 35, 1, tagsToUse, out Highlightings salesHighlights)
.Highlight(x => x.Title, 35, 1, tagsToUse, out Highlightings managerHighlights)
.ToList();
// Define customized tags to use for highlighting the searched terms
// =================================================================
HighlightingOptions tagsToUse = new HighlightingOptions
{
// Provide strings of your choice to 'PreTags' & 'PostTags', e.g.:
// The first term searched for will be wrapped with '+++'
// the second term searched for will be wrapped with '<<<' & '>>>'
PreTags = new[] { "+++", "<<<" },
PostTags = new[] { "+++", ">>>" }
};
// Make a full-text search dynamic query:
// ======================================
List<Employee> employeesResults = await asyncSession
.Query<Employee>()
// Search for:
// * documents containing the term 'sales' in their 'Notes' field
// * OR for documents containing the term 'manager' in their 'Title' field
.Search(x => x.Notes, "sales")
.Search(x => x.Title, "manager")
// Call 'Highlight' for each field searched
// Pass 'tagsToUse' to OVERRIDE the default tags used
.Highlight(x => x.Notes, 35, 1, tagsToUse, out Highlightings salesHighlights)
.Highlight(x => x.Title, 35, 1, tagsToUse, out Highlightings managerHighlights)
.ToListAsync();
from "Employees"
where (search(Notes, "sales") or search(Title, "manager"))
include highlight(Notes, 35, 1, $p0), highlight(Title, 35, 1, $p1)
{
"p0":{"PreTags":["+++","<<<"],"PostTags":["+++",">>>"]},
"p1":{"PreTags":["+++","<<<"],"PostTags":["+++",">>>"]}
}
// The resulting salesHighlights fragments:
// ========================================
// "for the +++Sales+++ Professional."
// "hired as a +++sales+++ associate in"
// "company as a +++sales+++"
// "company as a +++sales+++ representativ"
// The resulting managerHighlights fragments:
// ==========================================
// "Sales <<<Manager>>>"
Highlight - projected results
- Highlighting can also be used when projecting query results.
// Make a full-text search dynamic query & project results:
// ========================================================
var employeesProjectedResults = session
.Query<Employee>()
// Search for documents containing 'sales' or 'german' in their 'Notes' field
.Search(x => x.Notes, "manager german")
// Request to highlight the searched terms from the 'Notes' field
.Highlight(x => x.Notes, 35, 2, out Highlightings termsHighlights)
// Define the projection
.Select(x => new
{
// These fields will be returned instead of the whole document
// Note: it is Not mandatory to return the field in which we search for the highlights
Name = $"{x.FirstName} {x.LastName}",
x.Title
})
.ToList();
// Make a full-text search dynamic query & project results:
// ========================================================
var employeesProjectedResults = await asyncSession
.Query<Employee>()
// Search for documents containing 'sales' or 'german' in their 'Notes' field
.Search(x => x.Notes, "manager german")
// Request to highlight the searched terms from the 'Notes' field
.Highlight(x => x.Notes, 35, 2, out Highlightings termsHighlights)
// Define the projection
.Select(x => new
{
// These fields will be returned instead of the whole document
// Note: it is Not mandatory to return the field in which we search for the highlights
Name = $"{x.FirstName} {x.LastName}",
x.Title
})
.ToListAsync();
from "Employees" as x
where search(x.Notes, "manager german")
select { Name : "{0} {1}".format(x.FirstName, x.LastName), Title : x.Title }
include highlight(Notes, 35, 2)
// The resulting fragments from termsHighlights:
// =============================================
// "to sales <b style=\"background:yellow\">manager</b> in March"
// "and reads <b style=\"background:lawngreen\">German</b>. He joined"
// "to sales <b style=\"background:yellow\">manager</b> in January"
// "in French and <b style=\"background:lawngreen\">German</b>."
// NOTE: each search term is wrapped with a different color
// 'manager' is wrapped with yellow
// 'german' is wrapped with lawngreen
Syntax
IRavenQueryable<T> Highlight(
string fieldName,
int fragmentLength,
int fragmentCount,
out Highlightings highlightings);
IRavenQueryable<T> Highlight(
string fieldName,
int fragmentLength,
int fragmentCount,
HighlightingOptions options,
out Highlightings highlightings);
IRavenQueryable<T> Highlight(
Expression<Func<T, object>> path,
int fragmentLength,
int fragmentCount,
out Highlightings highlightings);
IRavenQueryable<T> Highlight(
Expression<Func<T, object>> path,
int fragmentLength,
int fragmentCount,
HighlightingOptions options,
out Highlightings highlightings);
Parameter | Type | Description |
---|---|---|
fieldName | string | Name of the field that contains the searched terms to highlight. |
path | Expression<Func<T, object>> |
Path to the field that contains the searched terms to highlight. |
fragmentLength | int | Maximum length of a text fragment. Must be >= 18 . |
fragmentCount | int | Maximum number of text fragments that will be returned. |
options | HighlightingOptions |
Customizing options. |
highlightings | Highlightings |
An 'out' param that will contain the highlighted text fragments for each returned result. |
Highlighting options:
public string GroupKey { get; set; }
public string[] PreTags { get; set; }
public string[] PostTags { get; set; }
Option | Type | Description |
---|---|---|
GroupKey | string | Grouping key for the results. Used when highlighting query results from a Map-Reduce index. If null results are grouped by document ID (default).Note: Highlighting is Not available for dynamic aggregation queries. |
PreTags | string[] | Array of PRE tags used to wrap the highlighted search terms in the text fragments. |
PostTags | string[] | Array of POST tags used to wrap the highlighted search terms in the text fragments. |
Highlightings object:
public string FieldName { get; }
public IEnumerable<string> ResultIndents;
Property | Type | Description |
---|---|---|
FieldName | string | Name of the field that contains the searched terms to highlight. |
ResultIndents | IEumerable<string> |
The resulting keys (document IDs, or the map-reduce keys) |
public string[] GetFragments(string key);
Method | Description |
---|---|
GetFragments | Returns the list of the highlighted text fragments for the passed document ID, or the map-reduce key |