hotchpotch commited on
Commit
eb5b356
Β·
verified Β·
1 Parent(s): f6f614d

Rewrite model card prose in a natural tone

Browse files
Files changed (1) hide show
  1. README.md +42 -42
README.md CHANGED
@@ -24,35 +24,35 @@ tags:
24
 
25
  # bekko-embedding-v1-a25m
26
 
27
- **bekko-embedding-v1-a25m** is an ultra-small multilingual text-embedding model β€” just **25M active parameters (AP)** and practical even on low-spec CPUs β€” that delivers retrieval quality comparable to models with **3–10x more active parameters**.
 
 
 
 
28
 
29
  For a smaller, faster model, see [bekko-embedding-v1-a8m](https://huggingface.co/hotchpotch/bekko-embedding-v1-a8m) (8M active parameters).
30
 
31
  > [!NOTE]
32
- > 🚧 **WIP** β€” we're writing the technical paper.
33
 
34
  ## Highlights
35
 
36
- - 🎯 Retrieval quality comparable to models with **3–10x more active parameters**.
37
- - 🌍 **Multilingual** β€” 100+ languages supported.
38
- - πŸͺΆ Just **25M active parameters**, so inference stays fast and cheap.
39
- - πŸ“œ Long context up to **8k tokens**.
40
- - πŸͺ† Native **384-dim** embeddings, Matryoshka-truncatable to **256 / 128 / 64**.
41
- - πŸ’» Runs on modest hardware. The default **OpenVINO** / **ONNX** exports compress the static token embedding table to row-wise int8, making the main artifact about **190 MiB** while keeping vector outputs nearly identical to PyTorch.
42
- - ⚑ Fast on GPU, with Flash Attention / SDPA when the runtime supports it.
43
- - πŸ”“ **MIT License**.
44
 
45
  ## Quickstart
46
 
47
- We recommend **Sentence Transformers 5.0+** and **Transformers 5.12+**:
48
 
49
  ```bash
50
  pip install -U "sentence-transformers>=5.0" "transformers>=5.12"
51
  ```
52
 
53
- Use `encode()` for both queries and documents. Normalize embeddings when using cosine similarity or dot-product search on normalized vectors.
54
-
55
- The examples use PyTorch SDPA as the standard attention backend for predictable behavior across CPU, CUDA, and Apple Silicon environments.
56
 
57
  ```python
58
  from sentence_transformers import SentenceTransformer, util
@@ -78,24 +78,24 @@ print(scores)
78
  print("best doc:", docs[int(scores.argmax())])
79
  ```
80
 
81
- Example output, with exact scores varying slightly by backend:
82
 
83
  ```text
84
  tensor([0.2953, 0.2785, 0.3209, 0.4378])
85
  best doc: A Japanese dish made with vinegared rice, often shaped with seafood, vegetables, or egg.
86
  ```
87
 
88
- Want it faster? For CPU- and GPU-specific tuning, ONNX, OpenVINO, browser inference, and Matryoshka truncation, see [Optimized Inference](#optimized-inference) below.
89
 
90
  ## Benchmark results
91
 
92
- The chart summarizes Bekko's main design goal: the models sit at the far left because they use very few active parameters, while achieving HAKARI retrieval scores comparable toβ€”or aboveβ€”many substantially larger models. This makes the quality-per-compute advantage visible at a glance; the best efficiency region is toward the upper-left.
93
 
94
  <p align="center">
95
  <img src="https://storage.googleapis.com/secons-site-images/other/huggingface/bekko/hakari_score_vs_active_params_v3.png" alt="HAKARI-Bench overall vs active parameters" width="600">
96
  </p>
97
 
98
- On the 131-task **MMTEB Multilingual v2** suite, a25m reaches **57.5 Retrieval** and **58.3 Mean(Task)** with only 24.9M active parameters. It slightly exceeds gte-multilingual-base on Retrieval and matches it on Mean while using about 4.5x fewer active parameters, and exceeds multilingual-e5-large and BGE-M3 on Retrieval with about 12x fewer.
99
 
100
  <details>
101
  <summary>MMTEB Multilingual v2 comparison (131 tasks)</summary>
@@ -119,7 +119,7 @@ Scores are Γ—100. Retrieval is task-macro nDCG@10; Mean is the mean across all 1
119
  <details>
120
  <summary>Full MMTEB Retrieval: all 18 tasks and representative models</summary>
121
 
122
- Scores are Γ—100. **a25m is stronger than a8m on 13 of 18 tasks and on the mean**; its main regression is WinoGrande.
123
 
124
  | Task | a8m | a25m | mE5-s | G97 | GTE | BGE-M3 |
125
  | --- | ---: | ---: | ---: | ---: | ---: | ---: |
@@ -143,25 +143,25 @@ Scores are Γ—100. **a25m is stronger than a8m on 13 of 18 tasks and on the mean*
143
  | MIRACL HN | 53.50 | 59.77 | 60.09 | 56.09 | 64.17 | 69.59 |
144
  | **Mean** | **56.23** | **57.45** | **50.91** | **60.32** | **57.16** | **54.59** |
145
 
146
- Abbreviations: **mE5-s** = multilingual-e5-small; **G97** = Granite Embedding 97M Multilingual R2; **GTE** = gte-multilingual-base; **MIRACL HN** = MIRACL Retrieval Hard Negatives.
147
 
148
  </details>
149
 
150
  </details>
151
 
152
- The following **retrieval** scores use multilingual *Nano* benchmarks measured with [HAKARI-Bench](https://huggingface.co/spaces/hakari-bench/leaderboard). Higher is better.
153
 
154
  <details>
155
  <summary>HAKARI-Bench and multilingual Nano benchmark details</summary>
156
 
157
  What each column means:
158
 
159
- - **Overall** β€” HAKARI-Bench Overall, the **micro-average** across all the sets below
160
- - **MNanoBEIR** β€” multilingual NanoBEIR, general-purpose retrieval
161
- - **NanoMMTEB-v2** β€” Nano subset of MMTEB v2 (massive multilingual retrieval)
162
- - **NanoRTEB** β€” multilingual retrieval benchmark
163
- - **NanoLongEmbed** β€” long-document retrieval
164
- - **NanoCoIR** β€” code retrieval
165
 
166
  | Model | Active Params | Overall | MNanoBEIR | NanoMMTEB-v2 | NanoRTEB | NanoLongEmbed | NanoCoIR |
167
  | --- | ---: | ---: | ---: | ---: | ---: | ---: | ---: |
@@ -178,7 +178,7 @@ What each column means:
178
  <details>
179
  <summary>NanoMMTEB-v2: all 18 tasks and representative models</summary>
180
 
181
- Scores are nDCG@10. **a25m scores higher than a8m on 14 of 18 tasks**; its slightly lower simple mean is mainly due to LEMBPasskey.
182
 
183
  | Task | a8m | a25m | mE5-s | G97 | GTE | BGE-M3 |
184
  | --- | ---: | ---: | ---: | ---: | ---: | ---: |
@@ -225,18 +225,18 @@ Model abbreviations match the Full MMTEB Retrieval table above.
225
 
226
  ## Why active parameters?
227
 
228
- For a transformer encoder, most of the inference cost β€” and most of the latency β€” comes from the **non-embedding ("active") parameters**: the attention and feed-forward layers that run on every token. The token embedding table dominates the **total** parameter count, but at inference it is just a lookup, not heavy computation.
229
 
230
- So a model can be larger on disk yet still run fast, as long as its active-parameter count is small. bekko-embedding-v1-a25m has only **25M active parameters**, which is why it stays fast on CPU and GPU even though its total size is ~123M parameters β€” most of which is the multilingual embedding table. The default OpenVINO / ONNX artifacts store that static table as row-wise int8, reducing the main model file from about 470 MiB to **190 MiB**.
231
 
232
  ### Speed vs other models
233
 
234
- **a25m delivers substantially more throughput than much larger models while retaining comparable retrieval quality.** On a Ryzen 9 7950X with OpenVINO it reaches 134 docs/sβ€”about 6.4x multilingual-e5-largeβ€”and on an RTX 5090 with Flash Attention 2 it reaches 4,006 docs/s, faster than every measured comparison model except a8m.
235
 
236
  <details>
237
  <summary>Measured throughput and benchmark setup</summary>
238
 
239
- Document throughput uses Natural Questions text, batch size 64 and max length 512 for CPU/MPS. CUDA uses NQ 100k, fp16, and Flash Attention 2. **All throughput values in the table are docs/s.**
240
 
241
  | Model | AP | x86 | Pi 5 | M4 | RTX |
242
  | --- | ---: | ---: | ---: | ---: | ---: |
@@ -249,7 +249,7 @@ Document throughput uses Natural Questions text, batch size 64 and max length 51
249
  | mE5-large | 303.9M | 21 | 1.5 | 67 | 1,318 |
250
  | BGE-M3 | 311.8M | β€” | β€” | 78 | 1,324 |
251
 
252
- Abbreviations: **mE5** = multilingual-e5; **granite-97m/311m-r2** = Granite Embedding Multilingual R2; **EmbGemma** = EmbeddingGemma. **x86** = Ryzen 9 7950X + OpenVINO; **Pi 5** = Raspberry Pi 5 + OpenVINO; **M4** = Apple M4 Max + MPS; **RTX** = RTX 5090 + CUDA/Flash Attention 2. AP means active parameters.
253
 
254
  Throughput depends on input lengths, batch size, runtime, and hardware. OpenVINO is recommended for CPU; MPS for Apple Silicon; Flash Attention 2 for supported NVIDIA GPUs.
255
 
@@ -257,12 +257,12 @@ Throughput depends on input lengths, batch size, runtime, and hardware. OpenVINO
257
 
258
  ## Optimized Inference
259
 
260
- For CPU inference, use the default OpenVINO artifact. For browser and ONNX Runtime compatibility, use the default ONNX artifact. Both preserve the full tokenizer and vocabulary while compressing only the static token embedding table.
261
 
262
  <details>
263
  <summary>NVIDIA GPU</summary>
264
 
265
- SDPA is the recommended default. On supported NVIDIA GPU environments, Flash Attention 2 can provide additional throughput; our RTX 5090 measurements were about 18% faster for a8m and 24% faster for a25m than SDPA.
266
 
267
  ```python
268
  import torch
@@ -409,7 +409,7 @@ const embedding = await extractor("What are the characteristics of sushi?", {
409
  <details>
410
  <summary>Smaller embeddings with Matryoshka (truncate_dim)</summary>
411
 
412
- These models are trained with Matryoshka representation learning, so you can shrink the **384-dim** embeddings to **256**, **128**, or **64** dimensions by passing `truncate_dim`. Smaller dimensions reduce index size and speed up similarity search, at a small cost in retrieval quality (see [Truncation and Quantization](#truncation-and-quantization)).
413
 
414
  ```python
415
  from sentence_transformers import SentenceTransformer, util
@@ -442,7 +442,7 @@ Beyond the Sentence Transformers backends above, you can also serve or run the m
442
  <details>
443
  <summary>Text Embeddings Inference (production API)</summary>
444
 
445
- Text Embeddings Inference (TEI) is a Rust-based production inference server from Hugging Face, with Docker images, dynamic batching, and production features such as Prometheus metrics and tracing.
446
 
447
  Before deploying, confirm your TEI version supports this model's encoder architecture, and pick the image tag that matches your target β€” a CPU image, or a GPU image for your specific architecture. See the [TEI image list](https://github.com/huggingface/text-embeddings-inference#docker-images) for current tags.
448
 
@@ -515,7 +515,7 @@ print(scores.squeeze(-1))
515
 
516
  ## Truncation and Quantization
517
 
518
- The results below are for `bekko-embedding-v1-a25m`. Use 384 dimensions for maximum quality. Use 256 dimensions when index size matters and quality loss must stay small. Quantized search-only variants lose more quality on these small models; rescoring recovers most of that loss.
519
 
520
  <details>
521
  <summary>Truncation and output-vector quantization results</summary>
@@ -551,18 +551,18 @@ The results below are for `bekko-embedding-v1-a25m`. Use 384 dimensions for maxi
551
 
552
  *bekko* (/ˈbek.koː/) is a coined name that joins two pieces of Japanese tradition:
553
 
554
- - **akabeko** (血べこ) β€” the red ox that has been cherished in Japan for centuries as a guardian charm, believed to ward off illness and misfortune.
555
- - **bekko-iro** (ιΌˆη”²θ‰²) β€” a beautiful traditional Japanese color: a warm, translucent, amber-like hue.
556
 
557
  The name pairs the protective spirit of the red ox with the quiet beauty of this classic amber tone.
558
 
559
  ## Citation
560
 
561
- A BibTeX citation will be added when the technical paper is released. It is currently in preparation.
562
 
563
  ## Training data
564
 
565
- The datasets we built to train bekko-embedding:
566
 
567
  - [hotchpotch/bekko-embedding-v1-unsupervised](https://huggingface.co/datasets/hotchpotch/bekko-embedding-v1-unsupervised) β€” unsupervised pretraining data.
568
  - [hotchpotch/bekko-embedding-hard-negatives](https://huggingface.co/datasets/hotchpotch/bekko-embedding-hard-negatives) β€” hard negatives for contrastive fine-tuning.
 
24
 
25
  # bekko-embedding-v1-a25m
26
 
27
+ bekko-embedding-v1-a25m is a small multilingual text embedding model. It has just 25M active parameters β€” light enough to run comfortably on modest CPUs β€” yet its retrieval quality is comparable to models with 3–10x more active parameters.
28
+
29
+ <p align="center">
30
+ <img src="https://storage.googleapis.com/secons-site-images/other/huggingface/bekko/hakari_score_vs_active_params_v3.png" alt="HAKARI-Bench overall vs active parameters" width="600">
31
+ </p>
32
 
33
  For a smaller, faster model, see [bekko-embedding-v1-a8m](https://huggingface.co/hotchpotch/bekko-embedding-v1-a8m) (8M active parameters).
34
 
35
  > [!NOTE]
36
+ > 🚧 WIP β€” we're writing the technical paper.
37
 
38
  ## Highlights
39
 
40
+ - Retrieval quality on par with models 3–10x its active-parameter count
41
+ - 100+ languages, context up to 8k tokens
42
+ - 384-dim embeddings that truncate cleanly to 256 / 128 / 64 (Matryoshka)
43
+ - Runs well on CPU β€” even a Raspberry Pi 5 β€” with ONNX and OpenVINO artifacts included
44
+ - Fast on GPU too, with SDPA or Flash Attention 2
45
+ - MIT license
 
 
46
 
47
  ## Quickstart
48
 
49
+ We recommend Sentence Transformers 5.0+ and Transformers 5.12+:
50
 
51
  ```bash
52
  pip install -U "sentence-transformers>=5.0" "transformers>=5.12"
53
  ```
54
 
55
+ Queries and documents go through the same `encode()` call β€” no prefixes or task instructions needed. Pass `normalize_embeddings=True` when you plan to search with cosine similarity or dot product. The examples pin the attention backend to SDPA because it behaves the same across CPU, CUDA, and Apple Silicon.
 
 
56
 
57
  ```python
58
  from sentence_transformers import SentenceTransformer, util
 
78
  print("best doc:", docs[int(scores.argmax())])
79
  ```
80
 
81
+ Output (exact scores vary slightly by backend):
82
 
83
  ```text
84
  tensor([0.2953, 0.2785, 0.3209, 0.4378])
85
  best doc: A Japanese dish made with vinegared rice, often shaped with seafood, vegetables, or egg.
86
  ```
87
 
88
+ That's everything you need for basic use. For more speed β€” OpenVINO on CPU, Flash Attention on GPU, browser inference, smaller embeddings β€” see [Optimized Inference](#optimized-inference) below.
89
 
90
  ## Benchmark results
91
 
92
+ In the chart above, up and to the left is better: more retrieval quality from fewer active parameters. Both bekko models sit in that upper-left region, scoring at or above many models several times their size β€” which is the whole point of the project.
93
 
94
  <p align="center">
95
  <img src="https://storage.googleapis.com/secons-site-images/other/huggingface/bekko/hakari_score_vs_active_params_v3.png" alt="HAKARI-Bench overall vs active parameters" width="600">
96
  </p>
97
 
98
+ On the 131-task MMTEB Multilingual v2 suite, a25m scores 57.5 Retrieval and 58.3 Mean(Task) with 24.9M active parameters. That edges out gte-multilingual-base on Retrieval and ties it on Mean with ~4.5x fewer active parameters, and beats multilingual-e5-large and BGE-M3 on Retrieval with ~12x fewer.
99
 
100
  <details>
101
  <summary>MMTEB Multilingual v2 comparison (131 tasks)</summary>
 
119
  <details>
120
  <summary>Full MMTEB Retrieval: all 18 tasks and representative models</summary>
121
 
122
+ Scores are Γ—100. a25m is stronger than a8m on 13 of 18 tasks and on the mean; its main regression is WinoGrande.
123
 
124
  | Task | a8m | a25m | mE5-s | G97 | GTE | BGE-M3 |
125
  | --- | ---: | ---: | ---: | ---: | ---: | ---: |
 
143
  | MIRACL HN | 53.50 | 59.77 | 60.09 | 56.09 | 64.17 | 69.59 |
144
  | **Mean** | **56.23** | **57.45** | **50.91** | **60.32** | **57.16** | **54.59** |
145
 
146
+ Abbreviations: mE5-s = multilingual-e5-small; G97 = Granite Embedding 97M Multilingual R2; GTE = gte-multilingual-base; MIRACL HN = MIRACL Retrieval Hard Negatives.
147
 
148
  </details>
149
 
150
  </details>
151
 
152
+ The following retrieval scores use multilingual *Nano* benchmarks measured with [HAKARI-Bench](https://huggingface.co/spaces/hakari-bench/leaderboard). Higher is better.
153
 
154
  <details>
155
  <summary>HAKARI-Bench and multilingual Nano benchmark details</summary>
156
 
157
  What each column means:
158
 
159
+ - Overall β€” HAKARI-Bench Overall, the micro-average across all the sets below
160
+ - MNanoBEIR β€” multilingual NanoBEIR, general-purpose retrieval
161
+ - NanoMMTEB-v2 β€” Nano subset of MMTEB v2 (massive multilingual retrieval)
162
+ - NanoRTEB β€” multilingual retrieval benchmark
163
+ - NanoLongEmbed β€” long-document retrieval
164
+ - NanoCoIR β€” code retrieval
165
 
166
  | Model | Active Params | Overall | MNanoBEIR | NanoMMTEB-v2 | NanoRTEB | NanoLongEmbed | NanoCoIR |
167
  | --- | ---: | ---: | ---: | ---: | ---: | ---: | ---: |
 
178
  <details>
179
  <summary>NanoMMTEB-v2: all 18 tasks and representative models</summary>
180
 
181
+ Scores are nDCG@10. a25m scores higher than a8m on 14 of 18 tasks; its slightly lower simple mean is mainly due to LEMBPasskey.
182
 
183
  | Task | a8m | a25m | mE5-s | G97 | GTE | BGE-M3 |
184
  | --- | ---: | ---: | ---: | ---: | ---: | ---: |
 
225
 
226
  ## Why active parameters?
227
 
228
+ The "a25m" in the name counts active parameters: the attention and feed-forward weights that run on every token, which is where nearly all of a transformer encoder's inference cost lives. The token embedding table dominates the total parameter count, but at inference it's only a lookup.
229
 
230
+ That's why a model can be large on disk and still fast. bekko-embedding-v1-a25m totals ~123M parameters, but the bulk of that is the multilingual embedding table β€” only 25M parameters do real work per token, so latency behaves like a 25M model. The default OpenVINO / ONNX artifacts also store that static table as row-wise int8, cutting the main model file from about 470 MiB to 190 MiB.
231
 
232
  ### Speed vs other models
233
 
234
+ On a Ryzen 9 7950X with OpenVINO, a25m encodes 134 docs/s β€” about 6.4x multilingual-e5-large. On an RTX 5090 with Flash Attention 2 it reaches 4,006 docs/s, faster than every model we measured except a8m.
235
 
236
  <details>
237
  <summary>Measured throughput and benchmark setup</summary>
238
 
239
+ Document throughput uses Natural Questions text, batch size 64 and max length 512 for CPU/MPS. CUDA uses NQ 100k, fp16, and Flash Attention 2. All throughput values in the table are docs/s.
240
 
241
  | Model | AP | x86 | Pi 5 | M4 | RTX |
242
  | --- | ---: | ---: | ---: | ---: | ---: |
 
249
  | mE5-large | 303.9M | 21 | 1.5 | 67 | 1,318 |
250
  | BGE-M3 | 311.8M | β€” | β€” | 78 | 1,324 |
251
 
252
+ Abbreviations: mE5 = multilingual-e5; granite-97m/311m-r2 = Granite Embedding Multilingual R2; EmbGemma = EmbeddingGemma. x86 = Ryzen 9 7950X + OpenVINO; Pi 5 = Raspberry Pi 5 + OpenVINO; M4 = Apple M4 Max + MPS; RTX = RTX 5090 + CUDA/Flash Attention 2. AP means active parameters.
253
 
254
  Throughput depends on input lengths, batch size, runtime, and hardware. OpenVINO is recommended for CPU; MPS for Apple Silicon; Flash Attention 2 for supported NVIDIA GPUs.
255
 
 
257
 
258
  ## Optimized Inference
259
 
260
+ The short version: on CPU, use the default OpenVINO artifact; in the browser or with ONNX Runtime, use the default ONNX artifact. Both keep the tokenizer and vocabulary untouched and compress only the static token embedding table.
261
 
262
  <details>
263
  <summary>NVIDIA GPU</summary>
264
 
265
+ SDPA works everywhere and is the safe default. If your GPU supports Flash Attention 2, it's worth enabling: on our RTX 5090 it was about 24% faster than SDPA for a25m (18% for a8m).
266
 
267
  ```python
268
  import torch
 
409
  <details>
410
  <summary>Smaller embeddings with Matryoshka (truncate_dim)</summary>
411
 
412
+ These models are trained with Matryoshka representation learning, so you can shrink the 384-dim embeddings to 256, 128, or 64 dimensions by passing `truncate_dim`. Smaller dimensions reduce index size and speed up similarity search, at a small cost in retrieval quality (see [Truncation and Quantization](#truncation-and-quantization)).
413
 
414
  ```python
415
  from sentence_transformers import SentenceTransformer, util
 
442
  <details>
443
  <summary>Text Embeddings Inference (production API)</summary>
444
 
445
+ Text Embeddings Inference (TEI) is Hugging Face's Rust-based serving stack, with official Docker images, dynamic batching, and Prometheus metrics built in.
446
 
447
  Before deploying, confirm your TEI version supports this model's encoder architecture, and pick the image tag that matches your target β€” a CPU image, or a GPU image for your specific architecture. See the [TEI image list](https://github.com/huggingface/text-embeddings-inference#docker-images) for current tags.
448
 
 
515
 
516
  ## Truncation and Quantization
517
 
518
+ How much quality do you trade for a smaller index? For `bekko-embedding-v1-a25m`: very little at 256 dimensions (-1.4%), progressively more below that. If you quantize the output vectors to int8 or binary, add a rescoring step β€” it recovers nearly all of the loss.
519
 
520
  <details>
521
  <summary>Truncation and output-vector quantization results</summary>
 
551
 
552
  *bekko* (/ˈbek.koː/) is a coined name that joins two pieces of Japanese tradition:
553
 
554
+ - *akabeko* (血べこ) β€” the red ox that has been cherished in Japan for centuries as a guardian charm, believed to ward off illness and misfortune.
555
+ - *bekko-iro* (ιΌˆη”²θ‰²) β€” a beautiful traditional Japanese color: a warm, translucent, amber-like hue.
556
 
557
  The name pairs the protective spirit of the red ox with the quiet beauty of this classic amber tone.
558
 
559
  ## Citation
560
 
561
+ The technical paper is in preparation. A BibTeX entry will be added here once it's published.
562
 
563
  ## Training data
564
 
565
+ Both datasets built for training bekko-embedding are public:
566
 
567
  - [hotchpotch/bekko-embedding-v1-unsupervised](https://huggingface.co/datasets/hotchpotch/bekko-embedding-v1-unsupervised) β€” unsupervised pretraining data.
568
  - [hotchpotch/bekko-embedding-hard-negatives](https://huggingface.co/datasets/hotchpotch/bekko-embedding-hard-negatives) β€” hard negatives for contrastive fine-tuning.