USER2-1C-code / README.md
pruha-wakup's picture
апдейт ридми
b587ab2 verified
---
license: apache-2.0
language:
- ru
library_name: sentence-transformers
pipeline_tag: sentence-similarity
base_model: deepvk/USER2-base
tags:
- sentence-transformers
- feature-extraction
- sentence-similarity
- code-retrieval
- 1c
- bsl
- matryoshka
- ru
model-index:
- name: USER2-1C-code
results:
- task:
type: retrieval
name: Code Retrieval
dataset:
type: PruhaNLP/1C-Ebench
name: 1C-Ebench (forum)
config: forum
split: test
metrics:
- type: ndcg_at_10
value: 0.4617
- type: recall_at_10
value: 0.6008
- type: mrr_at_10
value: 0.4178
- task:
type: retrieval
name: Code Retrieval
dataset:
type: PruhaNLP/1C-Ebench
name: 1C-Ebench (fastcode)
config: fastcode
split: test
metrics:
- type: ndcg_at_10
value: 0.7366
- type: recall_at_10
value: 0.9208
- type: mrr_at_10
value: 0.6774
---
# USER2-1C-code
**Первая открытая эмбеддинг-модель, заточенная под код и язык 1С (1С:Предприятие / BSL).**
`USER2-1C-code` — это би-энкодер для семантического поиска по коду 1С: на вход подаётся вопрос на естественном языке, на выходе — релевантные фрагменты кода/решений. Модель — fine-tune [`deepvk/USER2-base`](https://huggingface.co/deepvk/USER2-base) (ModernBERT, контекст до 8192 токенов) на парах «вопрос → код 1С».
- **Тип:** bi-encoder (sentence-transformers), mean pooling, cosine similarity
- **База:** `deepvk/USER2-base` (ModernBERT, 768d, до 8192 токенов)
- **Языки:** русский + код 1С (BSL)
- **Matryoshka (MRL):** полноценные эмбеддинги на `768 / 512 / 384 / 256 / 128 / 64 / 32`
- **Префиксы:** `search_query` для запросов, `search_document` для кода
## Результаты на 1C-Ebench
Бенчмарк [`PruhaNLP/1C-Ebench`](https://huggingface.co/datasets/PruhaNLP/1C-Ebench): retrieval по двум источникам — `forum` (живые вопросы с тематических площадок) и `fastcode` (готовые сниппеты/шаблоны). Метрика — nDCG@10.
![Leaderboard](assets/leaderboard_gradient.png)
| Модель | avg nDCG@10 |
|---|---|
| **USER2-1C-code (наша)** | **0.599** |
| google/embeddinggemma-300m | 0.540 |
| deepvk/USER2-base | 0.493 |
| deepvk/USER-bge-m3 | 0.491 |
| ibm-granite/granite-embedding-311m-multilingual-r2 | 0.485 |
| microsoft/harrier-oss-v1-270m | 0.480 |
| intfloat/multilingual-e5-base | 0.429 |
| ai-forever/sbert_large_nlu_ru | 0.086 |
Прирост относительно базовой `deepvk/USER2-base` — **+0.106 avg nDCG@10** (0.493 → 0.599).
### Детально по сплитам
![Метрики по сплитам](assets/ours_by_split.png)
| Сплит | nDCG@10 | Recall@10 | MRR@10 |
|---|---|---|---|
| forum | 0.4617 | 0.6008 | 0.4178 |
| fastcode | 0.7366 | 0.9208 | 0.6774 |
## Matryoshka (MRL): обрезаемые эмбеддинги
Модель обучена с `MatryoshkaLoss`, поэтому эмбеддинг можно усекать до меньшей размерности (взять первые `d` компонент и перенормировать) почти без потери качества. Это позволяет экономить память индекса и ускорять поиск.
![MRL degradation](assets/mrl_degradation.png)
| dim | avg nDCG@10 | от полной 768d |
|---|---|---|
| 768 | 0.599 | 100.0% |
| 512 | 0.600 | 100.1% |
| 384 | 0.600 | 100.2% |
| 256 | 0.598 | 99.9% |
| 128 | 0.584 | 97.5% |
| 64 | 0.560 | 93.5% |
| 32 | 0.503 | 83.9% |
До **256d качество практически не падает** — можно смело уменьшать индекс втрое.
## Использование
```python
from sentence_transformers import SentenceTransformer
model = SentenceTransformer("PruhaNLP/USER2-1C-code")
query = "Как программно провести документ в 1С?"
docs = [
"Документы.РеализацияТоваровУслуг.СоздатьДокумент();",
"Процедура ПровестиДокумент(Ссылка) Экспорт ... КонецПроцедуры",
]
q_emb = model.encode(query, prompt_name="search_query", normalize_embeddings=True)
d_emb = model.encode(docs, prompt_name="search_document", normalize_embeddings=True)
scores = model.similarity(q_emb, d_emb)
print(scores)
```
Для MRL укажите целевую размерность:
```python
model = SentenceTransformer("PruhaNLP/USER2-1C-code", truncate_dim=256)
```
## Кастомный токенайзер для приватности
При подготовке данных персональные данные в коде/текстах не вырезаются грубо, а заменяются на отдельные **служебные токены**, которые модель видит как единый элемент (а не как ломаную последовательность сабтокенов):
| Сущность | Токен | Токенов после кодирования |
|---|---|---|
| Пути | `[PATH]` | 1 |
| Имена | `[PERSON]` | 1 |
| E-mail | `\|\|\|EMAIL_ADDRESS\|\|\|` | 1 |
| Телефон | `\|\|\|PHONE_NUMBER\|\|\|` | 1 |
| IP | `\|\|\|IP_ADDRESS\|\|\|` | 1 |
Свободные слоты словаря (`[unused0]`/`[unused1]`) переиспользованы под `[PATH]`/`[PERSON]`, а их эмбеддинги инициализированы средним по сабтокенам исходных строк. В результате анонимизация не ломает токенизацию и не плодит шум в последовательности — это аккуратно закрывает персональные данные и держит распределение входа стабильным.
## Детали обучения
- **База:** `deepvk/USER2-base` (ModernBERT)
- **Лосс:** `CachedMultipleNegativesRankingLoss` (scale 20, hard-negatives) внутри `MatryoshkaLoss` по размерностям `[768, 512, 384, 256, 128, 64, 32]`
- **Хард-негативы:** майнинг по FAISS
- **LR-расписание:** трапеция (warmup → stable → cosine decay), peak LR 2e-5
- **Контекст:** до 8192 токенов, fp16
- **Префиксы:** `search_query` / `search_document`
## Код валидации
Eval метод опубликован отдельно:
[`https://github.com/PruhaNLP/1C-RB`](https://github.com/PruhaNLP/1C-RB).
## Правовая информация
«1С», «1С:Предприятие» и связанные обозначения — товарные знаки ООО «1С». Проект является независимым, **не аффилирован с фирмой «1С»** и не одобрен ею. Названия используются исключительно для указания предметной области (номинативное использование). Модель и датасеты предоставляются «как есть», без гарантий. Если вы правообладатель и считаете, что какой-либо материал нарушает ваши права — напишите на контакт ниже, и он будет удалён.
## Контакт для связи
`konstphx@gmail.com`
## Цитирование
```bibtex
@misc{user2_1c_code,
title = {USER2-1C-code: эмбеддинг-модель для поиска по коду 1С},
author = {PruhaNLP},
year = {2026},
url = {https://huggingface.co/PruhaNLP/USER2-1C-code}
}
```