Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix guides/bulk.md #616

Closed
zoran-php opened this issue Oct 1, 2023 · 4 comments · Fixed by #723
Closed

Fix guides/bulk.md #616

zoran-php opened this issue Oct 1, 2023 · 4 comments · Fixed by #723
Assignees
Labels
good first issue Good for newcomers

Comments

@zoran-php
Copy link

What is the bug?

Bulk method for creating multiple documents is not working properly.

How can one reproduce the bug?

In the Creating multiple documents guide, there is a snippet of code how to create multiple documents.

client.bulk({ index: movies, body: [ { create: { data: { title: 'Beauty and the Beast 2', year: 2030 } } }, { create: { data: { title: 'Beauty and the Beast 3', year: 2031 } } }, { create: { data: { title: 'Beauty and the Beast 4', year: 2049 } } }, { create: { _index: books, data: { title: 'The Lion King 2', year: 1998 } } } ] }).then((response) => { console.log(response); });

My Code Snippet:

const bulk = async (index: string) => { try { const res = await OpenSearchClient.getClient().bulk({ index, body: [ { create: { data: { Id: '1', Title: 'Title 1', Language: 'en-US', ShortDocument: 'Short Doc 1', FullDocument: 'Full Doc 1', }, }, }, { create: { data: { Id: '2', Title: 'Title 2', Language: 'en-US', ShortDocument: 'Short Doc 2', FullDocument: 'Full Doc 2', }, }, }, { create: { data: { Id: '3', Title: 'Title 3', Language: 'en-US', ShortDocument: 'Short Doc 3', FullDocument: 'Full Doc 3', }, }, }, ], }); return res.body; } catch (error) { console.error(error); return { error }; } };

Returns:

ResponseError: illegal_argument_exception: [illegal_argument_exception] Reason: Malformed action/metadata line [1], expected a simple value for field [data] but found [START_OBJECT] at onBody (C:\Users\zoran\Documents\node_projects\opensearchdemo\node_modules\@opensearch-project\opensearch\lib\Transport.js:425:23) at IncomingMessage.onEnd (C:\Users\zoran\Documents\node_projects\opensearchdemo\node_modules\@opensearch-project\opensearch\lib\Transport.js:340:11) at IncomingMessage.emit (node:events:524:35) at endReadableNT (node:internal/streams/readable:1378:12) at process.processTicksAndRejections (node:internal/process/task_queues:82:21) { meta: { body: { error: [Object], status: 400 }, statusCode: 400, headers: { 'content-type': 'application/json; charset=UTF-8', 'content-length': '339' }, meta: { context: null, request: [Object], name: 'opensearch-js', connection: [Object], attempts: 0, aborted: false } } }

What is the expected behavior?

Successfully create multiple documents.

What is your host/environment?

Windows 11 Pro, Version 22H2, OS Build 22621.2283. Node version v20.4.0. NPM version 9.7.2

Do you have any screenshots?

Screenshot

Do you have any additional context?

Is the guide up to date or is it deprecated?

@nhtruong
Copy link
Collaborator

nhtruong commented Oct 2, 2023

The Guide is wrong. It should be something like:

client.bulk({
    index: movies,
    body: [
      { create: { _id: 1} },
      { title: 'Beauty and the Beast 1', year: 2050 },
      { delete: { _id: 1 } },
      { create: { _id: 2 } },
      { title: 'Beauty and the Beast 2', year: 2051 },
      { create: {} },
      { title: 'Beauty and the Beast 2', year: 2051 },
      { create: { _index: books } },
      { title: '2012', year: 2012 },
    ]
  }).then((response) => {
    console.log(response.body.items);
  });

Note that in the body array, the actions come in pairs (except for delete action) where the first item of the pair is the action like { create: { _index: books, _id:20 } } where create is the action and _index and _id specify which document ID of which Index is the action to be performed on (In the case of create, _id is optional as OS will assign the new doc with a random ID that it generates). And the second item of the pair is the document itself { title: 'Beauty and the Beast 1', year: 2050 }

@nhtruong nhtruong added the good first issue Good for newcomers label Oct 2, 2023
@nhtruong nhtruong changed the title Bulk API - Creating multiple documents Fix guides/bulk.md Oct 2, 2023
@dblock
Copy link
Member

dblock commented Oct 2, 2023

@zoran-php Want to help fix the guide and add working samples along the way to avoid this kind of errors in the future? We've been doing this in other clients, e.g. https://github.com/opensearch-project/opensearch-py/tree/main/samples

@AbhinavGarg90
Copy link

I can take this issue up if it's available @nhtruong

@AbhinavGarg90
Copy link

The Guide is wrong. It should be something like:

client.bulk({
    index: movies,
    body: [
      { create: { _id: 1} },
      { title: 'Beauty and the Beast 1', year: 2050 },
      { delete: { _id: 1 } },
      { create: { _id: 2 } },
      { title: 'Beauty and the Beast 2', year: 2051 },
      { create: {} },
      { title: 'Beauty and the Beast 2', year: 2051 },
      { create: { _index: books } },
      { title: '2012', year: 2012 },
    ]
  }).then((response) => {
    console.log(response.body.items);
  });

Note that in the body array, the actions come in pairs (except for delete action) where the first item of the pair is the action like { create: { _index: books, _id:20 } } where create is the action and _index and _id specify which document ID of which Index is the action to be performed on (In the case of create, _id is optional as OS will assign the new doc with a random ID that it generates). And the second item of the pair is the document itself { title: 'Beauty and the Beast 1', year: 2050 }

I'm working on replacing the documentation using this format. This seemed to slot in perfectly for most of the examples. However, under the Handling Errors section, a similar replacement is causing an unusual exception. I am unsure of the root cause of this.

My Code Snippet:

const { Client } = require('@opensearch-project/opensearch');
try {
  const client = new Client({
    node: 'https://admin:admin@localhost:9200',
    ssl: { rejectUnauthorized: false }
  });
  const movies = 'movies';
  const books = 'books';
  client.bulk({
    index: movies,
    body: [
      { create: { _id: 1 }},
      { title: 'Beauty and the Beast', year: 1991 },
      { create: { _id: 2}},
      { title: 'Beauty and the Beast 2', year: 2030 },
      { create: { _id: 1 } },
      { title: 'Beauty and the Beast 3', year: 2031 }, // document already exists error
      { create: { _id: 2 } },
      { title: 'Beauty and the Beast 4', year: 2049 }  // document already exists error
    ]
  }).then((response) => {
    response.body.forEach((item) => {
      const createStatus = item.create && item.create.status;
      if (createStatus && !createStatus.toString().match(/2\d{2}/)) {
        console.log(item.create.error.reason);
      }
    });
  }).catch((error) => {
    console.error(error);
  });
} catch(e) {
  console.log("error", e)
}

the Error:

user:~/osci/opensearchjs-test$ node index.js 
TypeError: response.body.forEach is not a function
    at /home/abhinavgarg/osci/opensearchjs-test/index.js:22:19
    at process.processTicksAndRejections (node:internal/process/task_queues:95:5)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
good first issue Good for newcomers
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants