Search API
The Search API is the core functionality of the Seekora SDK, providing powerful full-text search with filtering, faceting, and sorting capabilities.
Basic Search
const results = await client.search('laptop');
Search with Options
const results = await client.search('laptop', {
per_page: 20,
page: 1,
filter_by: 'price:100-500',
facet_by: 'category,brand',
sort_by: 'price:asc',
});
Search Options Reference
Pagination
| Option | Type | Default | Description |
|---|---|---|---|
per_page | number | 10 | Number of results per page |
page | number | 1 | Page number (1-indexed) |
Filtering
| Option | Type | Description |
|---|---|---|
filter / filter_by | string | Filter expression |
Filter Syntax:
// Single filter
filter_by: 'price:100-500'
// Range filter
filter_by: 'price:>=100'
// Multiple filters (AND)
filter_by: 'category:Electronics && brand:Apple'
// Multiple filters (OR)
filter_by: 'category:Electronics || category:Computers'
// Combined
filter_by: 'category:Electronics && (brand:Apple || brand:Samsung)'
Faceting
| Option | Type | Description |
|---|---|---|
facet_by | string | Comma-separated list of facet fields |
max_facet_values | number | Maximum values per facet |
const results = await client.search('laptop', {
facet_by: 'category,brand,color,size',
max_facet_values: 10,
});
// Access facets
console.log(results.facets);
// { category: { counts: [...] }, brand: { counts: [...] }, ... }
Sorting
| Option | Type | Description |
|---|---|---|
sort / sort_by | string | Sort expression |
// Sort by price ascending
sort_by: 'price:asc'
// Sort by price descending
sort_by: 'price:desc'
// Sort by relevance (default)
sort_by: 'relevance:desc'
// Multiple sort fields
sort_by: 'category:asc,price:desc'
Search Fields
| Option | Type | Description |
|---|---|---|
search_fields | string[] | Fields to search in |
field_weights | number[] | Weights for search fields |
const results = await client.search('laptop', {
search_fields: ['title', 'description', 'brand'],
field_weights: [10, 5, 3],
});
Return Fields
| Option | Type | Description |
|---|---|---|
return_fields | string[] | Fields to include in results |
omit_fields | string[] | Fields to exclude from results |
// Only return specific fields
return_fields: ['id', 'title', 'price', 'image']
// Exclude large fields
omit_fields: ['description', 'specifications']
Snippets
| Option | Type | Description |
|---|---|---|
include_snippets | boolean | Include highlighted snippets |
snippet_fields | string[] | Fields for snippets |
snippet_prefix | string | Prefix for highlights |
snippet_suffix | string | Suffix for highlights |
snippet_token_limit | number | Max tokens in snippet |
const results = await client.search('laptop', {
include_snippets: true,
snippet_fields: ['title', 'description'],
snippet_prefix: '<mark>',
snippet_suffix: '</mark>',
});
Grouping
| Option | Type | Description |
|---|---|---|
group_field | string | Field to group by |
group_size | number | Results per group |
// Group by category, 3 results per group
const results = await client.search('laptop', {
group_field: 'category',
group_size: 3,
});
Typo Tolerance
| Option | Type | Description |
|---|---|---|
typo_max | number | Maximum typos allowed |
typo_min_len_1 | number | Min length for 1 typo |
typo_min_len_2 | number | Min length for 2 typos |
typo_timeout_ms | number | Timeout for typo search |
const results = await client.search('laptp', { // typo in query
typo_max: 2,
typo_min_len_1: 4,
typo_min_len_2: 8,
});
Prefix and Infix Matching
| Option | Type | Description |
|---|---|---|
prefix_mode | 'always' | 'fallback' | 'false' | Prefix matching behavior |
infix_mode | 'always' | 'fallback' | 'false' | Infix matching behavior |
// Enable prefix matching for autocomplete-style search
const results = await client.search('lap', {
prefix_mode: 'always',
});
Other Options
| Option | Type | Description |
|---|---|---|
analytics_tags | string[] | Tags for analytics |
widget_mode | boolean | Simplified response format |
require_all_terms | boolean | All terms must match |
exact_match_boost | boolean | Boost exact matches |
cache_results | boolean | Cache results |
apply_rules | boolean | Apply search rules |
preset_name | string | Use a search preset |
search_timeout_ms | number | Search timeout |
Multi-Search
Batch up to 10 independent search queries in a single request. Each query runs independently with its own filters, sorting, and pagination. Useful for federated search, loading multiple sections, or comparison views.
const response = await client.multiSearch([
{ q: 'laptop', per_page: 5, filter_by: 'category:Electronics' },
{ q: 'laptop bag', per_page: 3, sort_by: 'price:asc' },
{ q: '*', per_page: 4, filter_by: 'on_sale:true', sort_by: 'popularity:desc' },
]);
// Each result has its own SearchContext for independent analytics tracking
response.results.forEach((result, i) => {
console.log(`Query ${i}: ${result.totalResults} results`);
// Track clicks against the correct search context
// await client.trackClick(itemId, position, result.context);
});
MultiSearchQuery
Each query object accepts all the same options as client.search():
interface MultiSearchQuery {
q: string;
per_page?: number;
page?: number;
filter_by?: string;
facet_by?: string;
sort_by?: string;
return_fields?: string[];
// ... all other search options
}
MultiSearchResponse
interface MultiSearchResponse {
results: SearchResponse[]; // One per input query, same order
}
Use Cases
// Federated search: products + articles + FAQs
const federated = await client.multiSearch([
{ q: 'returns policy', per_page: 5 },
{ q: 'returns policy', per_page: 3, filter_by: 'type:article' },
{ q: 'returns policy', per_page: 3, filter_by: 'type:faq' },
]);
// Collection page: multiple sections at once
const collections = await client.multiSearch([
{ q: '*', per_page: 8, filter_by: 'category:New Arrivals', sort_by: 'created_at:desc' },
{ q: '*', per_page: 8, filter_by: 'on_sale:true', sort_by: 'discount:desc' },
{ q: '*', per_page: 8, sort_by: 'popularity:desc' },
]);
Search Response
interface SearchResponse {
results: any[]; // Array of search results
totalResults: number; // Total number of matches
searchId?: string; // Search ID for analytics
context: SearchContext; // Context for event tracking
facets?: Record<string, any>; // Facet data
}
Search Context
The context object is used for linking analytics events to searches:
interface SearchContext {
correlationId: string; // Unique ID for this search session
searchId?: string; // Search ID from backend
userId?: string; // User ID (if authenticated)
anonId: string; // Anonymous user ID
sessionId: string; // Session ID
}
Always pass the context to tracking methods:
const results = await client.search('laptop');
// Correct - pass context
await client.trackClick(itemId, position, results.context);
// Deprecated - passing searchId directly
await client.trackClick(itemId, position, results.searchId);
Advanced Examples
Search with Multiple Filters
const results = await client.search('shoes', {
per_page: 20,
filter_by: 'price:50-200 && category:Sneakers && brand:Nike',
facet_by: 'color,size',
sort_by: 'price:asc',
max_facet_values: 20,
});
E-commerce Product Search
const results = await client.search('wireless headphones', {
per_page: 24,
filter_by: 'in_stock:true && price:<=200',
facet_by: 'brand,color,connectivity,rating',
sort_by: 'popularity:desc',
return_fields: ['id', 'title', 'price', 'image', 'rating', 'brand'],
include_snippets: true,
snippet_fields: ['title', 'description'],
analytics_tags: ['category:audio', 'page:search'],
});
Autocomplete-style Search
const results = await client.search('lap', {
per_page: 5,
prefix_mode: 'always',
return_fields: ['id', 'title'],
widget_mode: true,
});
Empty Query (Browse All)
// Empty queries are converted to wildcard search
const results = await client.search('', {
per_page: 20,
facet_by: 'category',
sort_by: 'created_at:desc',
});
Next Steps
- Query Suggestions - Implement autocomplete
- Analytics - Track search events
- Configuration - Configure SDK behavior