Tutorial: from zero to search¶
This is the shortest path from a fresh install to indexing photos, searching them and classifying images. It is a learning path, not a second copy of the reference: each step links to the page that documents it completely.
You need:
- Linux, macOS or Windows, Python 3.12+.
- ~2 GB free for the base model and the environment.
- A folder with a few images (the examples use openly licensed images).
1. Install¶
With uv:
[server] adds FastAPI/uvicorn for the REST surface. The core already includes
torch/transformers; see Installation for CPU-only torch and
source checkouts.
Verify:
2. Get a model¶
The toolkit has its own model cache; it never chooses a model silently.
siglip2 models download google/siglip2-base-patch16-naflex
siglip2 models use google/siglip2-base-patch16-naflex
siglip2 models current
The base checkpoint is about 1.5 GB. See Models for sizes, devices, offline import and the rest of the family.
3. Embed text¶
The same with the library:
from siglip2_toolkit import Embedder, models
resolved = models.resolve_model("google/siglip2-base-patch16-naflex")
embedder = Embedder(
model=resolved.path,
model_id=resolved.identifier,
device="auto",
)
vectors = embedder.embed_texts(["a wedding at sunset", "a dog on the beach"])
print(vectors.shape) # (2, dimensions)
Embeddings are L2-normalised float32 arrays. See the
library guide and API reference.
4. Embed images and compare¶
The toolkit can compare text and images in the same space:
Full runnable example: examples/07_text_image_similarity.py.
import numpy as np
from pathlib import Path
from siglip2_toolkit import Embedder, models
resolved = models.resolve_model()
embedder = Embedder(model=resolved.path, model_id=resolved.identifier)
images = sorted(str(p) for p in Path("examples/images").glob("*.jpg"))
texts = ["a cat", "an astronaut", "a cup of coffee"]
image_vectors = embedder.embed_images(images) # (n_images, dim)
text_vectors = embedder.embed_texts(texts) # (n_texts, dim)
similarity = image_vectors @ text_vectors.T # normalized → cosine
print(similarity.round(3))
5. Export a corpus¶
The export has a format header with the embedding-space manifest and one
record per image (id, vector, optional metadata). Incremental updates:
See Export format and
examples/02_export_and_inspect.py.
6. Search the export¶
from siglip2_toolkit import Embedder, formats, models
from siglip2_toolkit.retrieval import (
apply_similarity_drop, rank_by_similarity, results_matrix,
)
records = formats.load_records("embeddings.jsonl")
matrix = results_matrix(records)
resolved = models.resolve_model()
embedder = Embedder(model=resolved.path, model_id=resolved.identifier)
query = embedder.embed_texts(["a cat on a sofa"])[0]
ranked = rank_by_similarity(query, matrix, top_k=20, metric="cosine")
for row, distance in apply_similarity_drop(ranked, max_drop_percent=15):
metadata = records[row].get("metadata") or {}
print(distance, metadata.get("path") or records[row].get("id"))
rank_by_similarity returns distances (lower is better). See
Retrieval, Recipes and
examples/03_search_export.py.
7. Classify¶
With a threshold, the library can abstain instead of forcing a weak label:
labels = ["cat", "dog", "astronaut", "coffee"]
results = embedder.classify(
["examples/images/cat.jpg"],
labels,
template="a photo of a {}",
top_k=None,
)
best_label, best_probability = results[0][0]
print(best_label, best_probability, best_probability < 0.5) # abstain below 0.5
Full example:
examples/08_classify_threshold.py.
See Classification.
8. Serve the REST API¶
curl -s http://127.0.0.1:8000/v1/embed/text \
-H "Content-Type: application/json" \
-d '{"texts": ["a wedding at sunset"]}'
- Interactive docs:
http://127.0.0.1:8000/docs - Image/classify uploads:
curl -F files=@examples/images/cat.jpg ... - The model loads lazily on the first request.
See REST API and
examples/06_rest_client.py.
9. Offline¶
Only models download uses the network. Copy the toolkit home or import a
local model:
siglip2 --home /data/toolkit models import /media/model \
--name google/siglip2-base-patch16-naflex
siglip2 --home /data/toolkit models use google/siglip2-base-patch16-naflex
See Models → Offline workflow.
10. What next¶
- Library guide — the full Python API.
- CLI and REST — the other two surfaces.
- Recipes — search, fusion, filters and batch.
- Examples — runnable scripts.
- Troubleshooting and API reference.