Meilisearch 将 Algolia 的用户体验封装进了一个单一的 Rust 二进制文件。运行在 $5 VPS 上,通过 HTTP 建立索引,毫秒级查询响应。开源项目,使用与 Algolia 相同的 UI 组件库。
运行 Meilisearch 有两种方式:自托管(免费,自行维护服务器)或 Meilisearch Cloud ↗(付费,由官方托管)。本教程介绍自托管方案。
单一二进制文件,一行命令启动:
curl -L https://install.meilisearch.com | sh
./meilisearch --master-key="your-strong-master-key"
监听 http://localhost:7700。生产环境必须设置 master key;不设置时 Meilisearch 以开发模式运行(无身份验证)。正式使用请生成一个足够长的随机字符串。
Docker 方式:
docker run -it --rm \
-p 7700:7700 \
-v $(pwd)/meili_data:/meili_data \
getmeili/meilisearch:latest \
meilisearch --master-key="your-strong-master-key"
验证是否正常运行:
curl http://localhost:7700/health
# {"status":"available"}
在 DigitalOcean、Hetzner 等平台开一台 $5/月的服务器,SSH 登录后执行:
# Install Meilisearch
curl -L https://install.meilisearch.com | sh
sudo mv ./meilisearch /usr/local/bin/
# Run as a systemd service
sudo nano /etc/systemd/system/meilisearch.service
粘贴以下内容:
[Unit]
Description=Meilisearch
After=systemd-user-sessions.service
[Service]
Type=simple
ExecStart=/usr/local/bin/meilisearch --config-file-path /etc/meilisearch.toml
Restart=on-failure
[Install]
WantedBy=multi-user.target
创建 /etc/meilisearch.toml,填入 master key、数据路径、运行环境等配置(参见 配置文档 ↗)。
sudo systemctl enable meilisearch
sudo systemctl start meilisearch
在前面加上 Nginx + HTTPS,你就拥有了一个真正可用的搜索端点:https://search.yourdomain.com。
master key 仅用于管理员操作,不要在应用中直接使用。请为应用创建权限受限的 API 密钥。
首次启动时会自动生成两个默认密钥,用 master key 查询 keys 接口获取:
curl -X GET 'http://localhost:7700/keys' \
-H 'Authorization: Bearer your-master-key'
两个默认密钥:
MEILI_HOST=https://search.yourdomain.com
MEILI_MASTER_KEY=your-master-key # backend admin ops only
MEILI_ADMIN_KEY=xxxxxxxxxx # backend; from Default Admin API Key
MEILI_SEARCH_KEY=xxxxxxxxxx # safe for client; from Default Search API Key
npm install meilisearch
import { MeiliSearch } from "meilisearch";
const client = new MeiliSearch({
host: process.env.MEILI_HOST,
apiKey: process.env.MEILI_ADMIN_KEY,
});
// Add documents (creates the index automatically)
await client.index("posts").addDocuments([
{
id: 1, // required; primary key
title: "How to deploy to Vercel",
body: "First, install the CLI...",
tags: ["deploy", "vercel"],
published_at: 1714521600,
},
{ id: 2, title: "...", body: "..." },
]);
Meilisearch 异步处理文档,返回一个任务 ID。批量导入数百万条记录时,可轮询 /tasks/{id} 确认完成状态。少量添加时,数据通常在毫秒内即可搜索。
最常用的两类设置(与 Algolia 概念相同):
// Which fields are searchable, in priority order
await client.index("posts").updateSearchableAttributes([
"title",
"body",
"tags",
]);
// Which fields you can filter on
await client.index("posts").updateFilterableAttributes(["tags", "author"]);
// Custom ranking
await client.index("posts").updateRankingRules([
"words", "typo", "proximity", "attribute",
"sort", "exactness",
"published_at:desc", // newer first
]);
import { MeiliSearch } from "meilisearch";
const client = new MeiliSearch({
host: process.env.NEXT_PUBLIC_MEILI_HOST,
apiKey: process.env.NEXT_PUBLIC_MEILI_SEARCH_KEY, // search-only; safe
});
const results = await client.index("posts").search("vercel", {
limit: 10,
filter: ['tags = "deploy"'],
});
使用仅搜索密钥。该密钥只能读取,不能修改数据,可以安全地放到浏览器端。
Meilisearch 提供了与 InstantSearch 兼容的适配器,所有 Algolia UI 组件都可以直接使用:
npm install instantsearch.js @meilisearch/instant-meilisearch
# or for React:
npm install react-instantsearch @meilisearch/instant-meilisearch
import { InstantSearch, SearchBox, Hits } from "react-instantsearch";
import { instantMeiliSearch } from "@meilisearch/instant-meilisearch";
const { searchClient } = instantMeiliSearch(
process.env.NEXT_PUBLIC_MEILI_HOST,
process.env.NEXT_PUBLIC_MEILI_SEARCH_KEY,
);
export function Search() {
return (
<InstantSearch searchClient={searchClient} indexName="posts">
<SearchBox />
<Hits hitComponent={({ hit }) => <div>{hit.title}</div>} />
</InstantSearch>
);
}
与 Algolia 的同步模式相同:
addDocuments。实现简单,但会略微增加写延迟。对于 Postgres → Meilisearch 的同步,Airbyte ↗ 提供免费的连接器。如果你使用 Supabase,也可以直接使用 Supabase 的 Meilisearch Wrapper ↗。
// Update (merges with existing fields by primary key)
await client.index("posts").updateDocuments([
{ id: 1, body: "Updated body" },
]);
// Delete
await client.index("posts").deleteDocument(1);
await client.index("posts").deleteDocuments({ filter: 'tags = "draft"' });
// Stats
const stats = await client.index("posts").getStats();
console.log(stats.numberOfDocuments);
// Drop the whole index
await client.deleteIndex("posts");
Meilisearch 会生成一个单独的 dump 文件,可用于恢复数据:
curl -X POST 'http://localhost:7700/dumps' \
-H 'Authorization: Bearer your-master-key'
dump 文件保存在配置的数据目录中。可通过 cron 定期触发,再用 rsync 同步到 S3 / R2 进行异地备份。恢复时,在启动 Meilisearch 时加上 --import-dump path/to/dump.dump 参数即可。
Meilisearch 可以在几分钟内从源数据库重建索引——对很多团队来说,"数据库就是备份,发生故障时重新同步到 Meilisearch"的方案已经足够。
Meilisearch Cloud ↗ 托管的是与自托管完全相同的引擎。入门套餐 $30/月。如果你不想维护一台 Linux 服务器,这是值得的选择;在相当规模下,费用仍远低于 Algolia。
迁移是对称的——从自托管导出 dump,恢复到 Cloud,再更新客户端的 host URL 即可。