Skip to content

Commit

Permalink
Add higher-level HTTP DSL methods (opensearch-project#447) (opensearc…
Browse files Browse the repository at this point in the history
…h-project#456)

* Lay foundations

Signed-off-by: Thomas Farr <[email protected]>

* Implement generation

Signed-off-by: Thomas Farr <[email protected]>

* Run generator

Signed-off-by: Thomas Farr <[email protected]>

* Update samples

Signed-off-by: Thomas Farr <[email protected]>

* Update guide

Signed-off-by: Thomas Farr <[email protected]>

* Add changelog entry

Signed-off-by: Thomas Farr <[email protected]>

* PR comments

Signed-off-by: Thomas Farr <[email protected]>

* Fix naming tests

Signed-off-by: Thomas Farr <[email protected]>

* Why is the ordering of these statements load-bearing???

Signed-off-by: Thomas Farr <[email protected]>

---------

Signed-off-by: Thomas Farr <[email protected]>
(cherry picked from commit 9054705)
  • Loading branch information
Xtansia authored Dec 1, 2023
1 parent 630fc9f commit b93f4db
Show file tree
Hide file tree
Showing 29 changed files with 1,827 additions and 132 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ Inspired from [Keep a Changelog](https://keepachangelog.com/en/1.0.0/)
- Added support for point-in-time search and associated APIs ([#405](https://github.com/opensearch-project/opensearch-net/pull/405))
- Added support for the component template APIs ([#411](https://github.com/opensearch-project/opensearch-net/pull/411))
- Added support for the composable index template APIs ([#437](https://github.com/opensearch-project/opensearch-net/pull/437))
- Added high-level DSL for raw HTTP methods ([#447](https://github.com/opensearch-project/opensearch-net/pull/447))

### Deprecated
- Deprecated the low-level `IndexTemplateV2` APIs in favour of the new `ComposableIndexTemplate` APIs ([#454](https://github.com/opensearch-project/opensearch-net/pull/454))
Expand Down
9 changes: 9 additions & 0 deletions USER_GUIDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -260,3 +260,12 @@ var client = new OpenSearchLowLevelClient(config);
```

Note the main difference here is that we are instantiating an `OpenSearchLowLevelClient` rather than `OpenSearchClient`, and `ConnectionConfiguration` instead of `ConnectionSettings`.


## Advanced Features

- [Bulk Requests](guides/bulk.md)
- [Document Lifecycle](guides/document-lifecycle.md)
- [Index Template](guides/index-template.md)
- [Making Raw JSON REST Requests](guides/json.md)
- [Search](guides/search.md)
155 changes: 155 additions & 0 deletions guides/bulk.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,155 @@
# Bulk

In this guide, you'll learn how to use the OpenSearch .NET Client API to perform bulk operations. You'll learn how to index, update, and delete multiple documents in a single request.

## Setup

First, create a client instance with the following code:

```cs
var nodeAddress = new Uri("http://myserver:9200");
var client = new OpenSearchClient(nodeAddress);
```

Next, create an index named `movies` and another named `books` with the default settings:

```cs
var movies = "movies";
var books = "books";
if (!(await client.Indices.ExistsAsync(movies)).Exists) {
await client.Indices.CreateAsync(movies);
}

if (!(await client.Indices.ExistsAsync(books)).Exists) {
await client.Indices.CreateAsync(books);
}
```

## Bulk API

The `bulk` API action allows you to perform document operations in a single request. The body of the request is an array of objects that contains the bulk operations and the target documents to index, create, update, or delete.

### Indexing multiple documents

The following code creates two documents in the `movies` index and one document in the `books` index:

```cs
var response = await client.BulkAsync(b => b
.Index<object>(i => i
.Index(movies)
.Id(1)
.Document(new { Title = "Beauty and the Beast", Year = 1991 })
)
.Index<object>(i => i
.Index(movies)
.Id(2)
.Document(new { Title = "Beauty and the Beast - Live Action", Year = 2017 })
)
.Index<object>(i => i
.Index(books)
.Id(1)
.Document(new { Title = "The Lion King", Year = 1994 })
));
```

### Creating multiple documents

Similarly, instead of calling the `create` method for each document, you can use the `bulk` API to create multiple documents in a single request. The following code creates three documents in the `movies` index and one in the `books` index:

```cs
var response = await client.BulkAsync(b => b
.Index(movies)
.CreateMany(new[]
{
new { Title = "Beauty and the Beast 2", Year = 2030 },
new { Title = "Beauty and the Beast 3", Year = 2031 },
new { Title = "Beauty and the Beast 4", Year = 2049 }
})
.Create<object>(i => i
.Index(books)
.Document(new { Title = "The Lion King 2", Year = 1998 })
));
```

Note that we specified only the `_index` for the last document in the request body. This is because the `bulk` method accepts an `index` parameter that specifies the default `_index` for all bulk operations in the request body. Moreover, we omit the `_id` for each document and let OpenSearch generate them for us in this example, just like we can with the `create` method.

### Updating multiple documents

```cs
var response = await client.BulkAsync(b => b
.Index(movies)
.Update<object>(i => i
.Id(1)
.Doc(new { Year = 1992 })
)
.Update<object>(i => i
.Id(2)
.Doc(new { Year = 2018 })
));
```

### Deleting multiple documents

```cs
var response = await client.BulkAsync(b => b
.Index(movies)
.DeleteMany<object>(new long[] { 1, 2 }));
```

### Mix and match operations

You can mix and match the different operations in a single request. The following code creates two documents, updates one document, and deletes another document:

```cs
var response = await client.BulkAsync(b => b
.Index(movies)
.CreateMany(new[]
{
new { Title = "Beauty and the Beast 5", Year = 2050 },
new { Title = "Beauty and the Beast 6", Year = 2051 }
})
.Update<object>(i => i
.Id(3)
.Doc(new { Year = 2052 })
)
.Delete<object>(i => i.Id(4)));
```

### Handling errors

The `bulk` API returns an array of responses for each operation in the request body. Each response contains a `status` field that indicates whether the operation was successful or not. If the operation was successful, the `status` field is set to a `2xx` code. Otherwise, the response contains an error message in the `error` field.

The following code shows how to look for errors in the response:

```cs
var response = await client.BulkAsync(b => b
.Index(movies)
.Create<object>(i => i
.Id(1)
.Document(new { Title = "Beauty and the Beast", Year = 1991 })
)
.Create<object>(i => i
.Id(2)
.Document(new { Title = "Beauty and the Beast 2", Year = 2030 })
)
.Create<object>(i => i // document already exists error
.Id(1)
.Document(new { Title = "Beauty and the Beast 3", Year = 2031 })
)
.Create<object>(i => i // document already exists error
.Id(2)
.Document(new { Title = "Beauty and the Beast 4", Year = 2049 })
));

foreach (var item in response.ItemsWithErrors) {
Console.WriteLine(item.Error.Reason);
}
```

## Cleanup

To clean up the resources created in this guide, delete the `movies` and `books` indices:

```cs
await client.Indices.DeleteAsync(new[] { movies, books });
```
Loading

0 comments on commit b93f4db

Please sign in to comment.