数据目录
Quickwit 使用一个本地目录来存储临时文件。默认情况下,这个工作目录名为 qwdata
,位于 Quickwit 二进制文件旁边。
让我们来看看 Quickwit 如何组织数据目录。
数据目录布局
运行 Quickwit 时,最终会得到以下目录结构:
qwdata
├── cache
│ └── splits
| ├── 03BSWV41QNGY5MZV9JYAE1DCGA.split
│ └── 01GSWV41QNGY5MZV9JYAE1DCB7.split
├── delete_task_service
│ └── wikipedia%01H13SVKDS03P%TpCfrA
├── indexing
│ ├── wikipedia%01H13SVKDS03P%_ingest-api-source%RbaOAI
│ └── wikipedia%01H13SVKDS03P%kafka-source%cNqQtI
└── queues
├── partition_id
├── wal-00000000000000000028
└── wal-00000000000000000029
/queues
目录
此目录仅在您的节点上运行 ingest API 服务时创建。它包含 ingest API 的写前日志文件,以防止数据丢失。 当 Quickwit 提交一个分片(索引的一部分)时,队列会被截断,这意味着分片已存储在存储中,其元数据也在元存储中。
您可以在 节点配置文件 中配置 max_queue_memory_usage
和 max_queue_disk_usage
以限制最大磁盘使用量。
/indexing
目录
此目录保存每个索引的每个索引源的本地索引目录。在上面的目录树中,可以看到两个对应于 wikipedia
索引的目录,这意味着该索引当前正在处理两个来源。
/delete_task_service
目录
此目录由 Janitor 服务用于在索引上应用删除操作。在此过程中,分片会被下载,同时应用删除操作创建新的分片,并上传到目标存储。此目录仅在运行 Janitor 服务的节点上创建。
/cache
目录
此目录用于缓存即将进行合并操作的分片,以节省磁盘 IOPS。如果分片超过两天,则会被驱逐。如果达到缓存限制,则驱逐最旧的分片。
您可以 配置 缓存可以持有的分片数量 split_store_max_num_splits
,并使用 split_store_max_num_bytes
限制分片的整体字节数。
设置合适的分片缓存限制
在 Quickwit 需要合并分片时,缓存分片可以节省磁盘 IOPS。
设置合适的限制取决于您的 合并策略 和使用的分区数量。默认的分片缓存限制应该适用于大多数用例。
默认配置下的分片缓存
对于给定的索引,Quickwit 每分钟提交一个分片,并使用 "Stable log" 合并策略。此合并策略默认按组合并分片,每组 10、11 或 12 个分片,直到分片包含超过 1000 万条文档。一个分片通常会经历 3 或 4 次合并,之后被认为是成熟的,并从缓存中驱逐。
下表显示了在给定时间内创建多少分片,假设以 20MB/s 的速率进行索引,并且压缩比为 0.5:
Time (minutes) | Number of splits | Splits size (GB) |
---|---|---|
1 | 1 | 0.6 GB |
2 | 2 | 1.2 GB |
10 | 10 | 6 GB |
11 | 1 + 1 (merged once) | 6.6 GB |
21 | 1 + 2 (merged once) | 12.6 GB |
91 | 1 + 9 (merged once) | 54.6 GB |
101 | 1 + 1 (merged twice) | 60.6 GB |
111 | 2 + 1 (merged once) + 1 (merged twice) | 66.6 GB |
201 | 1 + 0 (merged once) + 2 (merged twice) | 120.6 GB |
.. | ... |
在这种情况下,默认的缓存限制(1000 个分片和 100GB)足以避免在前两次合并时从存储中下载分片。这对于生产环境来说是完全可行的。如果您希望避免任何分片下载,可以增加分片缓存大小。
您可以使用我们的 indexers dashboard 监控下载速率。
使用分区的分片缓存
当使用 分区 时,Quickwit 会为每个分区创建一个分片,分片的数量会迅速增加。
让我们通过一个具体的例子来看,假设条件如下:
- 提交超时时间 为 1 分钟。
- 分区数量为 100 个。假设每分钟每个分区都有一条文档被索引,Quickwit 将每分钟创建 100 个分片。
- 合并策略会在每个分区有 10 个分片时立即进行合并。
下表显示了在给定时间内创建的分片数量:
Time (minutes) | Number of splits |
---|---|
1 | 100 |
2 | 200 |
10 | 1000 |
11 | 100 + 100 (merged once) |
21 | 100 + 200 (merged once) |
91 | 100 + 900 (merged once) |
100 | 1000 + 900 (merged once) |
101 | 100 + 0 (merge once) + 100 (merged twice) |
200 | 1000 + 900 (merged once) + 100 (merged twice) |
201 | 100 + 0 (merged once) + 200 (merged twice) |
在这种情况下,为了在第一次合并操作时避免从存储中下载分片,您需要将 split_store_max_num_splits
设置为至少 1000。由于合并操作可能需要一些时间,建议将 split_store_max_num_splits
设置为一个能够容纳所有未合并分片加上新进入分片的值,例如 1100 个分片应该足够。如果您希望存储分片直到第二次合并,那么 2500 个分片的限制应该足够。
处理大量本地分片的问题
启动时,Quickwit 会扫描缓存目录中的所有分片,以确定哪些分片存在于本地。如果有数万个分片,这可能会花费几分钟的时间。在 Kubernetes 上,如果启动时间过长,您的 Pod 可能会被重启,因此您可能需要清理数据目录或增加存活探测(liveness probe)的超时时间。
此外,请在 GitHub 上报告这种行为,因为我们肯定可以优化启动阶段。