Nội Dung Bất Biến của Mapping trong Elasticsearch
Khi một chỉ mục đã được khởi tạo trong Elasticsearch, các định nghĩa về loại dữ liệu (mapping types) của trường không thể chỉnh sửa trực tiếp. Để thay đổi kiểu dữ liệu từ văn bản sang số nguyên (ví dụ text sang integer), người dùng phải tuân thủ quy trình di chuyển dữ liệu sang cấu hình mới.
Bước 1: Thiết Lập Chỉ Mục Nguồn
Bắt đầu bằng việc tạo chỉ mục chứa dữ liệu mẫu với kiểu trường chưa phù hợp. Ví dụ dưới đây tạo chỉ mục old_data với thuộc tính product_count là chuỗi.
PUT old_data
{
"mappings": {
"properties": {
"product_count": {
"type": "text"
}
}
}
}
POST old_data/_doc
{
"product_count": "150"
}
Bước 2: Xác Định Chỉ Mục Mục Tiêu
Tạo một chỉ mục tạm thời nhằm định nghĩa lại cấu trúc dữ liệu chính xác. Trong ví dụ này, chỉ mục new_schema sẽ lưu trữ product_count ở dạng số nguyên.
PUT new_schema
{
"mappings": {
"properties": {
"product_count": {
"type": "long"
}
}
}
}
Bước 3: Sử Dụng Script Chuyển Đổi Dữ Liệu
Sử dụng API _reindex để nhúng mã Painless giúp ép buộc kiểu dữ liệu khi di chuyển thông tin từ nơi chứa nguồn sang nơi đích. Điều này đảm bảo giá trị chuỗi được chuyển thành số hợp lệ.
POST _reindex
{
"source": {
"index": "old_data"
},
"dest": {
"index": "new_schema"
},
"script": {
"lang": "painless",
"source": "ctx._source.product_count = ctx._source.product_count.toInteger()"
}
}
Việc bỏ qua đoạn script trên có thể dẫn đến lỗi hoặc dữ liệu bị giữ nguyên dạng chuỗi trong trường đích yêu cầu số. Sau khi chuyển, hãy kiểm tra kết quả để xác nhận sự thay đổi kiểu dữ liệu diễn ra đúng như mong đợi.
Bước 4: Thực Hiện Di Chuyển Cuối Cùng
Cuối cùng, xóa chỉ mục gốc và khôi phục nó với cấu hình mới, đồng thời đẩy ngược dữ liệu từ chỉ mục tạm thời trở lại. Đây là bước hoàn thiện việc cập nhật mapping.
DELETE old_data
PUT old_data
{
"mappings": {
"properties": {
"product_count": {
"type": "long"
}
}
}
}
POST _reindex
{
"source": {
"index": "new_schema"
},
"dest": {
"index": "old_data"
}
}
GET old_data/_search
Xác Minh Tích Hợp Với Ứng Dụng .NET
Dưới đây là ví dụ sử dụng thư viện Nest Client để truy vấn dữ liệu sau khi đã cập nhật định dạng. Lưu ý rằng câu lệnh tìm kiếm phải phù hợp với kiểu dữ liệu mới.
using Nest;
namespace ElasticApp.Controllers
{
public class ProductStats
{
[Property(Type = FieldType.Long)]
public long StockQuantity { get; set; }
public string ProductName { get; set; }
}
[Route("api/stats/")]
public class InventoryController : ControllerBase
{
private readonly IElasticClient _client;
public InventoryController(ConnectionSettings settings)
{
var server = new Uri("http://localhost:9200");
_client = new ElasticClient(new ConnectionSettings(server).DefaultIndex("old_data"));
}
[HttpGet("search")]
public IActionResult QueryStock()
{
var response = _client.Search<ProductStats>(s => s
.Query(q => q
.Range(r => r
.Field(f => f.StockQuantity)
.GreaterThanOrEqualTo(100)
)
)
);
return Ok(response.Documents.ToList());
}
}
}