Skip to content

test(cerebro): add backup and restore integration test#738

Merged
yacosta738 merged 5 commits into
mainfrom
feat/cerebro-backup-restore-test
May 1, 2026
Merged

test(cerebro): add backup and restore integration test#738
yacosta738 merged 5 commits into
mainfrom
feat/cerebro-backup-restore-test

Conversation

@yacosta738
Copy link
Copy Markdown
Contributor

@yacosta738 yacosta738 commented May 1, 2026

Summary

Adds comprehensive backup and restore integration test for Cerebro with detailed operational documentation.

Closes #694

Changes

  • Integration Test (backup_restore_test.rs):

    • Validates complete backup/restore cycle with 10 test memories
    • Tests data persistence through shutdown and restore
    • Verifies memory count, search, and individual retrieval post-restore
    • Uses real MCP calls (mem_save, mem_stats, mem_search, mem_get_observation)
  • Test Helpers (tests/helpers/mod.rs):

    • start_cerebro_server() - starts server with custom config and returns JoinHandle
    • wait_for_ready() - polls health endpoint with timeout
    • create_test_memories() - creates test data via MCP
  • Documentation (operations.md):

    • Step-by-step backup procedures with Authorization headers
    • Restore workflow with verification steps
    • Best practices and safety guidelines
    • Practical examples with real commands
  • Dependencies:

    • Added fs_extra for directory operations in tests
    • Updated PostCSS to ^8.5.13 for consistency
    • Updated Astro to ^6.2.1 for consistency

Test Results

All 63 Cerebro tests pass, including the new backup/restore test (~2.2s).

Validation

The test validates:

  1. ✅ Start Cerebro with embedded SurrealDB
  2. ✅ Create 10 test memories via MCP mem_save
  3. ✅ Verify data exists (mem_stats shows count: 10)
  4. ✅ Graceful shutdown with 2s wait for lock release
  5. ✅ Copy storage directory to backup location
  6. ✅ Simulate data loss (remove original storage)
  7. ✅ Restore from backup copy
  8. ✅ Restart Cerebro successfully
  9. ✅ Verify memory count matches (10 == 10)
  10. ✅ Verify individual memories retrievable
  11. ✅ Verify search functionality works with actual hit validation

Code Review Fixes

  • Fixed rustfmt formatting in shutdown block
  • Enhanced search assertions to verify actual hits with summary field
  • Added JoinHandle return from start_cerebro_server for proper shutdown tracking
  • Fixed PostCSS and Astro version inconsistencies
  • Added Authorization headers to MCP curl examples in documentation

yacosta738 added 2 commits May 1, 2026 13:16
- Add comprehensive backup_restore_test.rs that validates:
  * Data persistence through backup/restore cycle
  * Memory count preservation (10 test memories)
  * Individual memory retrieval after restore
  * Search functionality post-restore
- Add test helpers for:
  * Starting/stopping Cerebro server with custom config
  * Creating test memories via MCP calls
  * Waiting for service readiness
- Update operations.md with detailed backup/restore procedures:
  * Step-by-step backup instructions
  * Restore workflow with verification steps
  * Best practices and safety guidelines
- Add fs_extra dependency for directory operations in tests

The test validates the complete backup/restore workflow:
1. Start Cerebro with embedded SurrealDB
2. Create test data via MCP mem_save calls
3. Verify data exists via mem_stats and mem_search
4. Gracefully shutdown and copy storage directory
5. Simulate data loss by removing original storage
6. Restore from backup copy
7. Restart Cerebro and verify all data is intact

All Cerebro tests pass (63 tests total).
@github-actions github-actions Bot added the size/xl Denotes an extra large change size label May 1, 2026
@cloudflare-workers-and-pages
Copy link
Copy Markdown

cloudflare-workers-and-pages Bot commented May 1, 2026

Deploying corvus with  Cloudflare Pages  Cloudflare Pages

Latest commit: fee7878
Status: ✅  Deploy successful!
Preview URL: https://7c5621a1.corvus-42x.pages.dev
Branch Preview URL: https://feat-cerebro-backup-restore.corvus-42x.pages.dev

View logs

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 1, 2026

📝 Walkthrough

Walkthrough

This PR improves test infrastructure by capturing server handles from async operations, strengthens backup/restore test assertions by validating actual data content, updates API documentation to reflect authentication requirements and parameter format changes, and bumps dependency versions for astro and postcss.

