Link Search Menu Expand Document Documentation Menu

搜索数据

在 OpenSearch 中,有几种搜索数据的方法

  • 查询领域特定语言 (DSL):主要的 OpenSearch 查询语言,您可以使用它来创建复杂的、完全可定制的查询。
  • 查询字符串查询语言:一种简化的查询语言,您可以在搜索请求的查询参数或 OpenSearch Dashboards 中使用。
  • SQL:一种传统的查询语言,它弥合了传统关系数据库概念与 OpenSearch 面向文档的数据存储的灵活性之间的差距。
  • 管道处理语言 (PPL):用于 OpenSearch 可观测性的主要语言。PPL 使用管道语法将命令链接到查询中。
  • Dashboards 查询语言 (DQL):一种简单的基于文本的查询语言,用于在 OpenSearch Dashboards 中过滤数据。

本教程简要介绍了如何使用 查询字符串查询查询 DSL 进行搜索。

准备数据

对于本教程,如果您尚未这样做,则需要为学生数据建立索引。您可以先删除 students 索引 (DELETE /students),然后发送以下批量请求

POST _bulk
{ "create": { "_index": "students", "_id": "1" } }
{ "name": "John Doe", "gpa": 3.89, "grad_year": 2022}
{ "create": { "_index": "students", "_id": "2" } }
{ "name": "Jonathan Powers", "gpa": 3.85, "grad_year": 2025 }
{ "create": { "_index": "students", "_id": "3" } }
{ "name": "Jane Doe", "gpa": 3.52, "grad_year": 2024 }

检索索引中的所有文档

要检索索引中的所有文档,请发送以下请求

GET /students/_search

前面的请求等效于 match_all 查询,该查询匹配索引中的所有文档

GET /students/_search
{
  "query": {
    "match_all": {}
  }
}

OpenSearch 返回匹配的文档

{
  "took": 12,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": {
      "value": 3,
      "relation": "eq"
    },
    "max_score": 1,
    "hits": [
      {
        "_index": "students",
        "_id": "1",
        "_score": 1,
        "_source": {
          "name": "John Doe",
          "gpa": 3.89,
          "grad_year": 2022
        }
      },
      {
        "_index": "students",
        "_id": "2",
        "_score": 1,
        "_source": {
          "name": "Jonathan Powers",
          "gpa": 3.85,
          "grad_year": 2025
        }
      },
      {
        "_index": "students",
        "_id": "3",
        "_score": 1,
        "_source": {
          "name": "Jane Doe",
          "gpa": 3.52,
          "grad_year": 2024
        }
      }
    ]
  }
}

响应正文字段

前面的响应包含以下字段。

took

took 字段包含查询运行所花费的时间,以毫秒为单位。

timed_out

此字段指示请求是否超时。如果请求超时,则 OpenSearch 返回在超时之前收集的结果。您可以通过提供 timeout 查询参数来设置所需的超时值

GET /students/_search?timeout=20ms

_shards

_shards 对象指定查询运行的总分片数以及成功或失败的分片数。如果分片本身及其所有副本都不可用,则分片可能会失败。如果任何涉及的分片失败,OpenSearch 将继续在剩余的分片上运行查询。

hits

hits 对象包含匹配文档的总数和文档本身(在 hits 数组中列出)。每个匹配的文档都包含 _index_id 字段以及 _source 字段,其中包含完整的原始索引文档。

每个文档在 _score 字段中都有一个相关性分数。因为您运行了 match_all 搜索,所以所有文档的分数都设置为 1(它们的相关性没有差异)。max_score 字段包含任何匹配文档的最高分数。

查询字符串查询

查询字符串查询是轻量级的但功能强大。您可以将查询字符串查询作为 q 查询参数发送。例如,以下查询搜索名称为 john 的学生

GET /students/_search?q=name:john

OpenSearch 返回匹配的文档

{
  "took": 18,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": {
      "value": 1,
      "relation": "eq"
    },
    "max_score": 0.9808291,
    "hits": [
      {
        "_index": "students",
        "_id": "1",
        "_score": 0.9808291,
        "_source": {
          "name": "John Doe",
          "grade": 12,
          "gpa": 3.89,
          "grad_year": 2022,
          "future_plans": "John plans to be a computer science major"
        }
      }
    ]
  }
}

有关查询字符串语法的更多信息,请参阅 查询字符串查询语言

查询 DSL

使用查询 DSL,您可以创建更复杂和自定义的查询。

