In this article we will explore how to utilise Elastic Search into our .Net 6 API.
You can watch the full video on YouTube
Starting Source code:
https://github.com/mohamadlawand087/Net6-ELK
Finished Project
https://github.com/mohamadlawand087/ELS-Dotnet6
DotNet SDK:
https://dotnet.microsoft.com/download
Visual Studio Code:
https://code.visualstudio.com/](https://code.visualstudio.com/
Docker
https://www.docker.com/products/docker-desktop
We will start by adding ELS nuget package
dotnet add package NEST --version 7.17.0
Once our package is installed we can verify it inside our csproj file. The next step is to create our Model which will represent the data which will be using to save in ELS
public class Product
{
public int Id { get; set; }
public string Title { get; set; }
public string Description { get; set; }
public int Quantity { get; set; }
}
Then we need to update our configuration, inside our appsettings.json we need to change it to the following
{
"Serilog": {
"MinimumLevel": {
"Default": "Information",
"Override": {
"Microsoft": "Information",
"System": "Warning"
}
}
},
"ELKConfiguration": {
"Uri": "http://localhost:9200",
"index": "products",
},
"AllowedHosts": "*"
}
Inside the root folder of our application, create a new folder called extensions. Then create a class called ElasticSearchExtensions which is our ELS extension method which will be used to initialise ELS when our application starts
public static class ElasticSearchExtensions
{
public static void AddElasticsearch(
this IServiceCollection services, IConfiguration configuration)
{
var url = configuration["ELKConfiguration:url"];
var defaultIndex = configuration["ELKConfiguration:index"];
var settings = new ConnectionSettings(new Uri(url)).BasicAuthentication(userName, pass)
.PrettyJson()
.DefaultIndex(defaultIndex);
AddDefaultMappings(settings);
var client = new ElasticClient(settings);
services.AddSingleton<IElasticClient>(client);
CreateIndex(client, defaultIndex);
}
private static void AddDefaultMappings(ConnectionSettings settings)
{
settings
.DefaultMappingFor<Product>(m => m
.Ignore(p => p.Price)
.Ignore(p => p.Measurement)
);
}
private static void CreateIndex(IElasticClient client, string indexName)
{
var createIndexResponse = client.Indices.Create(indexName,
index => index.Map<Product>(x => x.AutoMap())
);
}
}
Now that our extension method has been added, its time to add it to our program.cs so it will be injected into our application startup
builder.Services.AddElasticsearch(builder.Configuration);
Now that our application knows about ELS we need to create our controller ProductsController so we can interact with our ELS.
public class ProductsController : ControllerBase
{
private readonly IElasticClient _elasticClient;
private readonly ILogger<ProductsController> _logger;
public ProductsController(
IElasticClient elasticClient,
ILogger<ProductsController> logger)
{
_logger = logger;
_elasticClient = elasticClient;
}
[HttpGet(Name = "GetAllProducts")]
public async Task<IActionResult> Get(string keyword)
{
var result = await _elasticClient.SearchAsync<Product>(
s => s.Query(
q => q.QueryString(
d => d.Query('*' + keyword + '*')
)).Size(5000));
_logger.LogInformation("ProductsController Get - ", DateTime.UtcNow);
return Ok(result.Documents.ToList());
}
[HttpPost(Name = "AddProduct")]
public async Task<IActionResult> Post(Product product)
{
// Add product to ELS index
var product1 = new Product
{
Description = "Product 1",
Id = 1,
Price = 200,
Measurement = "2",
Quantity = 90,
ShowPrice = true,
Title = "Nike Shoes",
Unit = "10"
};
// Index product dto
await _elasticClient.IndexDocumentAsync(product);
_logger.LogInformation("ProductsController Get - ", DateTime.UtcNow);
return Ok();
}
}
Please add your question below and follow me here and subscribe to my YouTube Channel.
Top comments (3)
Hi Mohamad,
Do you have any issue with localhost:9200? I dont have http for my setup. I could not make it work.
I got this issue, even I tried the solution github.com/elastic/elasticsearch-n...
Invalid NEST response built from a unsuccessful () low level call on PUT: /platforms/_doc/1
Audit trail of this API call:
1.PingAsync(IRequestPipeline pipeline, Node node, CancellationToken cancellationToken) at Elasticsearch.Net.Transport
1.RequestAsyncTResponse --- End of inner exception stack trace --- # Request: # Response:Great article, good job!!!
In line _logger.LogInformation("ProductsController Get - ", DateTime.UtcNow) alter to _logger.LogInformation("ProductsController Post - ", DateTime.UtcNow);
Have a nice week
in real application how should we index the document? And how to index for existing data?