Changes

Cohort / File(s) Summary
Test Infrastructure
clients/cerebro/tests/helpers/mod.rs, clients/cerebro/tests/backup_restore_test.rs
Updated start_cerebro_server to return tokio::task::JoinHandle<()> alongside existing tuple elements. Tests now capture and explicitly hold server handles. Strengthened mem_search assertions by parsing result.output.results as an array and validating that at least one hit contains expected test content, replacing looser shape validation.
API Documentation
clients/web/apps/docs/src/content/docs/cerebro/operations.md
Added Authorization: Bearer <YOUR_TOKEN> header to post-restore verification commands for mem_stats, mem_search, and tools/list. Updated MCP request payloads to use params.arguments.input structure and adjusted output extraction to read from result.output rather than result.content[0].text.
Dependencies
package.json
Bumped astro override from ^6.1.6 to ^6.2.1 and postcss override from ^8.5.10 to ^8.5.13 in pnpm.overrides.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~12 minutes

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed Title follows Conventional Commits style with 'test' prefix, includes scope 'cerebro', and is under 72 characters (54 chars). Clearly describes the main change: adding a backup and restore integration test.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description check ✅ Passed PR description comprehensively covers changes across four files, includes closing issue reference, detailed test validation steps, and code review fixes.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/cerebro-backup-restore-test

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 7

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@clients/cerebro/tests/backup_restore_test.rs`:
- Around line 121-127: Reformat the shutdown block to satisfy rustfmt by
removing the extra blank lines and aligning comments and statements on
consecutive lines: send on shutdown_tx (let _ = shutdown_tx.send(true);), then
drop(service); and then await tokio::time::sleep(Duration::from_secs(2)).await;
so the three statements and their comments are compactly arranged without stray
blank lines to fix the formatter failure.
- Around line 113-117: The test currently only checks that search_body["result"]
is an object which doesn't verify actual hits; update the assertions at the two
places around the search response parsing (the code that builds search_body from
search_resp.json().await and currently asserts
search_body["result"].is_object()) to instead assert that search_body["result"]
contains a non-empty hits array and that at least one hit matches the memory we
created (e.g., by id or by expected text/content field). Locate the occurrences
using the symbols search_resp, search_body and the mem_search-related assertions
and replace the generic is_object() check with an assert that
search_body["result"]["hits"].as_array() is Some and has length > 0 and that one
of the hits contains the expected memory identifier or content.

In `@clients/cerebro/tests/helpers/mod.rs`:
- Around line 44-62: The helper start_cerebro_server spawns the axum server but
doesn't return the tokio::task::JoinHandle, forcing callers to guess shutdown
timing; change start_cerebro_server to return the JoinHandle
(tokio::task::JoinHandle<()>) as part of its Result tuple, capture the result of
tokio::spawn into a variable (e.g., server_handle) instead of discarding it, and
return that handle alongside (service, shutdown_tx, base_url) so callers can set
the shutdown watch sender, await wait_for_shutdown, and then .await the returned
JoinHandle to observe proper shutdown and any panics from the axum::serve task
(keep existing wait_for_shutdown usage).

In `@clients/web/apps/dashboard/package.json`:
- Line 48: The PostCSS version is inconsistent:
clients/web/apps/dashboard/package.json declares "postcss": "^8.5.13" while the
root pnpm.overrides.postcss is "^8.5.10"; update the root override to match the
dashboard package (set pnpm.overrides.postcss to "^8.5.13") or alternatively
change the dashboard package to "^8.5.10" so both locations match, then run pnpm
install to regenerate pnpm-lock.yaml (ensure the lockfile records the chosen
version).

In `@clients/web/apps/docs/src/content/docs/cerebro/operations.md`:
- Around line 344-370: The MCP verification curl examples call the protected
/mcp endpoints (mem_stats, mem_search, and tools/list) but omit Authorization so
they'll 401; update each curl to include the Authorization header (e.g., add -H
"Authorization: Bearer <TOKEN>") or insert a short explicit note above the
commands instructing users to include a valid Bearer token when hitting /mcp so
mem_stats, mem_search, and tools/list succeed in token-protected deployments.

In `@clients/web/apps/marketing/package.json`:
- Line 25: Update the pinned Astro version in the root pnpm.overrides to match
the marketing package's "astro" range (^6.2.1) and then regenerate the lockfile
(run a workspace install such as pnpm install) so pnpm-lock.yaml reflects the
new override; verify the marketing package.json "astro" entry and the
pnpm.overrides "astro" entry are identical and that frozen-lockfile validation
passes.

In `@package.json`:
- Around line 3-4: The workspace has inconsistent TypeScript/@astrojs/check
versions between root and catalog causing mixed type checking; update the
catalog entries for "typescript" to 6.0.3 and "@astrojs/check" to 0.9.9 to match
the root package.json, then regenerate the lockfile (pnpm-lock.yaml) by running
the workspace install (e.g., pnpm install) so the new catalog versions are
resolved and the lockfile is updated.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: bd17eeb7-3651-42fd-8ae4-44d73713f056

📥 Commits

Reviewing files that changed from the base of the PR and between 2599c77 and 0bae9ba.

⛔ Files ignored due to path filters (3)
  • clients/agent-runtime/Cargo.lock is excluded by !**/*.lock
  • clients/cerebro/Cargo.lock is excluded by !**/*.lock
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (9)
  • clients/cerebro/Cargo.toml
  • clients/cerebro/tests/backup_restore_test.rs
  • clients/cerebro/tests/helpers/mod.rs
  • clients/web/apps/dashboard/package.json
  • clients/web/apps/docs/package.json
  • clients/web/apps/docs/src/content/docs/cerebro/operations.md
  • clients/web/apps/marketing/package.json
  • clients/web/package.json
  • package.json
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Cloudflare Pages
🧰 Additional context used
📓 Path-based instructions (3)
**/*

⚙️ CodeRabbit configuration file

**/*: Security first, performance second.
Validate input boundaries, auth/authz implications, and secret management.
Look for behavioral regressions, missing tests, and contract breaks across modules.

Files:

  • clients/web/apps/marketing/package.json
  • clients/cerebro/Cargo.toml
  • clients/web/package.json
  • package.json
  • clients/web/apps/dashboard/package.json
  • clients/web/apps/docs/package.json
  • clients/cerebro/tests/backup_restore_test.rs
  • clients/web/apps/docs/src/content/docs/cerebro/operations.md
  • clients/cerebro/tests/helpers/mod.rs
**/*.rs

⚙️ CodeRabbit configuration file

**/*.rs: Focus on Rust idioms, memory safety, and ownership/borrowing correctness.
Flag unnecessary clones, unchecked panics in production paths, and weak error context.
Prioritize unsafe blocks, FFI boundaries, concurrency races, and secret handling.

Files:

  • clients/cerebro/tests/backup_restore_test.rs
  • clients/cerebro/tests/helpers/mod.rs
**/*.{md,mdx}

⚙️ CodeRabbit configuration file

**/*.{md,mdx}: Verify technical accuracy and that docs stay aligned with code changes.
For user-facing docs, check EN/ES parity or explicitly note pending translation gaps.

Files:

  • clients/web/apps/docs/src/content/docs/cerebro/operations.md
🧠 Learnings (3)
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/**/Cargo.toml : Do not add heavy dependencies for minor convenience; justify new crate additions

Applied to files:

  • clients/cerebro/Cargo.toml
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/**/Cargo.toml : Preserve release-size profile assumptions in `Cargo.toml` and avoid adding heavy dependencies unless clearly justified

Applied to files:

  • clients/cerebro/Cargo.toml
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/**/*.rs : Run `cargo fmt --all -- --check`, `cargo clippy --all-targets -- -D warnings`, and `cargo test` for code validation, or document which checks were skipped and why

Applied to files:

  • clients/cerebro/Cargo.toml
🪛 GitHub Actions: PR Checks
clients/cerebro/tests/backup_restore_test.rs

[error] 119-120: cargo fmt --check failed: formatting diff detected (whitespace/blank line changes around shutdown_tx.send(true) and drop(service)).

clients/cerebro/tests/helpers/mod.rs

[error] 130-130: cargo fmt --check failed: formatting diff detected (whitespace/blank line changes around resp.json().await?).


[error] 137-138: cargo fmt --check failed: formatting diff detected (ok_or_else closure formatting for anyhow::anyhow(...) expression).

🪛 GitHub Actions: SonarQube Analysis
clients/web/apps/marketing/package.json

[error] 1-1: pnpm install --frozen-lockfile failed because pnpm-lock.yaml specifiers do not match package.json. Consider updating the lockfile (or run without --frozen-lockfile).

clients/web/package.json

[error] 1-1: pnpm install --frozen-lockfile failed because pnpm-lock.yaml specifiers do not match package.json. Consider updating the lockfile (or run without --frozen-lockfile).

package.json

[error] 1-1: pnpm install --frozen-lockfile failed because pnpm-lock.yaml specifiers do not match package.json. Consider updating the lockfile (or run without --frozen-lockfile).

clients/web/apps/dashboard/package.json

[error] 1-1: pnpm install --frozen-lockfile failed because pnpm-lock.yaml specifiers do not match package.json. Consider updating the lockfile (or run without --frozen-lockfile).

clients/web/apps/docs/package.json

[error] 1-1: pnpm install --frozen-lockfile failed because pnpm-lock.yaml specifiers do not match package.json. Consider updating the lockfile (or run without --frozen-lockfile).

🪛 LanguageTool
clients/web/apps/docs/src/content/docs/cerebro/operations.md

[uncategorized] ~231-~231: If this is a compound adjective that modifies the following noun, use a hyphen.
Context: ...db ### Cold Backup Procedure #### Bare Metal Deployment bash # 1. Stop Cerebro g...

(EN_COMPOUND_ADJECTIVE_INTERNAL)


[uncategorized] ~284-~284: If this is a compound adjective that modifies the following noun, use a hyphen.
Context: ...erebro ### Restore Procedure #### Bare Metal Deployment bash # 1. Stop Cerebro s...

(EN_COMPOUND_ADJECTIVE_INTERNAL)

🪛 markdownlint-cli2 (0.22.1)
clients/web/apps/docs/src/content/docs/cerebro/operations.md

[warning] 339-339: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 345-345: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 355-355: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 365-365: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)

🔇 Additional comments (3)
clients/web/apps/docs/package.json (1)

22-22: Duplicate: same Astro override conflict as the marketing app.

The root pnpm.overrides.astro entry still pins ^6.1.6, so this ^6.2.1 specifier is likely to be masked until the root override and lockfile are updated.

clients/web/package.json (1)

37-37: LGTM.

This is a localized Stylelint version bump and doesn't require any manifest or script changes.

clients/cerebro/tests/helpers/mod.rs (1)

132-137: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Fix the failing cargo fmt diff in this parsing block.

The whitespace/closure layout here is already tripping cargo fmt --check, so CI will stay red until this block is reformatted.

⛔ Skipped due to learnings
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/**/*.rs : Run `cargo fmt --all -- --check`, `cargo clippy --all-targets -- -D warnings`, and `cargo test` for code validation, or document which checks were skipped and why

Comment thread clients/cerebro/tests/backup_restore_test.rs
Comment thread clients/cerebro/tests/backup_restore_test.rs
Comment thread clients/cerebro/tests/helpers/mod.rs Outdated
Comment thread clients/web/apps/dashboard/package.json
Comment thread clients/web/apps/docs/src/content/docs/cerebro/operations.md
Comment thread clients/web/apps/marketing/package.json
Comment thread package.json
@github-actions github-actions Bot added size/xs Denotes an extra small change size and removed size/xl Denotes an extra large change size labels May 1, 2026
- Fix rustfmt formatting in backup_restore_test.rs shutdown block
- Update search assertions to verify actual hits with summary field
- Return JoinHandle from start_cerebro_server for proper shutdown tracking
- Fix PostCSS version inconsistency (^8.5.10 -> ^8.5.13)
- Fix Astro version inconsistency (^6.1.6 -> ^6.2.1)
- Add Authorization headers to MCP curl examples in operations.md
- Update pnpm lockfile with new dependency versions
@github-actions github-actions Bot added size/m Denotes a medium change size and removed size/xs Denotes an extra small change size labels May 1, 2026
@sonarqubecloud
Copy link
Copy Markdown

sonarqubecloud Bot commented May 1, 2026

@yacosta738 yacosta738 self-assigned this May 1, 2026
@yacosta738 yacosta738 merged commit 26f0e52 into main May 1, 2026
20 checks passed
@yacosta738 yacosta738 deleted the feat/cerebro-backup-restore-test branch May 1, 2026 13:10
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size/m Denotes a medium change size

Projects

None yet

Development

Successfully merging this pull request may close these issues.

cerebro: document and validate backup/restore for embedded storage

1 participant