Text Ranking
Transformers
Safetensors
multilingual
t5gemma2
text2text-generation
reranker
encoder-decoder
FBNL
Retrieval
RAG
cosyy's picture
Update vllm_support/README.md
1d3dcd7 verified
|
Raw
History Blame Contribute Delete
7.59 kB
# KaLM-Reranker-V1-Nano vLLM Support
This directory contains the experimental vLLM 0.19.1 adapter for
`KaLM-Embedding/KaLM-Reranker-V1-Nano`. It supports offline Python and CLI
reranking plus an optional FastAPI service.
The adapter does not modify or retrain the checkpoint. It reads the original
decoder logits for the single-token answers `yes` and `no` and returns:
```text
margin = yes_logit - no_logit
score = sigmoid(margin) = P(yes)
```
## Tested environment
- Linux and NVIDIA CUDA
- Python 3.12
- vLLM 0.19.1
- Transformers 5.6.2
- PyTorch 2.10.0
- BF16, one GPU
The package intentionally rejects other vLLM versions and
`tensor_parallel_size != 1`. These combinations have not been validated.
## Installation
Create an environment and download the model repository:
```bash
conda create -n kalm-vllm python=3.12 -y
conda activate kalm-vllm
pip install "vllm==0.19.1" "transformers==5.6.2"
pip install "fastapi>=0.136,<0.137" "uvicorn>=0.46,<0.47"
hf download KaLM-Embedding/KaLM-Reranker-V1-Nano \
--local-dir ./KaLM-Reranker-V1-Nano
pip install ./KaLM-Reranker-V1-Nano/vllm_support --no-deps
export VLLM_PLUGINS=kalm_t5gemma2
```
The model can also be loaded directly by its Hugging Face ID. In that case,
only download the `vllm_support` directory before installing the plugin:
```bash
hf download KaLM-Embedding/KaLM-Reranker-V1-Nano \
--include "vllm_support/**" \
--local-dir ./KaLM-Reranker-V1-Nano
pip install ./KaLM-Reranker-V1-Nano/vllm_support --no-deps
```
## Offline Python API
```python
from kalm_t5gemma2_vllm_plugin import KaLMVLLMReranker
query = "What is the capital of China?"
documents = [
"The capital of China is Beijing.",
"Gravity attracts bodies toward one another.",
]
pairs = [(query, document) for document in documents]
with KaLMVLLMReranker(
"KaLM-Embedding/KaLM-Reranker-V1-Nano",
query_max_length=512,
document_max_length=1024,
encoder_chunk_size=4,
max_model_len=2048,
batch_size=32,
) as reranker:
print(reranker.predict(pairs))
print(reranker.predict(pairs, return_margin=True))
print(reranker.rank(query, documents))
```
Expected BF16 scores are approximately:
```text
[0.99980897, 0.00000493699]
```
`predict()` preserves input order. `rank()` returns score-descending results
with the original document index in `corpus_id`.
## Offline CLI
Run the built-in example:
```bash
kalm-vllm-rerank --return-margin
```
Score JSONL input:
```bash
kalm-vllm-rerank \
--input-jsonl ./KaLM-Reranker-V1-Nano/vllm_support/examples/sample_pairs.jsonl \
--output-jsonl ./scores.jsonl \
--return-margin
```
Each input line must contain `query` and `document`. Optional fields are `id`
and `instruction`. `--top-k N` groups rows by exact query text, sorts each
group by score, and keeps its first `N` documents.
## Online service
Start one model instance:
```bash
kalm-vllm-serve \
--host 0.0.0.0 \
--port 8000 \
--model KaLM-Embedding/KaLM-Reranker-V1-Nano \
--encoder-chunk-size 4
```
The portable startup script exposes the same settings through environment
variables:
```bash
CUDA_VISIBLE_DEVICES=0 PORT=8000 \
./KaLM-Reranker-V1-Nano/vllm_support/examples/start_online_server.sh
```
In a second terminal, check health and send built-in demo requests:
```bash
kalm-vllm-client --health
kalm-vllm-client --endpoint rerank --return-margin
kalm-vllm-client --endpoint score --return-margin
```
For custom input, pass one JSON object with `--json-file`. Use `/rerank` for
one query against multiple documents:
```bash
kalm-vllm-client \
--endpoint rerank \
--json-file ./KaLM-Reranker-V1-Nano/vllm_support/examples/rerank_request.json \
--return-margin \
--top-k 10
```
Use `/score` for a batch of independent query-document pairs:
```bash
kalm-vllm-client \
--endpoint score \
--json-file ./KaLM-Reranker-V1-Nano/vllm_support/examples/score_request.json \
--return-margin
```
When `--json-file` is used, `--return-margin` sets
`"return_margin": true` in the outgoing request, and `--top-k` overrides the
JSON value for `/rerank`.
### `POST /rerank`
```json
{
"query": "What is the capital of China?",
"documents": [
"The capital of China is Beijing.",
"Gravity attracts bodies toward one another."
],
"instruction": "Given a query, retrieve documents that answer the query.",
"top_k": null,
"return_margin": true
}
```
Results are returned in descending score order:
```json
{
"object": "rerank",
"results": [
{"index": 0, "score": 0.9998089, "margin": 8.5625},
{"index": 1, "score": 0.00000493699, "margin": -12.21875}
]
}
```
### `POST /score`
```json
{
"pairs": [
{
"id": "doc-1",
"query": "What is the capital of China?",
"document": "The capital of China is Beijing."
}
],
"instruction": null,
"return_margin": false
}
```
`/score` accepts multiple entries in `pairs`, preserves their input order and
includes an input `id` when provided.
### `GET /health`
Returns service status and the effective model, length, chunking, dtype and
memory settings.
## Configuration
| Setting | Default | Meaning |
| --- | ---: | --- |
| `query_max_length` | `512` | Maximum raw query tokens before prompt insertion |
| `document_max_length` | `1024` | Maximum encoder tokens for `<Document>: ...` |
| `encoder_chunk_size` | `4` | Mean-pooling factor; one of `1,2,4,8,16,32` |
| `max_model_len` | `2048` | vLLM engine context budget |
| `batch_size` | `32` | Pairs passed to each `LLM.classify()` call |
| `dtype` | `bfloat16` | Model compute dtype |
| `gpu_memory_utilization` | `0.85` | vLLM GPU memory fraction |
| `tensor_parallel_size` | `1` | Only supported value in this release |
The query and document limits belong to separate decoder and encoder streams;
they are not a combined cross-encoder token limit. Larger values are
configurable but have not been validated up to the model card's full 128K
limit.
## Limitations
- This is a custom `LLM.classify()` plugin, not vLLM's native HTTP `/score`
implementation.
- The shim uses vLLM scheduling and pooling interfaces but executes the
T5Gemma2 semantic forward through Transformers. It is not a complete
vLLM-native kernel implementation and should not be used to claim native
vLLM throughput.
- Online serving is a single-process FastAPI wrapper around one model instance.
- `encoder_chunk_size=None`, `null`, or an empty string falls back to `4`; it
does not disable pooling in this release.
## Troubleshooting
**The plugin is not discovered**
Reinstall the package and ensure the environment variable includes its entry
point name:
```bash
pip install ./KaLM-Reranker-V1-Nano/vllm_support --no-deps --force-reinstall
export VLLM_PLUGINS=kalm_t5gemma2
```
**The adapter reports an unsupported vLLM version**
Install exactly `vllm==0.19.1`. Internal model and processor APIs are version
sensitive.
**The tokenizer check fails**
Confirm that the tokenizer belongs to this Nano checkpoint. The adapter
requires `yes -> 4443` and `no -> 1904`.
**CUDA runs out of memory**
Reduce `batch_size`, `document_max_length`, `query_max_length`,
`max_model_len`, or `gpu_memory_utilization`.
**CUDA initialization fails with error 803**
The process may be resolving a CUDA compatibility library before the host
driver library. On common Debian/Ubuntu layouts, retry with:
```bash
export LD_LIBRARY_PATH="/lib/x86_64-linux-gnu:/usr/lib/x86_64-linux-gnu${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}"
```
The provided `start_online_server.sh` applies this adjustment automatically
when both directories exist.