仅用CPU在VPS上运行EmbeddingGemma 2
Ollama 0.40 在 Linux CPU 上仍无法运行 EmbeddingGemma 2。本文提供 sentence-transformers 配置、任务前缀及写入 pgvector 的 256 维向量方案。
如何在仅使用 CPU 的 VPS 上运行 EmbeddingGemma 2
要在今天的仅使用 CPU 的 VPS 上运行 EmbeddingGemma 2,可以使用 sentence-transformers 提供服务,并在 localhost 上通过一个小型 HTTP 端点对外提供接口。Ollama 是显而易见的工具,但截至 7 October 2026,其模型库中的该模型构建版本需要使用 Ollama 的 MLX 引擎,而在 Linux 上,该引擎需要配备 CUDA 13 的 NVIDIA GPU。本指南会展示如何在您自己的服务器上执行检查并确认这一点。随后,本指南会构建一条可行路径:在 127.0.0.1 上提供文本嵌入 API,将 256 维向量写入 pgvector 表,以便进行搜索。
这里的每条命令都需要您在自己的 VPS 上执行。下载模型需要能够访问 Hugging Face hub,Ollama 检查需要能够访问 Ollama registry。没有出站互联网访问权限的服务器无法完成本指南。
使用的版本:Ollama 0.40.0(发布于 2026-09-25)和用于 Ollama 检查的 embeddinggemma-2:270m 标签,以及用于可行路径的 Hugging Face 上的 google/embeddinggemma-2 checkpoint。操作系统为 Ubuntu 24.04。
EmbeddingGemma 2 是什么,以及本指南使用的部分
EmbeddingGemma 2 是 Google DeepMind 发布的开源嵌入模型,采用 Apache 2.0 许可证。嵌入模型会将一段文本转换为固定长度的数字列表,称为向量。含义相近的文本,其向量方向也相近。这是 RAG(检索增强生成)流程中的检索部分。
Hugging Face 模型卡列出的参数总数为 740M。其中,文本主干网络占 270M。视觉编码器增加 170M,音频编码器增加 300M;加载时可以省略这两个编码器。输出是包含 768 个数字的向量。该模型采用 MRL(Matryoshka 表示学习)训练,因此向量开头的 512、256 或 128 个数字仍可单独用作嵌入。上下文窗口为 8,192 个 token,所有输入类型共用这一额度。
本指南仅介绍文本嵌入。图像、视频和音频嵌入通过 sentence-transformers 或 Transformers 处理,具体方式见 Hugging Face 模型卡;媒体文件会与文本一同传入。这些输入不会通过 Ollama 处理。Ollama 文档中的 /api/embed 端点只接受字符串或字符串列表,不接受其他类型。因此,即使 Ollama 在某台运行该模型的机器上,也无法为图片生成嵌入。
为什么 Ollama 目前还无法在 Linux CPU 上提供 EmbeddingGemma 2
截至 2026-10-07 查阅 Ollama library 页面时,该模型列出了 4 种大小。以下输入类型复制自该页面:
embeddinggemma-2:270m:378MB,输入类型列为 Textembeddinggemma-2:440m:714MB,输入类型列为 Text、Imageembeddinggemma-2:570m:990MB,输入类型列为 Textembeddinggemma-2:740m:1.3GB,输入类型列为 Text、Image,并且还标记为latest
该页面将 570m 列为仅支持 Text,但 Hugging Face 模型卡片将 570M 构建列为支持文本和音频。这里的差异没有影响,因为 /api/embed 只接受文本。
这些大小与 tags 页面上的 4-bit 构建一致。例如,270m-nvfp4-text 也是 378MB,其他 3 种大小也分别与其 nvfp4 构建一致。Ollama 0.40.0 的发行说明在 MLX 引擎部分加入了该模型:“MLX now has support for an embedding model: embeddinggemma-2”。MLX 是 Apple 的机器学习框架,最初针对 Apple silicon 构建。MLX 本身也提供仅使用 CPU 的 Linux 构建(pip install mlx[cpu]),但 Ollama 并不使用该构建。Ollama 开发文档仅在 Apple silicon Mac 上默认启用 MLX 引擎。在 Linux 上,MLX 是可选功能;文档将 CUDA 13 和 cuDNN 9 列为要求,也没有说明仅使用 CPU 的 MLX 后端。仅使用 CPU 的 VPS 不具备 CUDA 或 cuDNN。
2026-10-06 提交的一份错误报告(ollama/ollama issue 18825,截至 2026-10-12 仍未关闭)显示,一台运行 Ollama 0.40.0 的 Linux 主机在拉取 740m 标签时失败,并显示以下消息:
this model requires MLX support, but the MLX runtime is not available请在自己的主机上验证,不要直接依赖报告。固定 Ollama 版本,使你的结果与该报告具有相同条件:
curl -fsSL https://ollama.com/install.sh | OLLAMA_VERSION=0.40.0 sh
ollama --version
ollama pull embeddinggemma-2:270mollama --version 应输出 0.40.0。如果拉取操作以之前的 MLX 消息结束,请在本指南剩余部分按照 sentence-transformers 路径操作。如果后续 Ollama 版本能够拉取该模型,并且 ollama show embeddinggemma-2:270m 输出其详细信息,请转到最后一节,了解如何切换到 Ollama。
此后的稳定版本截至 2026 年 10 月 11 日的 0.40.3,都没有在发行说明中提及该模型。有一条线索值得关注。Ollama 0.40.4-rc0 是 2026 年 10 月 12 日发布的预发行版本,它更新了内置的 llama.cpp,以“支持 decision models 和 EmbeddingGemma 2”。llama.cpp 是 Ollama 在 MLX 之外使用的引擎,并且可以在 CPU 上运行。发行说明没有说明 library 标签是否发生变化,因此在稳定版本能够在你的主机上拉取该模型之前,只能将其视为线索。
tags 页面还列出了 bf16 构建,例如大小为 574MB 的 270m-bf16-text。Ollama 文档没有说明其 Linux 构建是否能在 CPU 上运行这些构建。ollama pull embeddinggemma-2:270m-bf16-text 可以针对你的主机给出答案。
library 页面还有两点值得注意。标签列表为每个标签都显示“256K context window”,但同一页面的 readme 和 Hugging Face 模型卡片都写明为 8,192 tokens。请按 8,192 规划。该页面还显示,270m 标签没有 template 层,只有 config、tokenizer 和权重文件。Ollama 不会添加下文所述的任务前缀,因此无论实际响应请求的是哪个服务器,都必须由调用方添加这些前缀。
安装仅使用 CPU 的 Python 软件栈
PyPI 中默认的 PyTorch 软件包会拉取 CPU VPS 用不到的 CUDA 库,这些库会占用数 GB 的磁盘空间。先从 PyTorch 自己的软件包索引安装 CPU 版本,再安装其余依赖。
sudo apt update
sudo apt install -y python3-venv
sudo mkdir -p /opt/eg2
sudo python3 -m venv /opt/eg2/venv
sudo /opt/eg2/venv/bin/pip install torch --index-url https://download.pytorch.org/whl/cpu
sudo /opt/eg2/venv/bin/pip install -U sentence-transformers transformers fastapi uvicorn "psycopg[binary]" pgvector
/opt/eg2/venv/bin/python -c 'import torch, sentence_transformers, transformers; print(torch.__version__, sentence_transformers.__version__, transformers.__version__)'最后一行应打印 3 个版本号,其中 torch 版本应以 +cpu 结尾。将这些版本号与日期一并记录,因为它们是 Python 端的固定版本。EmbeddingGemma 2 是新模型。较旧的 transformers 版本不了解其架构,因此加载会失败,并显示 Transformers “不识别此架构”的消息。重新运行 pip install -U 行即可修复。
编写嵌入服务
下面的服务只加载一次文本骨干模型,并响应 POST /api/embed。请求和响应使用与 Ollama 文档化的 /api/embed 相同的字段名:model、input(字符串或字符串列表)、dimensions,以及响应中的 embeddings。这是有意设计的。当 Ollama 可以在您的计算机上运行此模型时,客户端代码只需修改一个 URL 和一个模型名称。
sudo tee /opt/eg2/eg2_server.py > /dev/null <<'EOF'
import torch
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from sentence_transformers import SentenceTransformer
MODEL_ID = "google/embeddinggemma-2"
DIMS = (128, 256, 512, 768)
# Text only: the vision and audio encoders are not loaded into RAM.
# float32 on CPU, as the model card advises. Without it, Transformers 5 loads bfloat16.
st = SentenceTransformer(
MODEL_ID,
device="cpu",
config_kwargs={"vision_config": None, "audio_config": None},
model_kwargs={"dtype": torch.float32},
)
# The caller adds the task prefix, exactly as with Ollama.
# Make sure the library never adds one of its own on top.
st.default_prompt_name = None
print("loaded", MODEL_ID, flush=True)
app = FastAPI()
class EmbedRequest(BaseModel):
model: str = "embeddinggemma-2"
input: str | list[str]
dimensions: int = 768
@app.post("/api/embed")
def embed(req: EmbedRequest):
if req.dimensions not in DIMS:
raise HTTPException(status_code=400, detail=f"dimensions must be one of {DIMS}")
texts = [req.input] if isinstance(req.input, str) else req.input
vectors = st.encode(
texts,
batch_size=16,
truncate_dim=req.dimensions,
normalize_embeddings=True,
)
return {"model": req.model, "embeddings": vectors.tolist()}
EOFconfig_kwargs={"vision_config": None, "audio_config": None} 是 Hugging Face 模型卡针对 sentence-transformers 提供的纯文本设置。它会加载 270M 参数的文本骨干模型,并使另外两个编码器不占用内存。
model_kwargs={"dtype": torch.float32} 设置权重精度,您需要请求 float32。自 Transformers 5.0.0(2026 年 1 月)起,from_pretrained 默认为 dtype="auto",表示使用检查点配置中保存的 dtype;此检查点的 config.json 表示 bfloat16。sentence-transformers 会将 model_kwargs 原样传递给 Transformers,并且不会自行设置 dtype,因此省略这一行会得到 bfloat16。模型卡不建议使用 float16,因为模型的激活值会超出 float16 可表示的范围。在不支持原生 bfloat16 的硬件上,模型卡建议使用 float32,“包括大多数 CPU”。模型卡自己的示例传入较旧的参数名 torch_dtype;Transformers 5 仍接受该参数,但已将其标记为弃用,建议改用 dtype。
truncate_dim 将向量截断为请求的长度,随后 normalize_embeddings=True 将其重新缩放为长度 1。模型卡说明第二步是必需的。单位长度向量经过切片后不再保持单位长度,因此直接对切片计算的余弦分数是不正确的。下一节中的检查会证明该服务处理正确。
在 systemd 下运行服务
sudo tee /etc/systemd/system/eg2.service > /dev/null <<'EOF'
[Unit]
Description=EmbeddingGemma 2 text embedding API
After=network-online.target
Wants=network-online.target
[Service]
DynamicUser=yes
CacheDirectory=eg2
Environment=HF_HOME=/var/cache/eg2
Environment=HOME=/var/cache/eg2
WorkingDirectory=/opt/eg2
ExecStart=/opt/eg2/venv/bin/uvicorn eg2_server:app --host 127.0.0.1 --port 11435
Restart=on-failure
[Install]
WantedBy=multi-user.target
EOF
sudo systemctl daemon-reload
sudo systemctl enable --now eg2
journalctl -u eg2 -fDynamicUser=yes 会使用没有登录 shell 的临时用户运行服务,并且该用户无法写入自身目录以外的位置。CacheDirectory=eg2 会为该用户提供 /var/cache/eg2,HF_HOME 则将 Hugging Face 下载目录指向该位置。因此,模型只需下载一次,重启后仍会保留。
首次启动时会下载检查点,因此需要一段时间。等待日志中出现以下两行:loaded google/embeddinggemma-2,然后是 Uvicorn running on http://127.0.0.1:11435。只有模型加载完成后,Uvicorn 才会打开端口。在此之前,curl 会因 curl: (7) Failed to connect to 127.0.0.1 port 11435 而失败,这是正常现象。
如果日志显示 A process of this unit has been killed by the OOM killer,则表示 VPS 在加载模型时耗尽了 RAM。下面的 RAM 章节说明如何确定所需配置。
检查输出:256 个数字,长度为 1
curl -s http://127.0.0.1:11435/api/embed \
-H 'Content-Type: application/json' \
-d '{"model": "embeddinggemma-2", "input": ["task: search result | query: how do I add swap?"], "dimensions": 256}' \
| python3 -c 'import json,sys; v=json.load(sys.stdin)["embeddings"][0]; print(len(v), round(sum(x*x for x in v) ** 0.5, 4))'正常服务会输出 256 1.0。第一个数字是您请求的向量长度。第二个数字是该向量在空间中的长度,1.0 表示截断后的向量又经过了归一化。使用 "dimensions": 300 发送请求时,服务会返回包含 dimensions must be one of (128, 256, 512, 768) 的 HTTP 400 响应,因为 MRL 只训练了这 4 个截断点。请保留 Content-Type 请求头。只有该请求头声明内容为 JSON 时,FastAPI 才会将请求体解析为 JSON;否则会返回 422 错误。
自行添加任务前缀
EmbeddingGemma 2 的训练数据使用了简短的文本前缀,用于说明每个嵌入的任务。对于搜索,Hugging Face 模型卡逐字给出了以下两个前缀:
task: search result | query: {query}
title: {title} | text: {content}第一个前缀放在每个搜索查询之前。第二个前缀放在每个要存储的文档之前。对于没有标题的文档,模型卡建议写入 title: none。搜索是非对称的,也就是说,查询和文档使用不同的前缀,这是设计如此。模型卡还列出了其他查询前缀,例如 task: question answering | query: {question} 和 task: code retrieval | query: {query}。它们与相同的文档前缀配对使用。
这两个服务都不会替您添加前缀。上文的服务会关闭库的默认提示,而 Ollama 的 /api/embed 会按原样传递您的字符串。请在客户端代码中统一添加前缀,就像下面的 pgvector 部分那样。这样,之后更换服务时就不会在不知情的情况下丢失前缀。
占用多少 RAM,速度如何?
这两个数值都取决于 CPU 和文本长度,因此本指南不提供固定数值。请在您自己的套餐上进行测量。有一个数值无需测量即可计算:float32 每个参数占用 4 bytes,因此 270M 文本骨干模型的权重大约为 1.1GB,完整的 740M 模型大约为 3.0GB。这就是上文服务请求使用的精度。省略 dtype 设置后,Transformers 会以每个参数 2 bytes 的 bfloat16 加载模型,大小约为 0.54GB 和 1.5GB;该卡片不建议在不支持原生 bfloat16 的 CPU 上使用这种设置。PyTorch 和 Python 还会额外占用内存,因此这些数值只能作为下限。相同的计算方法适用于您托管的所有模型;计算 VPS RAM 可容纳多大的模型介绍了如何为聊天模型进行估算。
要获取实际 RAM 占用,请在服务处理完一个请求后读取服务状态中的 Memory: 行:
systemctl status eg2 --no-pager | grep Memory要测量吞吐量,请发送一批包含 256 个短文档的请求并计时:
/opt/eg2/venv/bin/python - <<'EOF'
import json, time, urllib.request
texts = [f"title: none | text: Test document {i} about swap files and server memory." for i in range(256)]
body = json.dumps({"model": "embeddinggemma-2", "input": texts, "dimensions": 256}).encode()
req = urllib.request.Request(
"http://127.0.0.1:11435/api/embed",
data=body,
headers={"Content-Type": "application/json"},
)
t = time.perf_counter()
with urllib.request.urlopen(req) as r:
n = len(json.load(r)["embeddings"])
dt = time.perf_counter() - t
print(f"{n} embeddings in {dt:.1f}s = {n / dt:.1f} per second")
EOF运行两次,并保留第二次的结果,因为第一次运行包含预热操作。将结果与 nproc 的输出以及 lscpu 中的 CPU 型号一并记录。脱离运行该测试的机器,单独看一个数值没有太大意义。您的实际文档比这些测试行更长,而较长的输入会增加每次 embedding 所需的时间。在确定套餐规格前,请使用您自己的文本样本再次测量。
270m 和 740m 构建返回的向量相同吗?
目前无法在 Linux CPU 上通过 Ollama 测试,因为这两个标签都无法在那里运行。使用 Hugging Face checkpoint 可以测试同一个问题:比较仅文本加载和完整加载的结果。模型卡片说明,在每个构建中,文本输入都会经过同一个 270M 文本骨干网络,因此预期的余弦相似度应为 1.0 或非常接近 1.0。下面的脚本会以与服务相同的 float32 精度进行检查。该脚本需要约 4GB 可用 RAM,因为它会先后保留两份权重副本。它还会将模型的副本下载到 ~/.cache/huggingface。
/opt/eg2/venv/bin/python - <<'EOF'
import torch
from sentence_transformers import SentenceTransformer
text = ["title: none | text: A swap file lets the kernel move idle memory pages to disk."]
small = SentenceTransformer("google/embeddinggemma-2", device="cpu",
config_kwargs={"vision_config": None, "audio_config": None},
model_kwargs={"dtype": torch.float32})
small.default_prompt_name = None
a = small.encode(text, normalize_embeddings=True)
del small
full = SentenceTransformer("google/embeddinggemma-2", device="cpu",
model_kwargs={"dtype": torch.float32})
full.default_prompt_name = None
b = full.encode(text, normalize_embeddings=True)
print("cosine:", float((a * b).sum()))
EOF无论输出什么,都必须遵守一条规则:索引和查询必须使用相同的构建和相同的维度。Ollama 中的库构建使用 4-bit 量化,因此不要期待它们生成的向量与 float32 向量相同,也绝不要在同一个表中混用这两类向量。
在 pgvector 中存储 256 维向量
256 维向量占用的空间只有 768 维向量的三分之一,表和索引都是如此。在小型 VPS 上,必须将 HNSW(分层可导航小世界)索引装入 RAM,因此节省内存比节省磁盘空间更重要。在小型 VPS 上构建 pgvector HNSW 索引详细介绍了索引设置及其内存成本。Ubuntu 24.04 将 pgvector 作为 PostgreSQL 16 的软件包提供。
sudo apt install -y postgresql postgresql-16-pgvector
sudo -u postgres createuser "$USER"
sudo -u postgres createdb -O "$USER" rag
sudo -u postgres psql -d rag -c 'CREATE EXTENSION IF NOT EXISTS vector;'
psql -d rag <<'EOF'
CREATE TABLE docs (
id bigserial PRIMARY KEY,
title text NOT NULL,
body text NOT NULL,
embedding vector(256) NOT NULL
);
CREATE INDEX ON docs USING hnsw (embedding vector_cosine_ops);
EOF数据库角色与您的登录名相同,因此 psql 以及下面的脚本无需密码即可通过本地套接字连接。vector(256) 列会拒绝其他长度的向量。768 个数字组成的向量会因 expected 256 dimensions, not 768 而失败。如果客户端忘记 dimensions 字段,您就希望看到这个错误。
接下来配置客户端。前缀和请求设置都在这里定义。
mkdir -p ~/rag && cd ~/rag
cat > client.py <<'EOF'
import json
import urllib.request
URL = "http://127.0.0.1:11435/api/embed"
MODEL = "embeddinggemma-2"
DIM = 256
def _embed(texts):
body = json.dumps({"model": MODEL, "input": texts, "dimensions": DIM}).encode()
req = urllib.request.Request(URL, data=body, headers={"Content-Type": "application/json"})
with urllib.request.urlopen(req) as r:
return json.load(r)["embeddings"]
def embed_documents(docs):
return _embed([f"title: {title or 'none'} | text: {text}" for title, text in docs])
def embed_query(query):
return _embed([f"task: search result | query: {query}"])[0]
EOF
cat > index.py <<'EOF'
import numpy as np
import psycopg
from pgvector.psycopg import register_vector
from client import embed_documents
DOCS = [
("Firewall", "ufw denies inbound connections by default and allows outbound ones."),
("Swap", "A swap file lets the kernel move idle memory pages to disk when RAM runs low."),
("SSH keys", "Key-based login replaces passwords with a private key that stays on your laptop."),
]
with psycopg.connect("dbname=rag") as conn:
register_vector(conn)
for (title, body), vec in zip(DOCS, embed_documents(DOCS)):
conn.execute(
"INSERT INTO docs (title, body, embedding) VALUES (%s, %s, %s)",
(title, body, np.array(vec)),
)
print(f"indexed {len(DOCS)} documents")
EOF
cat > search.py <<'EOF'
import sys
import numpy as np
import psycopg
from pgvector.psycopg import register_vector
from client import embed_query
q = np.array(embed_query(" ".join(sys.argv[1:])))
with psycopg.connect("dbname=rag") as conn:
register_vector(conn)
rows = conn.execute(
"SELECT title, 1 - (embedding <=> %s) AS score FROM docs ORDER BY embedding <=> %s LIMIT 3",
(q, q),
).fetchall()
for title, score in rows:
print(f"{score:.3f} {title}")
EOF
/opt/eg2/venv/bin/python index.py
/opt/eg2/venv/bin/python search.py how do I stop running out of memoryindex.py 应输出 indexed 3 documents。search.py 会按得分从高到低输出 3 个标题及其得分,对于该问题,Swap 文档应排在首位。<=> 是 pgvector 的余弦距离,因此 1 - 会将其转换为相似度得分。只运行一次 index.py;否则请先清空表,因为每次运行都会再次插入这些行。有关长文档分块并将匹配结果交给聊天模型的做法,请参阅VPS 上完整的自托管 RAG 流程,该流程从此表继续。
不要将端口 11434 暴露到公网
这两个 API 都没有任何身份验证。任何能够访问该端口的人都可以占用您的 CPU;使用 Ollama 时,还可以拉取和删除模型。Ollama 默认监听 127.0.0.1:11434,上面的服务监听 127.0.0.1:11435。请保持这两个设置不变。常见错误是将 OLLAMA_HOST=0.0.0.0:11434 设置为允许从其他计算机访问 Ollama。除非防火墙阻止,否则这会将其暴露给整个互联网。检查实际处于监听状态的地址:
sudo ss -tlnp | grep -E ':1143[45]'每一行都应将 127.0.0.1 显示为本地地址。包含 0.0.0.0 或 * 的行表示该端口已在所有网络接口上开放。如果另一台计算机需要使用嵌入服务,请为其提供 SSH 隧道,而不要开放端口:
ssh -N -L 11435:127.0.0.1:11435 you@your-vps然后,另一台计算机将 http://127.0.0.1:11435/api/embed 视为本地服务进行调用。端口的作用以及客户端如何找到该服务,请参阅端口 11434 上的 Ollama API。如果确实需要可访问的端点,请参阅保护 Ollama API 端点,在其前面配置带身份验证的反向代理。
Ollama 支持 Linux 后再切换
每次发布 Ollama 新版本后,都重新运行 Ollama 部分中的检查。VPS 上的 ollama pull embeddinggemma-2:270m 成功后,使用相同的请求格式进行测试:
curl -s http://127.0.0.1:11434/api/embed \
-d '{"model": "embeddinggemma-2:270m", "input": ["task: search result | query: how do I add swap?"], "dimensions": 256}' \
| python3 -c 'import json,sys; v=json.load(sys.stdin)["embeddings"][0]; print(len(v), round(sum(x*x for x in v) ** 0.5, 4))'如果输出 256,且长度接近 1.0,请在 client.py 中将 URL 改为端口 11434,并将 MODEL 改为 embeddinggemma-2:270m。然后清空该表,再次运行 index.py。这一步不可省略。4-bit Ollama 构建版本生成的向量与 float32 检查点生成的向量不同,因此旧行和新查询无法在相同条件下进行比较。
FAQ
Ollama 能在仅 CPU 的 Linux VPS 上运行 EmbeddingGemma 2 吗?
截至 2026 年 10 月 7 日,不能使用 Ollama 0.40.0。0.40.0 的发行说明在 Ollama 的 MLX 引擎下添加了 embeddinggemma-2;在 Linux 上,该引擎需要 CUDA 13 和 cuDNN 9。已有报告显示,Linux 拉取模型会因 this model requires MLX support, but the MLX runtime is not available 失败(ollama/ollama issue 18825)。截至 2026 年 10 月 11 日,所有稳定版本中最高为 0.40.3,均未提及修复;0.40.4-rc0 预发布版本只为该模型更新了 llama.cpp。请改用 sentence-transformers,在 127.0.0.1 上加载 Hugging Face checkpoint。每次 Ollama 发布新版本后,都应重新运行 ollama pull embeddinggemma-2:270m。
Ollama 会自动为我添加 EmbeddingGemma 2 的任务前缀吗?
不会。该模型的库页面没有提供模板,而 /api/embed 会完全按原样嵌入你发送的字符串。请自行在每个查询前添加 task: search result | query: ,在每个文档前添加 title: {title} | text: 。没有标题时使用 title: none。Hugging Face 模型卡列出了这些前缀,模型也是使用这些前缀训练的。
我应该在 pgvector 中存储多大的 embedding 维度?
在小型 VPS 上,256 是一个合适的默认值。MRL 训练允许 EmbeddingGemma 2 将 768 维向量截断为 512、256 或 128 维。维度越少,表越小,驻留在 RAM 中的 HNSW 索引也越小。截断向量后再次进行归一化,并确保查询和文档使用相同的维度。将列声明为 vector(256),这样长度错误的向量会被拒绝。
我可以通过 Ollama 使用 EmbeddingGemma 2 生成图像或音频 embedding 吗?
不能。Ollama 的 /api/embed 只接受字符串或字符串列表。Ollama 库页面为某些标签列出了图像输入,但文档化的 API 没有提供发送图像的方式。对于图像、视频和音频 embedding,请按照 Hugging Face 模型卡的说明使用 sentence-transformers 或 Transformers,并加载所需的视觉或音频编码器。
EmbeddingGemma 2 在 VPS 上需要多少 RAM?
请使用 systemctl status eg2 在你的方案上进行测量,因为额外开销会有所不同。模型权重本身决定了最低需求。对于 float32,每个参数占 4 字节,270M 的纯文本模型约占 1.1GB,完整的 740M 模型约占 3.0GB。除非传入 model_kwargs={"dtype": torch.float32},否则 Transformers 5 会将此 checkpoint 加载为 bfloat16;这样两项数据分别约为 0.54GB 和 1.5GB,但模型卡建议在大多数 CPU 上使用 float32。只生成文本 embedding 时,使用 config_kwargs={"vision_config": None, "audio_config": None} 加载纯文本模型。