C# 如何在Elasticsearch 5.6中将枚举保存为字符串而不使用属性映射(使用嵌套)
我想在Elasticsearch索引中以字符串的形式存储所有枚举。因为我使用的模型需要独立于任何特定技术,所以我不能使用 我知道您可以在创建C# 如何在Elasticsearch 5.6中将枚举保存为字符串而不使用属性映射(使用嵌套),c#,elasticsearch,nest,C#,elasticsearch,Nest,我想在Elasticsearch索引中以字符串的形式存储所有枚举。因为我使用的模型需要独立于任何特定技术,所以我不能使用 我知道您可以在创建连接设置时传递SerializerFactory,但我不知道什么选项将更改枚举的序列化 下面是我用来连接NEST的代码: var serializers = new SerializerFactory(<what to put here?>); var settings = new ConnectionSettings(myUri, serial
连接设置时传递SerializerFactory
,但我不知道什么选项将更改枚举的序列化
下面是我用来连接NEST的代码:
var serializers = new SerializerFactory(<what to put here?>);
var settings = new ConnectionSettings(myUri, serializers)
.DefaultIndex(myIndex)
.InferMappingFor<MyModel>(m => m
.IdProperty(s => s.MyId)
);
var client = new ElasticClient(settings);
嵌套版本:5.5.0
(最新版本)多亏了@RussCam,我才能找到解决方案。以下是我现在使用的代码:
var connectionPool = new SingleNodeConnectionPool(new Uri(myUri));
var connection = new HttpConnection();
var serializers = new SerializerFactory((s, v) => s.Converters.Add(new StringEnumConverter()) );
var settings = new ConnectionSettings(connectionPool, connection, serializers)
.DefaultIndex(StatusIndex)
.InferMappingFor<MyModel>(m => m
.IdProperty(s => s.MyId)
);
var client = new ElasticClient(settings);
var connectionPool=newsinglenodeconnectionpool(newuri(myUri));
var connection=新的HttpConnection();
var serializers=new SerializerFactory((s,v)=>s.Converters.Add(new StringEnumConverter());
var设置=新连接设置(连接池、连接、序列化程序)
.DefaultIndex(状态索引)
.InferMappingFor(m=>m
.IdProperty(s=>s.MyId)
);
var客户端=新的ElasticClient(设置);
第三行是重要的一行。添加到SerializerFactory
的Converters
中的StringEnumConverter
将使每个枚举序列化为字符串并从字符串反序列化(使用此ElasticClient
)。我使用了@Leifb建议的类似方法(在属性上使用StringEnumConverter):
但是,如果对类型使用自动映射,则会出现问题,因此我为该类型创建了一个通用枚举来字符串属性访问者:
var result = await _client.PutIndexTemplateAsync(
p.TemplateName, s=>s
.Template(p.Template)
.Mappings(m=>m
.Map(p.TemplateName, mm=>mm
.AutoMap<MyType>(new EnumAsStringPropertyVisitor())
)
));
public class EnumAsStringPropertyVisitor : NoopPropertyVisitor
{
public override void Visit(
INumberProperty type,
PropertyInfo propertyInfo,
ElasticsearchPropertyAttributeBase attribute)
{
if(propertyInfo.PropertyType.IsEnum)
{
type.Type = "keyword";
}
}
}
var result=await\u client.PutIndexTemplateAsync(
p、 TemplateName,s=>s
.模板(p.Template)
.Mappings(m=>m
.Map(p.TemplateName,mm=>mm
.AutoMap(新的EnumAsStringPropertyVisitor())
)
));
公共类EnumAsStringPropertyVisitor:NoopPropertyVisitor
{
公众参观(
INumberProperty类型,
PropertyInfo PropertyInfo,
ElasticsearchPropertyAttributeBase属性)
{
if(propertyInfo.PropertyType.IsEnum)
{
type.type=“关键字”;
}
}
}
看看:。从JsonNetSerializer
派生,您可以为enum
的任何类型添加StringEnumConverter
:这使用的是旧版本的客户端,但是Func
委托可能是您想要添加到派生序列化程序上的ContractConverters
的内容:@RussCam谢谢,你的第一句话帮了大忙!
[JsonConverter(typeof(StringEnumConverter))]
public MyEnum Status {get;set;}
var result = await _client.PutIndexTemplateAsync(
p.TemplateName, s=>s
.Template(p.Template)
.Mappings(m=>m
.Map(p.TemplateName, mm=>mm
.AutoMap<MyType>(new EnumAsStringPropertyVisitor())
)
));
public class EnumAsStringPropertyVisitor : NoopPropertyVisitor
{
public override void Visit(
INumberProperty type,
PropertyInfo propertyInfo,
ElasticsearchPropertyAttributeBase attribute)
{
if(propertyInfo.PropertyType.IsEnum)
{
type.Type = "keyword";
}
}
}