预处理管道
Elasticsearch中的预处理管道是一系列按照声明它们的相同顺序执行的处理器。
以下创建了两个用于本文测试的实体类:
public class Person
{
public int Id { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public string IpAddress { get; set; }
public GeoIp GeoIp { get; set; }
}
public class GeoIp
{
public string CityName { get; set; }
public string ContinentName { get; set; }
public string CountryIsoCode { get; set; }
public GeoLocation Location { get; set; }
public string RegionName { get; set; }
}
使用NEST创建预处理管道
在NEST中,假设我们正在索引Person文档,我们可以创建一个预处理管道,在文档被索引之前,在这个预处理管道中对文档进行加工和处理。
假设我们的应用程序总是希望姓氏大写,并且首字母被索引到它们自己的字段中。同时,我们还有一个IP地址,我们想把它转换成人类可读的地理位置。
在NEST中,我们可以通过创建一个自定义映射和创建一个预处理管道来实现这个需求。然后可以按原样使用Person类型,而无需进行任何更改。
client.Indices.Create("people", c => c
.Map<Person>(p => p
.AutoMap()
.Properties(props => props
.Keyword(t => t.Name("initials"))
.Ip(t => t.Name(dv => dv.IpAddress))
.Object<GeoIp>(t => t.Name(dv => dv.GeoIp))
)
)
);
client.Ingest.PutPipeline("person-pipeline", p => p
.Processors(ps => ps
.Uppercase<Person>(s => s
.Field(t => t.LastName)
)
.Script(s => s
.Lang("painless")
.Source("ctx.initials = ctx.firstName.substring(0,1) + ctx.lastName.substring(0,1)")
)
.GeoIp<Person>(s => s
.Field(i => i.IpAddress)
.TargetField(i => i.GeoIp)
)
)
);
var person = new Person
{
Id = 1,
FirstName = "Martijn",
LastName = "Laarman",
IpAddress = "139.130.4.5"
};
var indexResponse = client.Index(person, p => p.Index("people").Pipeline("person-pipeline"));
NEST中设置预处理超时时间
当指定了预处理管道时,索引时将增加文档的开销,如上面给出的示例,执行大写和Painless脚本。
在NEST中,对于数据量大的请求,我们可以增加默认索引超时时间,以避免出现请求超时异常。
client.Bulk(b => b
.Index("people")
.Pipeline("person-pipeline")
.Timeout("5m") // 增加服务端批量执行的超时时间,此处设置为5分钟
.Index<Person>(/*snip*/)
.Index<Person>(/*snip*/)
.Index<Person>(/*snip*/)
.RequestConfiguration(rc => rc
.RequestTimeout(TimeSpan.FromMinutes(5)) // 增加HTTP请求的超时时间,此处设置为5分钟
)
);
发表评论
登录用户才能发表评论, 请 登 录 或者 注册