仿京东电商商品搜索服务实战:基于 Elasticsearch 的实现与落地

在电商业务中,​商品搜索是核心功能之一 ​,其体验直接影响用户转化率。本文以 图灵商城商品搜索项目 为蓝本,系统拆解如何基于 Elasticsearch(ES) 构建一个高可用、高性能、高体验的仿京东商品搜索服务,涵盖 业务场景分析 → 文档建模 → DSL 查询构建 → Spring Boot 微服务落地 全流程,提供可直接复用的技术方案。


🔍 一、核心业务场景分析

图灵商城的商品搜索对标 ​京东搜索体验​,需支持以下六大核心能力:

  1. 关键字模糊查询
    • 支持对商品名称、关键词、副标题进行 中文分词检索
  2. 多条件精准筛选
    • 可按品牌、分类、商品属性(如 CPU、颜色、尺寸)、价格区间、库存状态等进行组合筛选;
  3. 自定义排序
    • 支持按销量、价格、上架时间进行 升序 / 降序 排序;
  4. 聚合统计展示
    • 搜索结果页实时聚合可选的品牌、分类、属性,实现 "边搜边筛" 的交互体验;
  5. 高亮显示
    • 对命中关键词进行 红色高亮,提升用户视觉感知;
  6. 分页加载
    • 支持分页查询,保障系统性能与响应速度。

🧱 二、Elasticsearch 商品文档建模

2.1 核心设计原则

为兼顾 ​检索效率、字段语义、关联准确性​,建模时遵循以下原则:

设计要点 技术实现
中文文本字段 使用​**ik_max_word 分词器**​,支持细粒度分词(如 "小米 11 手机" → [小米, 11, 手机])
精确匹配字段 定义为​**keyword 类型**​(如品牌名、分类名),避免分词干扰
多值动态属性 采用​**nested 嵌套类型**​,解决属性扁平化导致的"虚假匹配"问题
数值/布尔字段 使用 doublelongboolean 等原生类型,支持范围查询与排序
日期字段 定义为 date 类型,便于按上架时间排序

💡 为什么用 nested

若将属性数组扁平化存储(如 attrName: ["cpu", "颜色"], attrValue: ["2核", "黑色"]),ES 会丢失属性间的关联性,导致 "CPU=2 核 且 颜色=白色" 错误匹配到 "CPU=2 核 + 黑色" 和 "CPU=4 核 + 白色" 的商品。​**nested 类型保留对象完整性**​,确保多条件组合筛选精准无误。


2.2 商品文档结构示例

json 复制代码
{
  "id": "26",
  "name": "小米 11 手机",
  "keywords": "小米手机",
  "subTitle": "AI智慧全面屏 6GB+64GB 亮黑色 全网通版 4G手机",
  "price": 3999.0,
  "promotionPrice": "2999",
  "originalPrice": "5999",
  "pic": "<http://xxx/xiaomi.jpg>",
  "sale": 999,
  "hasStock": true,
  "salecount": 999,
  "putawayDate": "2021-04-01",
  "brandId": 6,
  "brandName": "小米",
  "categoryId": 19,
  "categoryName": "手机通讯",
  "attrs": [
    { "attrId": 1, "attrName": "cpu",     "attrValue": "2核" },
    { "attrId": 2, "attrName": "颜色",    "attrValue": "黑色" }
  ]
}

