Integrating Elasticsearch with Node.js – A Complete Guide

Elasticsearch Connect NodeJs

Elasticsearch is a powerful, distributed search and analytics engine, perfect for indexing and querying large datasets. By integrating it with Node.js, developers can build scalable, high-performance applications capable of handling complex search requirements.

In this article, we’ll explore how to connect Elasticsearch with Node.js, perform CRUD operations, and create a simple API that interacts with a React frontend for search functionalities.

1. Setting up Elasticsearch and Node.js

Before starting, ensure you have both Elasticsearch and Node.js installed. You’ll also need the official Elasticsearch client for Node.js, which simplifies communication with the Elasticsearch cluster.

To install the Elasticsearch client in your project, run the following:

npm install @elastic/elasticsearch

This package enables seamless interaction between your Node.js application and Elasticsearch.

2. Connecting Node.js to Elasticsearch

Once Elasticsearch is running, you can connect it to your Node.js application using the client library. Here’s how:

const { Client } = require('@elastic/elasticsearch');

const esClient = new Client({ node: 'http://localhost:9200' }); // Replace with your Elasticsearch URL

// Test connection
esClient.ping({}, (error) => {
  if (error) {
    console.error('Elasticsearch cluster is down!');
  } else {
    console.log('Elasticsearch is running.');
  }
});

This code creates an Elasticsearch client that points to your local Elasticsearch instance, and it checks if the cluster is operational by pinging it.

3. Creating an Index

In Elasticsearch, an **index** is like a database in relational systems. Here’s how to create one for storing blog posts:

async function createIndex(indexName) {
  const result = await esClient.indices.create({
    index: indexName,
  });
  console.log('Index created:', result);
}

createIndex('blog-posts');

The `createIndex` function creates an index called blog-posts that will store documents representing individual blog posts.

4. Inserting Data into the Index (Create)

Now that the index is ready, you can start adding documents to it. In Elasticsearch, documents are similar to rows in relational databases.

async function addPost(post) {
  const result = await esClient.index({
    index: 'blog-posts',
    document: post,
  });
  console.log('Post added:', result);
}

addPost({
  title: 'Introduction to Elasticsearch',
  body: 'Elasticsearch is a distributed search and analytics engine...',
  tags: ['search', 'elasticsearch', 'nodejs'],
  published: true,
});

This function inserts a new blog post into the blog-posts index. The document contains fields such as `title`, `body`, `tags`, and `published` status.

5. Reading Data from the Index (Read)

To read data from Elasticsearch, you can retrieve a document by its ID or perform a search query.

Retrieving a Document by ID:

async function getPostById(id) {
  const result = await esClient.get({
    index: 'blog-posts',
    id: id,
  });
  console.log('Post found:', result);
}

getPostById('some-post-id');

Performing a Search Query:

async function searchPosts(query) {
  const result = await esClient.search({
    index: 'blog-posts',
    query: {
      match: { body: query },
    },
  });
  console.log('Search results:', result.hits.hits);
}

searchPosts('Elasticsearch');

The `searchPosts` function searches for documents where the `body` field matches the query string. Elasticsearch returns the matching documents in the `hits.hits` array.

6. Updating a Document (Update)

Updating a document is straightforward with Elasticsearch. Here’s how you can update the title of a post by its ID:

async function updatePost(id, newTitle) {
  const result = await esClient.update({
    index: 'blog-posts',
    id: id,
    doc: { title: newTitle },
  });
  console.log('Post updated:', result);
}

updatePost('some-post-id', 'Advanced Elasticsearch');

The `updatePost` function modifies the `title` of a document identified by its ID.

7. Deleting a Document (Delete)

You can delete a document from an index using the following code:

async function deletePost(id) {
  const result = await esClient.delete({
    index: 'blog-posts',
    id: id,
  });
  console.log('Post deleted:', result);
}

deletePost('some-post-id');

This function removes the document with the specified ID from the blog-posts index.

8. Frontend Integration with React

To integrate Elasticsearch with a React frontend, you’ll need a server-side API that interacts with Elasticsearch. Here’s a simple example of how to set up an Express.js backend API for searching blog posts.

Backend API (Express.js):

const express = require('express');
const app = express();
const esClient = new Client({ node: 'http://localhost:9200' });

app.get('/api/search', async (req, res) => {
  const { query } = req.query;
  const result = await esClient.search({
    index: 'blog-posts',
    query: {
      match: { body: query },
    },
  });
  res.json(result.hits.hits);
});

app.listen(3001, () => console.log('Server running on port 3001'));

This Express.js API listens for GET requests on `/api/search`, performs a search on the blog-posts index, and returns the results.

React Frontend (Using Fetch):

import React, { useState } from 'react';

function SearchPosts() {
const [query, setQuery] = useState('');
const [results, setResults] = useState([]);

const search = async () => {
  const response = await fetch(`/api/search?query=${query}`);
  const data = await response.json();
  setResults(data);
};

return (
  <div>
    <input type="text" value={query} onChange={(e) => setQuery(e.target.value)} placeholder="Search posts" />
    <button onClick={search}>Search</button>

    <ul>
      {results.map((post) => (
        <li key={post._id}>{post._source.title}</li>
      ))}
    </ul>
  </div>
  );
}

export default SearchPosts;

In this React component, users can input a search query. When they click the search button, the application sends a request to the Express backend, which returns matching results that are then displayed in a list.

Conclusion

By integrating Elasticsearch with Node.js, you can perform powerful search and analytics operations on large datasets. This guide covers the basics of connecting to Elasticsearch, performing CRUD operations, and building a React frontend to interact with the search engine.

Elasticsearch’s rich set of features, including aggregations and real-time search, makes it a robust solution for modern web applications.

You may also like:

Related Posts

Leave a Reply