Skip to main content

Search API

The Search API is the core functionality of the Seekora SDK, providing powerful full-text search with filtering, faceting, and sorting capabilities.

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

OptionTypeDefaultDescription
per_pagenumber10Number of results per page
pagenumber1Page number (1-indexed)

Filtering

OptionTypeDescription
filter / filter_bystringFilter 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

OptionTypeDescription
facet_bystringComma-separated list of facet fields
max_facet_valuesnumberMaximum 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

OptionTypeDescription
sort / sort_bystringSort 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

OptionTypeDescription
search_fieldsstring[]Fields to search in
field_weightsnumber[]Weights for search fields
const results = await client.search('laptop', {
search_fields: ['title', 'description', 'brand'],
field_weights: [10, 5, 3],
});

Return Fields

OptionTypeDescription
return_fieldsstring[]Fields to include in results
omit_fieldsstring[]Fields to exclude from results
// Only return specific fields
return_fields: ['id', 'title', 'price', 'image']

// Exclude large fields
omit_fields: ['description', 'specifications']

Snippets

OptionTypeDescription
include_snippetsbooleanInclude highlighted snippets
snippet_fieldsstring[]Fields for snippets
snippet_prefixstringPrefix for highlights
snippet_suffixstringSuffix for highlights
snippet_token_limitnumberMax tokens in snippet
const results = await client.search('laptop', {
include_snippets: true,
snippet_fields: ['title', 'description'],
snippet_prefix: '<mark>',
snippet_suffix: '</mark>',
});

Grouping

OptionTypeDescription
group_fieldstringField to group by
group_sizenumberResults per group
// Group by category, 3 results per group
const results = await client.search('laptop', {
group_field: 'category',
group_size: 3,
});

Typo Tolerance

OptionTypeDescription
typo_maxnumberMaximum typos allowed
typo_min_len_1numberMin length for 1 typo
typo_min_len_2numberMin length for 2 typos
typo_timeout_msnumberTimeout 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

OptionTypeDescription
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

OptionTypeDescription
analytics_tagsstring[]Tags for analytics
widget_modebooleanSimplified response format
require_all_termsbooleanAll terms must match
exact_match_boostbooleanBoost exact matches
cache_resultsbooleanCache results
apply_rulesbooleanApply search rules
preset_namestringUse a search preset
search_timeout_msnumberSearch timeout

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,
});
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'],
});
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