Articles on: Getting started

How to setup Meilisearch with JavaScript


We recommend installing meilisearch-js in your project with your package manager of choice.

npm install meilisearch

meilisearch-js officially supports node versions >= 14 and <= 18.

Instead of using a package manager, you may also import the library directly into your HTML via a CDN.

Run Meilisearch

To use one of our SDKs, you must first have a running Meilisearch instance. Consult our documentation for instructions on how to download and launch Meilisearch.


After installing meilisearch-js, you must import it into your application. There are many ways of doing that depending on your development environment.

import syntax

Usage in an ES module environment:

import { MeiliSearch } from 'meilisearch'

const client = new MeiliSearch({
  host: 'url',
  apiKey: 'masterKey',

<script> tag

Usage in an HTML (or alike) file:

<script src=''></script>
  const client = new MeiliSearch({
    host: 'url',
    apiKey: 'masterKey',

require syntax

Usage in a back-end node.js or another environment supporting CommonJS modules:

const { MeiliSearch } = require('meilisearch')

const client = new MeiliSearch({
  host: 'url',
  apiKey: 'masterKey',

React Native

To use meilisearch-js with React Native, you must also install react-native-url-polyfill.


Usage in a Deno environment:

import { MeiliSearch } from ""

const client = new MeiliSearch({
  host: 'url',
  apiKey: 'masterKey',

Getting started

Add documents

const { MeiliSearch } = require('meilisearch')
// Or if you are in a ES environment
import { MeiliSearch } from 'meilisearch'

;(async () => {
  const client = new MeiliSearch({
    host: 'url',
    apiKey: 'masterKey',

  // An index is where the documents are stored.
  const index = client.index('movies')

  const documents = [
      { id: 1, title: 'Carol', genres: ['Romance', 'Drama'] },
      { id: 2, title: 'Wonder Woman', genres: ['Action', 'Adventure'] },
      { id: 3, title: 'Life of Pi', genres: ['Adventure', 'Drama'] },
      { id: 4, title: 'Mad Max: Fury Road', genres: ['Adventure', 'Science Fiction'] },
      { id: 5, title: 'Moana', genres: ['Fantasy', 'Action']},
      { id: 6, title: 'Philadelphia', genres: ['Drama'] },

  // If the index 'movies' does not exist, Meilisearch creates it when you first add the documents.
  let response = await index.addDocuments(documents)

  console.log(response) // => { "uid": 0 }

Tasks such as document addition always return a unique identifier. You can use this identifier taskUid to check the status (enqueued, processing, succeeded or failed) of a task.

// Meilisearch is typo-tolerant:
const search = await'philoudelphia')


  "hits": [
      "id": "6",
      "title": "Philadelphia",
      "genres": ["Drama"]
  "offset": 0,
  "limit": 20,
  "estimatedTotalHits": 1,
  "processingTimeMs": 1,
  "query": "philoudelphia"

Using search parameters

meilisearch-js supports all search parameters described in our main documentation website.

    attributesToHighlight: ['*']

  "hits": [
      "id": 2,
      "title": "Wonder Woman",
      "genres": ["Action", "Adventure"],
      "_formatted": {
        "id": "2",
        "title": "<em>Wonder</em> Woman",
        "genres": ["Action", "Adventure"]
  "offset": 0,
  "limit": 20,
  "estimatedTotalHits": 1,
  "processingTimeMs": 0,
  "query": "wonder"

Custom search with filters

To enable filtering, you must first add your attributes to the `filterableAttributes` index setting.

await index.updateAttributesForFaceting([

You only need to perform this operation once per index.

Note that Meilisearch rebuilds your index whenever you update filterableAttributes. Depending on the size of your dataset, this might take considerable time. You can track the process using the tasks API).

After you configured filterableAttributes, you can use the `filter` search parameter to refine your search:

    filter: ['id > 1 AND genres = Action']

  "hits": [
      "id": 2,
      "title": "Wonder Woman",
      "genres": ["Action","Adventure"]
  "offset": 0,
  "limit": 20,
  "estimatedTotalHits": 1,
  "processingTimeMs": 0,
  "query": "wonder"

Placeholder search makes it possible to receive hits based on your parameters without having any query (q). For example, in a movies database you can run an empty query to receive all results filtered by genre.

    filter: ['genres = fantasy'],
    facets: ['genres']

  "hits": [
      "id": 2,
      "title": "Wonder Woman",
      "genres": ["Action","Adventure"]
      "id": 5,
      "title": "Moana",
      "genres": ["Fantasy","Action"]
  "offset": 0,
  "limit": 20,
  "estimatedTotalHits": 2,
  "processingTimeMs": 0,
  "query": "",
  "facetDistribution": {
    "genres": {
      "Action": 2,
      "Fantasy": 1,
      "Adventure": 1

Note that to enable faceted search on your dataset you need to add genres to the filterableAttributes index setting. For more information on filtering and faceting, consult our documentation settings.

You can abort a pending search request by providing an AbortSignal to the request.

const controller = new AbortController()

  .search('wonder', {}, {
    signal: controller.signal,
  .then((response) => {
    /** ... */
  .catch((e) => {
    /** Catch AbortError here. */


API resources

Make a search request

client.index<T>('xxx').search(query: string, options: SearchParams = {}, config?: Partial<Request>): Promise<SearchResponse<T>>

Make a search request using the GET method (slower than the search method)

client.index<T>('xxx').searchGet(query: string, options: SearchParams = {}, config?: Partial<Request>): Promise<SearchResponse<T>>

client.multiSearch(queries?: MultiSearchParams, config?: Partial<Request>): Promise<Promise<MultiSearchResponse<T>>>

multiSearch uses the POST method when performing its request to Meilisearch.

Search For Facet Values

client.index<T>('myIndex').searchForFacetValues(params: SearchForFacetValuesParams, config?: Partial<Request>): Promise<SearchForFacetValuesResponse>


Add or replace multiple documents

client.index('myIndex').addDocuments(documents: Document<T>[]): Promise<EnqueuedTask>

Add or replace multiple documents in string format

client.index('myIndex').addDocumentsFromString(documents: string, contentType: ContentType, queryParams: RawDocumentAdditionOptions): Promise<EnqueuedTask>

Add or replace multiple documents in batches

client.index('myIndex').addDocumentsInBatches(documents: Document<T>[], batchSize = 1000): Promise<EnqueuedTask[]>

Add or update multiple documents

client.index('myIndex').updateDocuments(documents: Array<Document<Partial<T>>>): Promise<EnqueuedTask>

Add or update multiple documents in string format

client.index('myIndex').updateDocumentsFromString(documents: string, contentType: ContentType, queryParams: RawDocumentAdditionOptions): Promise<EnqueuedTask>

Add or update multiple documents in batches

client.index('myIndex').updateDocumentsInBatches(documents: Array<Document<Partial<T>>>, batchSize = 1000): Promise<EnqueuedTask[]>

Get Documents

client.index.getDocuments(parameters: DocumentsQuery = {}): Promise<DocumentsResults<T>>>

Get one document

client.index('myIndex').getDocument(documentId: string): Promise<Document<T>>

Delete one document

client.index('myIndex').deleteDocument(documentId: string | number): Promise<EnqueuedTask>

Delete multiple documents

client.index('myIndex').deleteDocuments(params: DocumentsDeletionQuery | DocumentsIds): Promise<EnqueuedTask>

Delete all documents

client.index('myIndex').deleteAllDocuments(): Promise<Types.EnqueuedTask>


Get all tasks

client.getTasks(parameters: TasksQuery): Promise<TasksResults>

Get one task

client.getTask(uid: number): Promise<Task>

Delete tasks

client.deleteTasks(parameters: DeleteTasksQuery = {}): Promise<EnqueuedTask>

Cancel tasks

client.cancelTasks(parameters: CancelTasksQuery = {}): Promise<EnqueuedTask>

Get all tasks of an index

client.index('myIndex').getTasks(parameters: TasksQuery): Promise<TasksResults>

Get one task of an index

client.index('myIndex').getTask(uid: number): Promise<Task>

Wait for one task

Using the client

client.waitForTask(uid: number, { timeOutMs?: number, intervalMs?: number }): Promise<Task>

Using the index

client.index('myIndex').waitForTask(uid: number, { timeOutMs?: number, intervalMs?: number }): Promise<Task>

Wait for multiple tasks

Using the client

client.waitForTasks(uids: number[], { timeOutMs?: number, intervalMs?: number }): Promise<Task[]>

Using the index

client.index('myIndex').waitForTasks(uids: number[], { timeOutMs?: number, intervalMs?: number }): Promise<Task[]>


Get all indexes in Index instances

client.getIndexes(parameters: IndexesQuery): Promise<IndexesResults<Index[]>>

Get all indexes

client.getRawIndexes(parameters: IndexesQuery): Promise<IndexesResults<IndexObject[]>>

Create a new index

client.createIndex<T>(uid: string, options?: IndexOptions): Promise<EnqueuedTask>

Create a local reference to an index

client.index<T>(uid: string): Index<T>

Get an index instance completed with information fetched from Meilisearch

client.getIndex<T>(uid: string): Promise<Index<T>>

Get the raw index JSON response from Meilisearch

client.getRawIndex(uid: string): Promise<IndexObject>

Get an object with information about the index

client.index('myIndex').getRawInfo(): Promise<IndexObject>

Update Index

Using the client

client.updateIndex(uid: string, options: IndexOptions): Promise<EnqueuedTask>

Using the index object

client.index('myIndex').update(data: IndexOptions): Promise<EnqueuedTask>

Delete index

Using the client

client.deleteIndex(uid): Promise<void>

Using the index object

client.index('myIndex').delete(): Promise<void>

Get specific index stats

client.index('myIndex').getStats(): Promise<IndexStats>

Return Index instance with updated information

client.index('myIndex').fetchInfo(): Promise<Index>

Get Primary Key of an Index

client.index('myIndex').fetchPrimaryKey(): Promise<string | undefined>

Swap two indexes

client.swapIndexes(params: SwapIndexesParams): Promise<EnqueuedTask>


Get settings

client.index('myIndex').getSettings(): Promise<Settings>

Update settings

client.index('myIndex').updateSettings(settings: Settings): Promise<EnqueuedTask>

Reset settings

client.index('myIndex').resetSettings(): Promise<EnqueuedTask>

Pagination Settings

Get pagination

client.index('myIndex').getPagination(): Promise<PaginationSettings>

Update pagination

client.index('myIndex').updatePagination(pagination: PaginationSettings): Promise<EnqueuedTask>

Reset pagination

client.index('myIndex').resetPagination(): Promise<EnqueuedTask>


Get synonyms

client.index('myIndex').getSynonyms(): Promise<Synonyms>

Update synonyms

client.index('myIndex').updateSynonyms(synonyms: Synonyms): Promise<EnqueuedTask>

Reset synonyms

client.index('myIndex').resetSynonyms(): Promise<EnqueuedTask>

Stop words

Get stop words

client.index('myIndex').getStopWords(): Promise<string[]>

Update stop words

client.index('myIndex').updateStopWords(stopWords: string[] | null ): Promise<EnqueuedTask>

Reset stop words

client.index('myIndex').resetStopWords(): Promise<EnqueuedTask>

Ranking rules

Get ranking rules

client.index('myIndex').getRankingRules(): Promise<string[]>

Update ranking rules

client.index('myIndex').updateRankingRules(rankingRules: string[] | null): Promise<EnqueuedTask>

Reset ranking rules

client.index('myIndex').resetRankingRules(): Promise<EnqueuedTask>

Distinct Attribute

Get distinct attribute

client.index('myIndex').getDistinctAttribute(): Promise<string | void>

Update distinct attribute

client.index('myIndex').updateDistinctAttribute(distinctAttribute: string | null): Promise<EnqueuedTask>

Reset distinct attribute

client.index('myIndex').resetDistinctAttribute(): Promise<EnqueuedTask>

Searchable attributes

Get searchable attributes

client.index('myIndex').getSearchableAttributes(): Promise<string[]>

Update searchable attributes

client.index('myIndex').updateSearchableAttributes(searchableAttributes: string[] | null): Promise<EnqueuedTask>

Reset searchable attributes

client.index('myIndex').resetSearchableAttributes(): Promise<EnqueuedTask>

Displayed attributes

Get displayed attributes

client.index('myIndex').getDisplayedAttributes(): Promise<string[]>

Update displayed attributes

client.index('myIndex').updateDisplayedAttributes(displayedAttributes: string[] | null): Promise<EnqueuedTask>

Reset displayed attributes

client.index('myIndex').resetDisplayedAttributes(): Promise<EnqueuedTask>

Filterable attributes

Get filterable attributes

client.index('myIndex').getFilterableAttributes(): Promise<string[]>

Update filterable attributes

client.index('myIndex').updateFilterableAttributes(filterableAttributes: string[] | null): Promise<EnqueuedTask>

Reset filterable attributes

client.index('myIndex').resetFilterableAttributes(): Promise<EnqueuedTask>

Sortable attributes

Get sortable attributes

client.index('myIndex').getSortableAttributes(): Promise<string[]>

Update sortable attributes

client.index('myIndex').updateSortableAttributes(sortableAttributes: string[] | null): Promise<EnqueuedTask>

Reset sortable attributes

client.index('myIndex').resetSortableAttributes(): Promise<EnqueuedTask>


Get faceting

client.index('myIndex').getFaceting(): Promise<Faceting>

Update faceting

client.index('myIndex').updateFaceting(faceting: Faceting): Promise<EnqueuedTask>

Reset faceting

client.index('myIndex').resetFaceting(): Promise<EnqueuedTask>

Typo tolerance

Get typo tolerance

client.index('myIndex').getTypoTolerance(): Promise<TypoTolerance>

Update typo tolerance

client.index('myIndex').updateTypoTolerance(typoTolerance: TypoTolerance | null): Promise<EnqueuedTask>

Reset typo tolerance

client.index('myIndex').resetTypoTolerance(): Promise<EnqueuedTask>


Get keys

client.getKeys(parameters: KeysQuery): Promise<KeysResults>

Get one key

client.getKey(keyOrUid: string): Promise<Key>

Create a key

client.createKey(options: KeyCreation): Promise<Key>

Update a key

client.updateKey(keyOrUid: string, options: KeyUpdate): Promise<Key>

Delete a key

client.deleteKey(keyOrUid: string): Promise<void>


Return true or false depending on the health of the server

client.isHealthy(): Promise<boolean>


Check if the server is healthy Promise<Health>


Get database stats

client.getStats(): Promise<Stats>


Get binary version

client.getVersion(): Promise<Version>


Trigger a dump creation process

client.createDump(): Promise<EnqueuedTask>

Updated on: 23/08/2023

Was this article helpful?

Share your feedback


Thank you!