diff --git a/.gitignore b/.gitignore index 6a6ec5c..656444b 100644 --- a/.gitignore +++ b/.gitignore @@ -76,3 +76,4 @@ logs_*/ .pytest_cache models/ +model_cache/ diff --git a/@ b/@ deleted file mode 100644 index 5de1e4a..0000000 --- a/@ +++ /dev/null @@ -1,17 +0,0 @@ - -# Please enter the commit message for your changes. Lines starting -# with '#' will be ignored, and an empty message aborts the commit. -# -# On branch master -# Your branch is ahead of 'origin/master' by 3 commits. -# (use "git push" to publish your local commits) -# -# Changes to be committed: -# modified: README.md -# modified: docs/Usage-Guide.md -# modified: scripts/service_ctl.sh -# new file: status.sh -# -# Changes not staged for commit: -# modified: third-party/clip-as-service (untracked content) -# diff --git a/] b/] deleted file mode 100644 index bd63c3d..0000000 --- a/] +++ /dev/null @@ -1,17 +0,0 @@ -docs -# Please enter the commit message for your changes. Lines starting -# with '#' will be ignored, and an empty message aborts the commit. -# -# On branch master -# Your branch is ahead of 'origin/master' by 5 commits. -# (use "git push" to publish your local commits) -# -# Changes to be committed: -# modified: config/config.yaml -# modified: docs/TODO.txt -# modified: "docs/\346\220\234\347\264\242API\345\257\271\346\216\245\346\214\207\345\215\227-07-\345\276\256\346\234\215\345\212\241\346\216\245\345\217\243\357\274\210Embedding-Reranker-Translation\357\274\211.md" -# modified: "docs/\347\233\270\345\205\263\346\200\247\346\243\200\347\264\242\344\274\230\345\214\226\350\257\264\346\230\216.md" -# -# Changes not staged for commit: -# modified: third-party/clip-as-service (untracked content) -# diff --git a/config/config.yaml b/config/config.yaml index c1cacb7..865bf6f 100644 --- a/config/config.yaml +++ b/config/config.yaml @@ -131,7 +131,7 @@ function_score: # 重排配置(provider/URL 在 services.rerank) rerank: enabled: true - rerank_window: 384 + rerank_window: 400 timeout_sec: 15.0 weight_es: 0.4 weight_ai: 0.6 @@ -275,7 +275,7 @@ services: max_docs: 1000 normalize: true # 服务内后端(reranker 进程启动时读取) - backend: "qwen3_transformers" # bge | qwen3_vllm | qwen3_transformers | dashscope_rerank + backend: "qwen3_vllm" # bge | qwen3_vllm | qwen3_transformers | dashscope_rerank backends: bge: model_name: "BAAI/bge-reranker-v2-m3" @@ -296,15 +296,18 @@ services: enforce_eager: false infer_batch_size: 100 sort_by_doc_length: true - length_sort_mode: "char" # char | token - instruction: "rank products by given query" + # "rank products by given query" 比 “Given a query, score the product for relevance” 更好点 + instruction: "rank products by given query" + # instruction: "Given a query, score the product for relevance" qwen3_transformers: model_name: "Qwen/Qwen3-Reranker-0.6B" instruction: "rank products by given query" + # instruction: "Score the product’s relevance to the given query" max_length: 8192 batch_size: 64 use_fp16: true - attn_implementation: "flash_attention_2" + # sdpa:默认无需 flash-attn;若已安装 flash_attn 可改为 flash_attention_2 + attn_implementation: "sdpa" dashscope_rerank: model_name: "qwen3-rerank" # 按地域选择 endpoint: diff --git a/docs/DEVELOPER_GUIDE.md b/docs/DEVELOPER_GUIDE.md index 847b3e7..4b9c5ca 100644 --- a/docs/DEVELOPER_GUIDE.md +++ b/docs/DEVELOPER_GUIDE.md @@ -360,7 +360,7 @@ services: ### 7.6 新增后端清单(以 Qwen3-Reranker 为例) 1. **实现协议**:在 `reranker/backends/qwen3_vllm.py` 中实现类,提供 `score_with_meta(query, docs, normalize) -> (scores, meta)`,输出与 docs 等长且顺序一致。 -2. **配置**:在 `config/config.yaml` 的 `services.rerank.backends` 下增加 `qwen3_vllm` 块(model_name、engine、max_model_len、gpu_memory_utilization、`infer_batch_size`、`sort_by_doc_length`、`length_sort_mode` 等);支持环境变量 `RERANK_BACKEND=qwen3_vllm`。 +2. **配置**:在 `config/config.yaml` 的 `services.rerank.backends` 下增加 `qwen3_vllm` 块(model_name、engine、max_model_len、gpu_memory_utilization、`infer_batch_size`、`sort_by_doc_length`等);支持环境变量 `RERANK_BACKEND=qwen3_vllm`。 3. **注册**:在 `reranker/backends/__init__.py` 的 `get_rerank_backend(name, config)` 中增加 `qwen3_vllm` 分支。 4. **服务启动**:`reranker/server.py` 启动时根据配置调用 `get_rerank_backend(backend_name, backend_cfg)` 得到实例。 5. **调用方**:无需修改;仅部署时启动使用新后端的 reranker 服务即可。 diff --git a/docs/TODO.txt b/docs/TODO.txt index 873a169..a022950 100644 --- a/docs/TODO.txt +++ b/docs/TODO.txt @@ -21,6 +21,15 @@ 如果有: 先做sku筛选,然后把最优的拼接到名称中,参与reranker。 +现在在reranker、分页之后、做填充的时候,已经有做sku的筛选。 +需要优化: +现在是,先做包含的判断,找到第一个 option_value被query包含的,则直接认为匹配。改为 +1. 第一轮:遍历完,如果有且仅有一个才这样。 +2. 第二轮:如果有多个,跳到3。如果没有,对每个词都走泛化词表进行匹配。 +3. 第三轮:如果有多个,那么对这多个,走embedding相关性取最高的。如果一个也没有,则对所有的走embedding相关性取最高的 +这个sku筛选也需要提取为一个独立的模块 + + 2026-03-21 10:29:23,698 - elastic_transport.transport - INFO - POST http://localhost:9200/search_products_tenant_163/_search?include_named_queries_score=false [status:200 duration:0.009s] 2026-03-21 10:29:23,700 - request_context - INFO - 分页详情回填 | ids=20 | filled=20 | took=7ms diff --git a/docs/工作总结-微服务性能优化与架构.md b/docs/工作总结-微服务性能优化与架构.md index abd3c31..802aeb7 100644 --- a/docs/工作总结-微服务性能优化与架构.md +++ b/docs/工作总结-微服务性能优化与架构.md @@ -41,7 +41,7 @@ - **精度**:`dtype: "float16"`,降低显存与计算量。 - **Prefix Caching**:`enable_prefix_caching: true`,对重复前缀(如相同 query)做缓存,减少重复计算。 - **CUDA 图**:`enforce_eager: false`(默认),利用 vLLM 的 CUDA graph 降低 kernel 启动开销。 -- **按文档长度分批**:`sort_by_doc_length: true`,请求内先按文档长度排序再按 `infer_batch_size` 分批推理,减少 padding 浪费;`length_sort_mode: "char"`(更快,短文本推荐)或 `"token"`(更精确)。 +- **按文档长度分批**:`sort_by_doc_length: true`,请求内先按文档长度排序再按 `infer_batch_size` 分批推理,减少 padding 浪费。 - **参数搜索结论**:在 T4、1000-doc 口径下对 `infer_batch_size` 做了 24/32/48/64 对比;**单请求延迟(c=1)** 上 `infer_batch_size=64` 最优,故当前默认 `infer_batch_size: 64`;`max_model_len: 256` 满足 query+doc 短文本场景;`gpu_memory_utilization: 0.36` 与 T4 16GB 匹配。 **具体配置**(`config/config.yaml` → `services.rerank.backends.qwen3_vllm`): @@ -56,7 +56,6 @@ enable_prefix_caching: true enforce_eager: false infer_batch_size: 64 sort_by_doc_length: true -length_sort_mode: "char" instruction: "Given a shopping query, rank product titles by relevance" ``` 环境变量覆盖:`RERANK_BACKEND`、`RERANKER_SERVICE_URL`、`RERANK_VLLM_INFER_BATCH_SIZE`、`RERANK_VLLM_SORT_BY_DOC_LENGTH` 等。启停:`./scripts/service_ctl.sh start reranker`,健康:`curl -sS http://127.0.0.1:6007/health`。 diff --git a/docs/搜索API对接指南-07-微服务接口(Embedding-Reranker-Translation).md b/docs/搜索API对接指南-07-微服务接口(Embedding-Reranker-Translation).md index 300d0db..274f6eb 100644 --- a/docs/搜索API对接指南-07-微服务接口(Embedding-Reranker-Translation).md +++ b/docs/搜索API对接指南-07-微服务接口(Embedding-Reranker-Translation).md @@ -161,7 +161,7 @@ curl "http://localhost:6008/ready" 说明:默认后端为 `qwen3_vllm`(`Qwen/Qwen3-Reranker-0.6B`),需要可用 GPU 显存。 -补充:`docs` 的请求大小与模型推理 `batch size` 解耦。即使一次传入 1000 条文档,服务端也会按 `services.rerank.backends.qwen3_vllm.infer_batch_size` 自动拆分;若 `sort_by_doc_length=true`,会先按文档长度排序后分批,减少 padding,再按原输入顺序返回分数。`length_sort_mode` 可选 `char`(更快)或 `token`(更精确)。 +补充:`docs` 的请求大小与模型推理 `batch size` 解耦。即使一次传入 1000 条文档,服务端也会按 `services.rerank.backends.qwen3_vllm.infer_batch_size` 自动拆分。 #### 7.2.1 `POST /rerank` — 结果重排 diff --git a/docs/相关性检索优化说明.md b/docs/相关性检索优化说明.md index f23c2f7..ab4d70a 100644 --- a/docs/相关性检索优化说明.md +++ b/docs/相关性检索优化说明.md @@ -267,3 +267,17 @@ python ./scripts/eval_search_quality.py 3. 源语种不在索引语言,翻译全部失败(验证多目标 fallback) 4. 自定义 `original_query_fallback_boost_when_translation_missing` 生效 5. 非 `zh/en` 语种字段动态拼接(如 `de/fr/es`) + + + +## reranker方面: +BAAI/bge-reranker-v2-m3的一个严重badcase: +q=黑色中长半身裙 + +Rerank score: 0.0785 +title.zh: 2026款韩版高腰显瘦雪尼尔包臀裙灯芯绒开叉中长款咖啡色半身裙女 +title.en: 2026 Korean-style High-waisted Slimming Corduroy Skirt with Slit, Mid-Length Coffee-colored Skirt for Women + +Rerank score: 0.9643 +title.en: Black Half-high Collar Base Shirt Women's Autumn and Winter fleece-lined Contrast Color Pure Desire Design Sense Horn Sleeve Ruffled Inner Top +title.zh: 黑色高领半高领女士秋冬内搭加绒拼色纯欲设计荷叶边袖内衬上衣 diff --git a/reranker/DEPLOYMENT_AND_TUNING.md b/reranker/DEPLOYMENT_AND_TUNING.md index fc181ed..e289135 100644 --- a/reranker/DEPLOYMENT_AND_TUNING.md +++ b/reranker/DEPLOYMENT_AND_TUNING.md @@ -93,19 +93,14 @@ curl -sS http://127.0.0.1:6007/health - 调用方一次可传入 1000 docs(业务需求) - 服务端按 `infer_batch_size` 自动拆批推理(模型效率需求) - -### 4.2 先排序再分批,降低 padding 浪费 - - `sort_by_doc_length: true`:按长度排序后再分批 -- `length_sort_mode: "char"`:短文本场景下开销更低,默认推荐 -- `length_sort_mode: "token"`:长度估计更精确,但有额外 tokenizer 开销 -### 4.3 全局去重后回填 +### 4.2 全局去重后回填 - 对 docs 进行全局去重(非“仅相邻去重”) - 推理后按原请求顺序回填 scores,保证接口契约稳定 -### 4.4 启动稳定性修复 +### 4.3 启动稳定性修复 - `service_ctl.sh` 对 reranker 使用独立启动路径 - 增加“稳定健康检查”(连续健康探测)避免“刚 healthy 即退出”的假阳性 @@ -159,7 +154,7 @@ curl -sS http://127.0.0.1:6007/health ## 7. 生产建议 -- 默认保持:`infer_batch_size: 64`、`sort_by_doc_length: true`、`length_sort_mode: "char"` +- 默认保持:`infer_batch_size: 64`、`sort_by_doc_length: true` - 满足以下条件时可考虑提高到 `96`:业务以吞吐优先、可接受更高单请求延迟、已通过同机同数据压测验证收益 - 每次改动后都必须复跑 `benchmark_reranker_1000docs.sh` 并归档结果 diff --git a/reranker/README.md b/reranker/README.md index 9d13809..4be9625 100644 --- a/reranker/README.md +++ b/reranker/README.md @@ -24,7 +24,7 @@ Reranker 服务提供统一的 `/rerank` API,支持可插拔后端(BGE、Qwe - `reranker/config.py`:服务端口、MAX_DOCS、NORMALIZE 等(后端参数在 config.yaml) ## 依赖 -- 通用:`torch`、`modelscope`、`fastapi`、`uvicorn`(见项目 `requirements.txt` / `requirements_ml.txt`) +- 通用:`torch`、`transformers`、`fastapi`、`uvicorn`(隔离环境见 `requirements_reranker_service.txt`;全量 ML 环境另见 `requirements_ml.txt`) - **Qwen3-vLLM 后端**:`vllm>=0.8.5`、`transformers>=4.51.0`(仅当使用 `backend: qwen3_vllm` 时需 vLLM) - **Qwen3-Transformers 后端**:`transformers>=4.51.0`、`torch`(无需 vLLM,适合 CPU 或小显存) ```bash @@ -53,7 +53,6 @@ services: max_model_len: 256 infer_batch_size: 64 sort_by_doc_length: true - length_sort_mode: "char" # char | token enable_prefix_caching: true enforce_eager: false instruction: "Given a shopping query, rank product titles by relevance" @@ -157,7 +156,7 @@ uvicorn reranker.server:app --host 0.0.0.0 --port 6007 --log-level info ## Notes - 无请求级缓存;输入按字符串去重后推理,再按原始顺序回填分数。 - 空或 null 的 doc 跳过并计为 0。 -- **Qwen3-vLLM 分批策略**:`docs` 请求体可为 1000+,服务端会按 `infer_batch_size` 拆分;当 `sort_by_doc_length=true` 时,会先按文档长度排序后分批,减少 padding 开销,最终再按输入顺序回填分数。`length_sort_mode` 支持 `char`(默认,更快)与 `token`(更精确)。 +- **Qwen3-vLLM 分批策略**:`docs` 请求体可为 1000+,服务端会按 `infer_batch_size` 拆分;当 `sort_by_doc_length=true` 时,会先按文档长度排序后分批,减少 padding 开销,最终再按输入顺序回填分数。 - 运行时可用环境变量临时覆盖批量参数:`RERANK_VLLM_INFER_BATCH_SIZE`、`RERANK_VLLM_SORT_BY_DOC_LENGTH`。 - **Qwen3-vLLM**:参考 [Qwen3-Reranker-0.6B](https://huggingface.co/Qwen/Qwen3-Reranker-0.6B),需 GPU 与较多显存;与 BGE 相比适合长文本、高吞吐场景(vLLM 前缀缓存)。 -- **Qwen3-Transformers**:官方 Transformers Usage 方式,无需 vLLM;适合 CPU 或小显存,可选 `attn_implementation: "flash_attention_2"` 加速。 +- **Qwen3-Transformers**:官方 Transformers Usage 方式,无需 vLLM;适合 CPU 或小显存。默认 `attn_implementation: "sdpa"`;若已安装 `flash_attn` 可设 `flash_attention_2`(未安装时服务会自动回退到 sdpa)。 diff --git a/reranker/backends/qwen3_vllm.py b/reranker/backends/qwen3_vllm.py index 36b3e75..5dbe952 100644 --- a/reranker/backends/qwen3_vllm.py +++ b/reranker/backends/qwen3_vllm.py @@ -76,7 +76,7 @@ class Qwen3VLLMRerankerBackend: dtype = str(self._config.get("dtype", "float16")).strip().lower() self._instruction = str( self._config.get("instruction") - or "Given a shopping query, rank product titles by relevance" + or "Given a query, score the product for relevance" ) infer_batch_size = os.getenv("RERANK_VLLM_INFER_BATCH_SIZE") or self._config.get("infer_batch_size", 64) sort_by_doc_length = os.getenv("RERANK_VLLM_SORT_BY_DOC_LENGTH") diff --git a/reranker/bge_reranker.py b/reranker/bge_reranker.py index 221818a..e98c62a 100644 --- a/reranker/bge_reranker.py +++ b/reranker/bge_reranker.py @@ -170,13 +170,14 @@ class BGEReranker: output_scores[orig_idx] = float(unique_scores[unique_idx]) # Log per-doc scores (aligned to original docs order) - try: - lines = [] - for i, d in enumerate(docs[:100]): - lines.append(f"{output_scores[i]},{'' if d is None else str(d)}") - logger.info("[BGE_RERANKER] query:%s Scores (score,doc):\n%s", query, "\n".join(lines)) - except Exception: - pass + if 0: + try: + lines = [] + for i, d in enumerate(docs[:100]): + lines.append(f"{output_scores[i]},{'' if d is None else str(d)}") + logger.info("[BGE_RERANKER] query:%s Scores (score,doc):\n%s", query, "\n".join(lines)) + except Exception: + pass elapsed_ms = (time.time() - start_ts) * 1000.0 dedup_ratio = 0.0 -- libgit2 0.21.2