2.3 索引 Mapping 定义(product_db

json 复制代码
PUT product_db
{
  "mappings": {
    "properties": {
      "id": {"type": "long"},
      "name": {"type": "text", "analyzer": "ik_max_word"},
      "keywords": {"type": "text", "analyzer": "ik_max_word"},
      "subTitle": {"type": "text", "analyzer": "ik_max_word"},
      "price": {"type": "double"},
      "promotionPrice": {"type": "keyword"},
      "originalPrice": {"type": "keyword"},
      "pic": {"type": "keyword"},
      "salecount": {"type": "long"},
      "putawayDate": {"type": "date"},
      "hasStock": {"type": "boolean"},
      "brandId": {"type": "long"},
      "brandName": {"type": "keyword"},
      "brandImg": {"type": "keyword"},
      "categoryId": {"type": "long"},
      "categoryName": {"type": "keyword"},
      "attrs": {
        "type": "nested",
        "properties": {
          "attrId": {"type": "long"},
          "attrName": {"type": "keyword"},
          "attrValue": {"type": "keyword"}
        }
      }
    }
  }
}

✅ ​关键点​:

  • name/keywords/subTitle 使用 ik_max_word 实现 高召回率
  • brandName/categoryName/attrValue 使用 keyword 保证 筛选精确性
  • attrsnested,支撑 多属性 AND 组合查询

2.4 测试数据准备

导入 ​17 条多品类商品数据​,覆盖:

  • 品牌:小米、华为、苹果、海澜之家、耐克
  • 类目:手机、T 恤、电视、运动鞋、笔记本
  • 属性:CPU、颜色、尺寸、容量等

为后续 DSL 测试与微服务验证提供数据基础。


🔎 三、Elasticsearch DSL 查询语句构建

3.1 核心能力拆解

功能 DSL 实现方式
多字段模糊搜索 multi_match 覆盖 name/keywords/subTitle
精准过滤 filter 子句(品牌、分类、库存、属性)
价格区间 range 查询(gte/lte
嵌套属性筛选 nested 查询 +term 匹配
排序 sortsalecount/price/putawayDate
聚合统计 terms 聚合 +nested 聚合
高亮 highlight+ 自定义 `` 标签
分页 from+size

⚠️ ​性能提示​:

所有过滤条件(不参与评分)应放入 filter 而非 must,利用 BitSet 缓存 提升性能。


3.2 完整 DSL 示例

场景​:搜索 "手机",价格 2000--5000 元、有库存,按销量降序,聚合品牌/分类/属性,高亮关键词。

json 复制代码
GET product_db/_search
{
  "from": 0,
  "size": 20,
  "query": {
    "bool": {
      "must": [
        {
          "multi_match": {
            "query": "手机",
            "fields": ["name", "keywords", "subTitle"]
          }
        }
      ],
      "filter": [
        { "term": { "hasStock": true } },
        { "range": { "price": { "gte": 2000, "lte": 5000 } } }
      ]
    }
  },
  "aggs": {
    "brandId_aggs": {
      "terms": { "field": "brandId", "size": 10 },
      "aggs": {
        "brandName_aggs": { "terms": { "field": "brandName" } },
        "brandImg_aggs": { "terms": { "field": "brandImg" } }
      }
    },
    "categoryId_aggs": {
      "terms": { "field": "categoryId", "size": 10 },
      "aggs": {
        "categoryName_aggs": { "terms": { "field": "categoryName" } }
      }
    },
    "attrs_aggs": {
      "nested": { "path": "attrs" },
      "aggs": {
        "attrId_aggs": {
          "terms": { "field": "attrs.attrId" },
          "aggs": {
            "attrName_aggs": { "terms": { "field": "attrs.attrName" } },
            "attrValue_aggs": { "terms": { "field": "attrs.attrValue" } }
          }
        }
      }
    }
  },
  "sort": [{ "salecount": { "order": "desc" } }],
  "highlight": {
    "pre_tags": ["<b style='color:red'>"],
    "post_tags": ["</b>"],
    "fields": { "name": {} }
  }
}

⚙️ 四、Spring Boot 微服务落地实现

4.1 引入依赖

xml 复制代码
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
</dependency>

4.2 核心代码逻辑

4.2.1 构建搜索请求(startBuildRequestParam

  • Bool 查询组装
    • mustmulti_match 关键字
    • filter:品牌、分类、库存、价格、属性(nested
  • 价格解析 :支持 10_5000(区间)、_5000(≤5000)、10_(≥10)
  • 属性筛选 :解析 attrs=1_2核&2_蓝色 → 构建多个 nested 查询
  • 排序 & 分页 & 高亮:标准化处理

4.2.2 执行检索

java 复制代码
SearchResponse<EsProduct> response = client.search(searchRequest, EsProduct.class);

4.2.3 封装响应(startBuildResponseResult

  • 解析商品列表,替换高亮字段
  • 解析聚合结果 → BrandVo / CategoryVo / AttrVo
  • 计算总页数、当前页、分页导航

4.3 接口测试示例

复制代码
GET <http://localhost:8054/searchList>?
  keyword=手机&
  price=1_5000&
  hasStock=1&
  categoryId=19&
  attrs=2_蓝色&
  attrs=1_2核&
  sort=salecount_asc&
  pageNum=1&
  pageSize=20

✅ 支持 ​任意维度组合查询​,参数灵活可扩展。


🌟 五、核心技术亮点与总结

5.1 技术亮点

亮点 说明
精准建模 合理使用 text/keyword/nested/date,解决电商核心痛点
高性能查询 filter+nested 保证筛选精准性与查询效率
高体验交互 高亮 + 聚合 + 排序 → 还原京东式搜索体验
工程化落地 参数化解析 →​DSL → Java 对象​,代码清晰可维护
全场景覆盖 支持价格多格式、属性多组合、排序多维度、分页自定义

5.2 项目总结

本项目完整实现了 从需求到上线 的电商搜索闭环:

业务驱动 → 模型设计 → 查询优化 → 服务封装

该方案具备以下优势:

  • 可直接复用于实际电商项目
  • 易于扩展:可叠加拼音搜索、同义词、热度排序、个性化推荐
  • 可水平扩展:配合 ES 集群,支撑高并发场景

未来演进方向​:

  • 引入 NLP 语义理解 提升搜索相关性
  • 结合 用户行为日志 实现个性化排序
  • 使用 向量检索 支持"以图搜商品"

📌 ​结语​:

搜索不仅是"找得到",更是"找得准、找得快、找得爽"。

通过 Elasticsearch + Spring Boot 的深度整合,我们打造了一个 高性能、高体验、高可用 的电商搜索引擎,为业务增长提供坚实底座。

相关推荐
juniperhan17 小时前
Flink 系列第12篇:Flink 维表关联详解
大数据·数据仓库·分布式·flink
如来神掌十八式17 小时前
Elasticsearch的dsl语句学习
elasticsearch
嘉立创FPC苗工18 小时前
多层 FPC 阻抗控制:从原理到实践的全流程指南
大数据·制造·fpc·电路板
查古穆18 小时前
AI Agent 开发的工业化道路:Harness 架构深度解析
大数据·人工智能
qyz_hr18 小时前
2026年AI招聘选购:5大品牌核心差异对比(红海云 / Moka / 北森 / 肯耐珂萨 / 金蝶)
大数据·人工智能
xcbrand18 小时前
工业制造品牌全案公司哪家专业
大数据·人工智能·python·制造
南棱笑笑生18 小时前
20260420给万象奥科的开发板HD-RK3576-PI适配瑞芯微原厂的Buildroot时使用ll命令
java·大数据·elasticsearch·rockchip
Irene199119 小时前
大数据开发中常见的排序算法
大数据·排序算法
蓝眸少年CY19 小时前
Azkaban - 入门教程
大数据·azkaban
清 晨19 小时前
海外社媒内容审核加强跨境卖家如何避免限流
大数据·人工智能·矩阵·新媒体运营·内容营销