Instructions to use Shuu12121/NightOwl-CodeEmbedding-v2 with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- sentence-transformers
How to use Shuu12121/NightOwl-CodeEmbedding-v2 with sentence-transformers:
from sentence_transformers import SentenceTransformer model = SentenceTransformer("Shuu12121/NightOwl-CodeEmbedding-v2") sentences = [ "The weather is lovely today.", "It's so sunny outside!", "He drove to the stadium." ] embeddings = model.encode(sentences) similarities = model.similarity(embeddings, embeddings) print(similarities.shape) # [3, 3] - Notebooks
- Google Colab
- Kaggle
NightOwl-CodeEmbedding-v2 🦉
NightOwl-CodeEmbedding-v2 is a compact, 768-dimensional dense embedding model built for
code retrieval, code-edit retrieval, and technical question answering.
It is an updated version of
Shuu12121/NightOwl-CodeEmbedding
(v1). Compared with v1, it:
- supports inputs of up to 4,096 tokens (v1: 1,024), and
- is much stronger on competitive-programming retrieval (AppsRetrieval 0.392 → 0.518) and long multi-turn queries (CodeFeedbackMT 0.767 → 0.886),
while staying within about 0.01 of v1 on every other task (see MTEB Results).
The model uses CLS pooling with cosine similarity and does not require
query: / passage: style prefixes.
What changed from v1
Longer context (1,024 → 4,096 tokens). v1 was trained with a 1,024-token limit, but simply raising the limit to 4,096 — with no further training — improves long-input tasks without hurting any task (MTEB 2.5.1, 11 tasks):
Task v1 @ 1,024 v1 @ 4,096 CodeFeedbackMT 0.7669 0.8870 CodeTransOceanContest 0.7595 0.7919 CodeTransOceanDL 0.3606 0.3747 AppsRetrieval 0.3918 0.3999 Other 7 tasks +0.000 to +0.004 Mean of 11 tasks 0.6987 0.7152 About 66% of CodeFeedbackMT queries exceed 1,024 tokens, and the question to answer is usually in the last turn, which v1 truncated away.
Additional fine-tuning + weight interpolation (WiSE-FT). v1 was fine-tuned further on competitive-programming data plus a replay of its own training data (see Training). The released weights are the average of v1 and the fine-tuned weights (α = 0.5). The fully fine-tuned model reached a higher AppsRetrieval score (0.540) but lost 0.02–0.06 on several other tasks. Interpolating at α = 0.5 keeps most of the gain while removing almost all of the regressions.
Highlights
- Compact (150.8M parameters), 768-d single-vector embeddings: plain dot-product / cosine search that drops straight into any vector-database stack
- 4,096-token context
- 0.7356 mean NDCG@10 on the 12 MTEB(Code, v1) tasks (self-evaluated with MTEB 2.5.1; v1's leaderboard score is 0.7091)
- Covers eight programming languages: the six CodeSearchNet languages plus Rust and TypeScript
- Handles NL-to-code search, code-to-code retrieval, code-edit retrieval, and technical QA
- Decontaminated against the benchmark test sets used for evaluation (see Data Decontamination)
- Drop-in compatible with
sentence-transformers; Apache-2.0 licensed
Supported Languages
- Go, Java, JavaScript, PHP, Python, Ruby (CodeSearchNet languages)
- Rust, TypeScript (additional)
Performance on languages outside this set is untested and may vary.
Usage
from sentence_transformers import SentenceTransformer
model = SentenceTransformer("Shuu12121/NightOwl-CodeEmbedding-v2")
print(model.max_seq_length) # 4096
queries = ["Python function that sorts a list in descending order"]
documents = [
"def sort_desc(values): return sorted(values, reverse=True)",
"def average(values): return sum(values) / len(values)",
]
query_embeddings = model.encode(queries)
document_embeddings = model.encode(documents)
# Cosine similarity (embeddings are normalized internally by similarity())
scores = model.similarity(query_embeddings, document_embeddings)
print(scores)
If memory or latency matters more than long-input quality, you can lower the limit, e.g.
model.max_seq_length = 1024.
Model Details
| Property | Value |
|---|---|
| Base model | Shuu12121/NightOwl-CodeEmbedding (v1) |
| Backbone | Shuu12121/NightOwl |
| Architecture | ModernBERT |
| Parameters | 150,779,136 |
| Embedding dimension | 768 |
| Pooling | CLS pooling |
| Maximum sequence length | 4,096 tokens |
| Similarity | Cosine similarity |
| Query/document prefixes | Not required |
| Weight dtype | FP32 |
| Weight memory | 575 MiB |
| License | Apache-2.0 |
MTEB Results
Evaluation setup:
- MTEB version:
2.5.1 - Metric:
NDCG@10 - Hardware: NVIDIA RTX PRO 6000 Blackwell
- Batch size: 64
max_seq_length: 4,096 (v2), 1,024 (v1, its released setting)
Multi-subset task scores are reported as macro averages. v1 was re-evaluated with the same MTEB version, so the two columns are directly comparable.
| Task | Split | v2 | v1 (1,024) | Diff |
|---|---|---|---|---|
| AppsRetrieval | test | 0.5181 | 0.3918 | +0.1263 |
| COIRCodeSearchNetRetrieval | test | 0.8381 | 0.8426² | – |
| CodeEditSearchRetrieval | train¹ | 0.7480 | 0.7481 | −0.0001 |
| CodeFeedbackMT | test | 0.8856 | 0.7669 | +0.1187 |
| CodeFeedbackST | test | 0.8535 | 0.8526 | +0.0010 |
| CodeSearchNetCCRetrieval | test | 0.9093 | 0.9182 | −0.0089 |
| CodeSearchNetRetrieval | test | 0.8901 | 0.8924 | −0.0022 |
| CodeTransOceanContest | test | 0.8038 | 0.7595 | +0.0443 |
| CodeTransOceanDL | test | 0.3765 | 0.3606 | +0.0159 |
| CosQA | test | 0.4333 | 0.4281 | +0.0051 |
| StackOverflowQA | test | 0.8679 | 0.8661 | +0.0019 |
| SyntheticText2SQL | test | 0.7030 | 0.7015 | +0.0015 |
| Mean, 11 tasks (excl. COIRCodeSearchNet) | 0.7263 | 0.6987 | +0.0276 | |
| Macro average, all 12 tasks | 0.7356 | – | ||
| CoIR macro average, 10 tasks | 0.7189 | – |
¹ CodeEditSearchRetrieval does not provide a standard test split in MTEB, so the
official train split is used for evaluation. These examples were not used for
fine-tuning. See Data Decontamination.
² v1 was not re-evaluated on COIRCodeSearchNetRetrieval (about 1M documents). This value is from v1's model card (MTEB 2.15.1), so it is not strictly comparable.
The CoIR macro average uses the same 10 tasks as v1's card (all 12 except CodeEditSearchRetrieval and CodeSearchNetRetrieval).
Leaderboard
v1 is listed on the MTEB(Code, v1) leaderboard with a task mean of 70.91. v2's results above are self-evaluated and have not yet been submitted to the leaderboard.
As with v1, MTEB(Code, v1) is largely in-domain for this model (8% zero-shot): it was
trained on most of these task families, so its scores reflect in-domain retrieval rather
than zero-shot transfer. Comparisons with models that are 100% zero-shot (e.g.
embeddinggemma-300m, Qwen3-Embedding) are not apples-to-apples.
Comparison with similar-sized models
Leaderboard task means (×100) for compact dense single-vector models. v2's value is self-evaluated (MTEB 2.5.1) and is shown for reference.
| Model | Params | Emb. dim | Max tokens | Zero-shot | MTEB(Code, v1) ↑ |
|---|---|---|---|---|---|
NightOwl-CodeEmbedding-v2 (this model) |
150.8M | 768 | 4,096 | 8% | 73.56†|
NightOwl-CodeEmbedding (v1) |
150.8M | 768 | 1,024 | 8% | 70.91 |
codefuse-ai/F2LLM-v2-160M |
159M | 640 | 40,960 | 58% | 70.38 |
google/embeddinggemma-300m |
308M | 768 | 2,048 | 100% | 68.76 |
codefuse-ai/F2LLM-v2-80M |
80M | 320 | 40,960 | 58% | 67.97 |
ibm-granite/granite-embedding-311m-multilingual-r2 |
312M | 768 | 8,192 | 100% | 63.84 |
| Larger single-vector reference | |||||
codefuse-ai/F2LLM-v2-0.6B |
596M | 1,024 | 40,960 | 58% | 77.41 |
Qwen/Qwen3-Embedding-0.6B |
596M | 1,024 | 32,768 | 100% | 75.42 |
†Self-evaluated with MTEB 2.5.1; not an official leaderboard entry.
Training
v1
v1 was fine-tuned from Shuu12121/NightOwl
with CachedMultipleNegativesRankingLoss (bidirectional query-to-document and
document-to-query) on 2,534,400 samples, each with one positive and 15 hard negatives mined
by Qwen/Qwen3-Embedding-0.6B (1 epoch, learning rate 6e-5, batch size 1024,
max sequence length 1,024). The data covers the CoIR task families of MTEB(Code, v1),
custom code–comment pairs in eight languages, and code-edit data derived from
commitpackft. See the
v1 model card for details.
v2
Starting from v1, the model was fine-tuned on:
- Competitive programming (problem statement → Python solution): APPS train and the CodeContests train split (up to 3 Python solutions per problem).
- Code translation (Python → C++): one (Python, C++) solution pair per CodeContests problem, targeting CodeTransOceanContest.
- Replay of v1's training data to limit forgetting: samples from
coir_hard_negative_datasets_v3_kd(CodeFeedbackMT 4,000, CodeFeedbackST 3,000, StackOverflowQA 3,000, CosQA 1,000, SyntheticText2SQL 2,000, CodeTransOceanContest 561) andcodeedit_hard_negative_datasets_kd(300 per language, 13 languages).
For data 1 and 2, 7 hard negatives per example were mined with Qwen/Qwen3-Embedding-0.6B;
solutions of the same problem (or of near-identical problems) were excluded from the
negatives. Data 3 reuses the hard negatives already in the datasets.
| Property | Value |
|---|---|
| Loss | CachedMultipleNegativesRankingLoss (scale 100, bidirectional) |
| Negatives per anchor | 7 |
| Batching | one data source per batch (proportional sampling), no duplicates |
| Epochs | 1 |
| Learning rate | 2e-5 (cosine, 10% warmup) |
| Batch size | 64 |
| Max sequence length | 1,024 during training (4,096 at inference) |
| Weight interpolation | 0.5 × v1 + 0.5 × fine-tuned |
Interpolation results (MTEB 2.5.1, 11 tasks, max_seq_length 1,024):
| α (share of fine-tuned weights) | 0 (v1) | 0.3 | 0.5 | 0.7 | 1 (fine-tuned) |
|---|---|---|---|---|---|
| AppsRetrieval | 0.3918 | 0.4692 | 0.5066 | 0.5285 | 0.5404 |
| Mean of 11 tasks | 0.6987 | 0.7081 | 0.7103 | 0.7076 | 0.6949 |
Data Decontamination
Overlaps with the evaluation data were removed before training.
v1:
- Custom code–comment pair data vs. the CodeSearchNet test split
commitpackft-derived code-edit data vs. the CodeEditSearchRetrieval evaluation data
v2 (additional data):
- APPS train problems whose statement has cosine similarity ≥ 0.95 to an APPS test problem
- CodeContests problems that are the same Codeforces problem as an APPS test problem, and problems whose statement has cosine similarity ≥ 0.90 to any APPS test or APPS train problem
- Python → C++ pairs whose Python or C++ code has cosine similarity ≥ 0.95 to a CodeTransOceanContest test query or its answer
Similarities were computed with v1. The replay data is a subset of v1's training data, so it adds no new overlap.
For CodeEditSearchRetrieval, note that MTEB labels the evaluation split train. This is
just the official split name for the task; the evaluated examples were not included in this
model's fine-tuning data. The score should therefore be read as in-domain generalization
on held-out benchmark examples.
Base Model: the NightOwl Backbone
The backbone, Shuu12121/NightOwl, is a
ModernBERT-style code encoder pre-trained from scratch, tokenizer included.
- Code-aware tokenizer: a custom 50,368-token BPE tokenizer in which whitespace is tokenized independently of adjacent words, so indentation gets its own tokens and the vocabulary is not wasted on "indent + word" variants.
- Two-phase pre-training with masked-language modeling (
mlm_probability = 0.3): standard random-token MLM over code, natural language, and documentation (Phase 1), then line-level MLM on code only, masking whole source lines (Phase 2).
| Property | Value |
|---|---|
| Architecture | ModernBERT (alternating local/global attention, RoPE) |
| Parameters | ≈150M |
hidden_size / layers / heads |
768 / 19 / 12 |
| Vocabulary | 50,368 (custom code BPE) |
| Max sequence length | 1,024 (Phase 1) → 2,048 (Phase 2) |
See the v1 model card for the pre-training data and the backbone comparison.
Intended Use
- Natural language to code search
- Code-to-code retrieval and similar-function search
- Code-edit retrieval (matching edit intents to code changes)
- Retrieval over programming Q&A, long multi-turn technical conversations, and competitive-programming problems
- Local semantic code search systems
- RAG systems over codebases and developer documentation
Limitations
- Specialized for code-related retrieval; may underperform general-purpose text embedding models on unrelated natural-language tasks.
- Inputs longer than 4,096 tokens are truncated. The model was trained on inputs of at most 1,024 tokens and the backbone was pre-trained on at most 2,048; the 4,096 setting is supported by the evaluation results above, but quality on very long inputs is less tested than on short ones.
- Slightly lower than v1 on CodeSearchNetCCRetrieval (−0.009) and CodeSearchNetRetrieval (−0.002).
- MTEB(Code, v1) is largely in-domain for this model (8% zero-shot). On code domains, query styles, or languages far from the training distribution, expect lower performance than the benchmark numbers suggest.
- The model produces dense single-vector embeddings. For very fine-grained token-level matching, late-interaction models or cross-encoder rerankers may be worth considering.
Recommended Indexing Settings
Encode both queries and documents with normalized embeddings:
embeddings = model.encode(texts, normalize_embeddings=True)
With normalized embeddings, dot product is equivalent to cosine similarity.
For codebase search, indexing function-level or class-level chunks usually works best.
Citation
If you use this model, please cite it together with the base model and Sentence Transformers.
@misc{nightowl_codeembedding_v2,
title = {NightOwl-CodeEmbedding-v2},
author = {Shuu12121},
year = {2026},
publisher = {Hugging Face},
url = {https://huggingface.co/Shuu12121/NightOwl-CodeEmbedding-v2}
}
- Downloads last month
- 28