ElasticSearch - 在不影响 "parent" 对象的情况下过滤嵌套对象
ElasticSearch - Filter nested objects without affecting the "parent" object
我有一个博客对象的 ElasticSearch 映射,其中包含用于评论的嵌套字段。这是为了让用户可以向上面显示的博客内容添加评论。 comments 字段有一个 published 标志,用于确定评论是否可以被其他用户查看或只能由主要用户查看。
"blogs" :[
{
"id":1,
"content":"This is my super cool blog post",
"createTime":"2017-05-31",
"comments" : [
{"published":false, "comment":"You can see this!!","time":"2017-07-11"}
]
},
{
"id":2,
"content":"Hey Guys!",
"createTime":"2013-05-30",
"comments" : [
{"published":true, "comment":"I like this post!","time":"2016-07-01"},
{"published":false, "comment":"You should not be able to see this","time":"2017-10-31"}
]
},
{
"id":3,
"content":"This is a blog without any comments! You can still see me.",
"createTime":"2017-12-21",
"comments" : None
},
]
我希望能够过滤评论,以便为每个博客对象仅显示 True 评论。我想展示每个博客,而不仅仅是那些有真实评论的博客。我在网上找到的所有其他解决方案似乎都会影响我的博客对象。有没有办法在不影响所有博客查询的情况下过滤掉评论对象?
所以上面的例子会在这样的查询之后 returned:
"blogs" :[
{
"id":1,
"content":"This is my super cool blog post",
"createTime":"2017-05-31",
"comments" : None # OR EMPTY LIST
},
{
"id":2,
"content":"Hey Guys!",
"createTime":"2013-05-30",
"comments" : [
{"published":true, "comment":"I like this post!","time":"2016-07-01"}
]
},
{
"id":3,
"content":"This is a blog without any comments! You can still see me.",
"createTime":"2017-12-21",
"comments" : None
},
]
示例仍然显示没有评论或虚假评论的博客。
这可能吗?
我一直在使用此示例中的嵌套查询:
但是这个例子影响的是博客本身,不会return只有虚假评论或没有评论的博客。
请帮忙:) 谢谢!
好的,所以发现显然没有办法使用 elasticsearch 查询来做到这一点。但是我想出了一种在 django/python 方面执行此操作的方法(这正是我所需要的)。我不确定是否有人需要此信息,但如果您需要此信息并且您正在使用 Django/ES/REST,这就是我所做的。
我按照 elasticsearch-dsl 文档 (http://elasticsearch-dsl.readthedocs.io/en/latest/) 将 elasticsearch 与我的 Django 应用程序连接起来。然后我使用 rest_framework_elasticsearch 包框架来创建视图。
要创建仅查询 elasticsearch 项目列表中 True
嵌套属性的 Mixin,请创建 rest_framework_elastic.es_mixins ListElasticMixin 对象的 mixin 子类。然后在我们的新 mixin 中覆盖 es_representation 定义如下。
class MyListElasticMixin(ListElasticMixin):
@staticmethod
def es_representation(iterable):
items = ListElasticMixin.es_representation(iterable)
for item in items:
for key in item:
if key == 'comments' and item[key] is not None:
for comment in reversed(item[key]):
if not comment['published']:
item[key].remove(comment)
return items
确保在评论的 for 循环中使用 reversed
函数,否则您将跳过列表中的一些评论。
这是我在我看来使用的这个新过滤器。
class MyViewSet(MyListElasticMixin, viewsets.ViewSet):
# Your view code here
def get(self, request, *args, **kwargs):
return self.list(request, *args, **kwargs)
在python这边做肯定更容易,也更有效。
我有一个博客对象的 ElasticSearch 映射,其中包含用于评论的嵌套字段。这是为了让用户可以向上面显示的博客内容添加评论。 comments 字段有一个 published 标志,用于确定评论是否可以被其他用户查看或只能由主要用户查看。
"blogs" :[
{
"id":1,
"content":"This is my super cool blog post",
"createTime":"2017-05-31",
"comments" : [
{"published":false, "comment":"You can see this!!","time":"2017-07-11"}
]
},
{
"id":2,
"content":"Hey Guys!",
"createTime":"2013-05-30",
"comments" : [
{"published":true, "comment":"I like this post!","time":"2016-07-01"},
{"published":false, "comment":"You should not be able to see this","time":"2017-10-31"}
]
},
{
"id":3,
"content":"This is a blog without any comments! You can still see me.",
"createTime":"2017-12-21",
"comments" : None
},
]
我希望能够过滤评论,以便为每个博客对象仅显示 True 评论。我想展示每个博客,而不仅仅是那些有真实评论的博客。我在网上找到的所有其他解决方案似乎都会影响我的博客对象。有没有办法在不影响所有博客查询的情况下过滤掉评论对象?
所以上面的例子会在这样的查询之后 returned:
"blogs" :[
{
"id":1,
"content":"This is my super cool blog post",
"createTime":"2017-05-31",
"comments" : None # OR EMPTY LIST
},
{
"id":2,
"content":"Hey Guys!",
"createTime":"2013-05-30",
"comments" : [
{"published":true, "comment":"I like this post!","time":"2016-07-01"}
]
},
{
"id":3,
"content":"This is a blog without any comments! You can still see me.",
"createTime":"2017-12-21",
"comments" : None
},
]
示例仍然显示没有评论或虚假评论的博客。
这可能吗?
我一直在使用此示例中的嵌套查询:
但是这个例子影响的是博客本身,不会return只有虚假评论或没有评论的博客。
请帮忙:) 谢谢!
好的,所以发现显然没有办法使用 elasticsearch 查询来做到这一点。但是我想出了一种在 django/python 方面执行此操作的方法(这正是我所需要的)。我不确定是否有人需要此信息,但如果您需要此信息并且您正在使用 Django/ES/REST,这就是我所做的。
我按照 elasticsearch-dsl 文档 (http://elasticsearch-dsl.readthedocs.io/en/latest/) 将 elasticsearch 与我的 Django 应用程序连接起来。然后我使用 rest_framework_elasticsearch 包框架来创建视图。
要创建仅查询 elasticsearch 项目列表中 True
嵌套属性的 Mixin,请创建 rest_framework_elastic.es_mixins ListElasticMixin 对象的 mixin 子类。然后在我们的新 mixin 中覆盖 es_representation 定义如下。
class MyListElasticMixin(ListElasticMixin):
@staticmethod
def es_representation(iterable):
items = ListElasticMixin.es_representation(iterable)
for item in items:
for key in item:
if key == 'comments' and item[key] is not None:
for comment in reversed(item[key]):
if not comment['published']:
item[key].remove(comment)
return items
确保在评论的 for 循环中使用 reversed
函数,否则您将跳过列表中的一些评论。
这是我在我看来使用的这个新过滤器。
class MyViewSet(MyListElasticMixin, viewsets.ViewSet):
# Your view code here
def get(self, request, *args, **kwargs):
return self.list(request, *args, **kwargs)
在python这边做肯定更容易,也更有效。