您可以对映射为 text 的字段运行全文搜索。默认情况下,文本字段由 default 分析器分析。分析器将文本拆分为术语并将其更改为小写。有关 OpenSearch 分析器的更多信息,请参阅 分析器

例如,以下查询搜索名称为 john 的学生

GET /students/_search
{
  "query": {
    "match": {
      "name": "john"
    }
  }
}

响应包含匹配的文档

{
  "took": 13,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": {
      "value": 1,
      "relation": "eq"
    },
    "max_score": 0.9808291,
    "hits": [
      {
        "_index": "students",
        "_id": "1",
        "_score": 0.9808291,
        "_source": {
          "name": "John Doe",
          "gpa": 3.89,
          "grad_year": 2022
        }
      }
    ]
  }
}

请注意,查询文本是小写的,而字段中的文本不是,但查询仍然返回匹配的文档。

您可以重新排序搜索字符串中的术语。例如,以下查询搜索 doe john

GET /students/_search
{
  "query": {
    "match": {
      "name": "doe john"
    }
  }
}

响应包含两个匹配的文档

{
  "took": 14,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": {
      "value": 2,
      "relation": "eq"
    },
    "max_score": 1.4508327,
    "hits": [
      {
        "_index": "students",
        "_id": "1",
        "_score": 1.4508327,
        "_source": {
          "name": "John Doe",
          "gpa": 3.89,
          "grad_year": 2022
        }
      },
      {
        "_index": "students",
        "_id": "3",
        "_score": 0.4700036,
        "_source": {
          "name": "Jane Doe",
          "gpa": 3.52,
          "grad_year": 2024
        }
      }
    ]
  }
}

match 查询类型默认使用 OR 作为运算符,因此查询在功能上是 doe OR johnJohn DoeJane Doe 都匹配了单词 doe,但 John Doe 的得分更高,因为它也匹配了 john

name 字段包含 name.keyword 子字段,该字段由 OpenSearch 自动添加。如果您以类似于先前请求的方式搜索 name.keyword 字段

GET /students/_search
{
  "query": {
    "match": {
      "name.keyword": "john"
    }
  }
}

然后,请求将不返回任何点击,因为 keyword 字段必须完全匹配。

但是,如果您搜索确切的文本 John Doe

GET /students/_search
{
  "query": {
    "match": {
      "name.keyword": "John Doe"
    }
  }
}

OpenSearch 返回匹配的文档

{
  "took": 19,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": {
      "value": 1,
      "relation": "eq"
    },
    "max_score": 0.9808291,
    "hits": [
      {
        "_index": "students",
        "_id": "1",
        "_score": 0.9808291,
        "_source": {
          "name": "John Doe",
          "gpa": 3.89,
          "grad_year": 2022
        }
      }
    ]
  }
}

过滤器

使用布尔查询,您可以向查询中添加过滤器子句,以用于具有确切值的字段

术语过滤器匹配特定术语。例如,以下布尔查询搜索毕业年份为 2022 年的学生

GET students/_search
{
  "query": { 
    "bool": { 
      "filter": [ 
        { "term":  { "grad_year": 2022 }}
      ]
    }
  }
}

使用范围过滤器,您可以指定值的范围。例如,以下布尔查询搜索 GPA 大于 3.6 的学生

GET students/_search
{
  "query": { 
    "bool": { 
      "filter": [ 
        { "range": { "gpa": { "gt": 3.6 }}}
      ]
    }
  }
}

有关过滤器的更多信息,请参阅 查询和过滤器上下文

复合查询

复合查询允许您组合多个查询或过滤器子句。布尔查询是复合查询的一个示例。

例如,要搜索名称与 doe 匹配的学生,并按毕业年份和 GPA 过滤,请使用以下请求

GET students/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "match": {
            "name": "doe"
          }
        },
        { "range": { "gpa": { "gte": 3.6, "lte": 3.9 } } },
        { "term":  { "grad_year": 2022 }}
      ]
    }
  }
}

有关布尔和其他复合查询的更多信息,请参阅 复合查询

搜索方法

除了本教程中描述的传统全文搜索之外,OpenSearch 还支持一系列机器学习 (ML) 驱动的搜索方法,包括 k-NN、语义、多模态、稀疏、混合和会话搜索。有关所有 OpenSearch 支持的搜索方法的信息,请参阅 搜索

后续步骤

  • 有关可用查询类型的信息,请参阅 查询 DSL
  • 有关可用搜索方法的信息,请参阅 搜索