Архитектура
Хранение
B-tree со страницами по 4 KB, значения сериализуются в JSON; крупные значения (>~2 KB) уходят в overflow-страницы. Каждая база — один файл .fdb плюс WAL (.fdb.wal).
Crash recovery
После любого сбоя (kill, SIGTERM, kernel panic, потеря питания) — каждая зафиксированная транзакция переживает рестарт:
- WAL пишется до основного файла, fsync на каждом commit.
- При
OpenDatabaserecovery проигрывает все committed-транзакции в порядке возрастания txID. - Каталог (rootID каждого B-tree + auto-increment счётчики + схема) обновляется внутри WAL-транзакции, атомарно с данными.
- Вытеснение «грязных» страниц из page cache не пишет в основной файл напрямую — это нарушило бы WAL-инвариант.
- Checkpoint сбрасывает page cache и усекает WAL — фоново каждые 60 секунд и при штатном
Close()/CloseAll().
Важно для встраивающих приложений: если процесс завершается без явного вызова CloseAll() (или Checkpoint() на конкретной базе) — например, голым os.Exit или необработанным сигналом — последние закоммиченные, но ещё не зачекпоинченные записи рискуют не попасть в основной файл при следующем открытии. Начиная с v2.10 в пакете api есть Server.CloseOnSignal() — опциональный помощник, который сам подписывается на SIGINT/SIGTERM, вызывает CloseAll() и передаёт сигнал дальше.
Безопасность
- Пароли — PBKDF2-HMAC-SHA256, 100 000 итераций, 16-байтовая соль.
- Constant-time compare для всех проверок credential.
- Path-traversal защита через
validateDBName()—..,/, `` отвергаются. - Лимит размера тела запроса — 16 MiB на auth-защищённых эндпоинтах.
- RPC — read deadline 60s и лимит попыток аутентификации.
- Конфиги с
api_keyсохраняются с правами0600.