Skip to content

feat(search): add Querit provider#2753

Merged
senamakel merged 9 commits into
tinyhumansai:mainfrom
MurphyZzzzz:codex/querit-search
May 29, 2026
Merged

feat(search): add Querit provider#2753
senamakel merged 9 commits into
tinyhumansai:mainfrom
MurphyZzzzz:codex/querit-search

Conversation

@MurphyZzzzz
Copy link
Copy Markdown
Contributor

@MurphyZzzzz MurphyZzzzz commented May 27, 2026

Summary

  • Add a direct Querit web search integration using POST https://api.querit.ai/v1/search.
  • Expose Querit as a selectable search engine alongside Managed, Parallel, and Brave.
  • Add Querit API key configuration through search settings, env overrides, and .env.example.
  • Register querit_search and web_search_tool when Querit is the active configured engine.
  • Add focused Rust coverage for Querit request shaping, response parsing, missing-key behavior, and tool registration.

Problem

OpenHuman currently supports managed search and several BYO search providers, but not Querit. Users with a Querit API key cannot configure OpenHuman to use Querit for direct web search, including site, time range, country, and language filters.

Solution

This PR adds a Querit integration that follows the official Querit POST API shape and the local querit-web-search skill behavior. The implementation reuses the existing unified search engine settings model by storing Querit credentials under search.querit with the same SearchEngineCredentials structure used by other BYO engines.

Important choices:

  • Keep Querit inside SearchConfig instead of adding a separate top-level config block.
  • Preserve existing Tauri command guards and existing search settings update response behavior.
  • Accept both Querit-native count / filters and OpenHuman-friendly aliases such as max_results, include_domains, time_range, countries, and languages.
  • Keep i18n changes scoped to adding Querit labels and fallback strings.

Submission Checklist

If a section does not apply to this change, mark the item as N/A with a one-line reason. Do not delete items.

  • Tests added or updated (happy path + at least one failure / edge case) per Testing Strategy
  • Diff coverage ≥ 80% — remote coverage workflow remains the source of truth; focused Rust tests were added and passed locally.
  • Coverage matrix updated — N/A: provider integration change, no feature row added/removed/renamed.
  • All affected feature IDs from the matrix are listed in the PR description under ## Related — N/A: no matrix feature IDs changed.
  • No new external network dependencies introduced (mock backend used per Testing Strategy) — tests use a local Axum mock for Querit execution.
  • Manual smoke checklist updated if this touches release-cut surfaces — N/A: no release smoke checklist surface changed.
  • N/A: Linked issue closed via Closes #NNN in the ## Related section — no issue provided.

Impact

Adds a new optional BYO search provider. Existing managed, Parallel, Brave, Seltz, and SearXNG paths are preserved.

Runtime impact:

  • Desktop/Tauri settings UI can select Querit and store a Querit API key.
  • Core registers Querit-backed web_search_tool and querit_search only when search.engine = "querit" and a Querit key is configured.
  • Pure Vite web mode still cannot save search settings because the existing Tauri command guard remains intact.

Security:

  • Querit API keys are stored through the existing search settings config path and included in the existing secret encryption/decryption path.
  • Search settings read API continues to expose only configured/not-configured booleans.
  • Querit upstream error bodies are not logged verbatim.

Related

  • Closes: N/A
  • Follow-up PR(s)/TODOs: N/A

AI Authored PR Metadata (required for Codex/Linear PRs)

Keep this section for AI-authored PRs. For human-only PRs, mark each field N/A.

Linear Issue

  • Key: N/A
  • URL: N/A

Commit & Branch

  • Branch: codex/querit-search
  • Commit SHA: 94bf886b347189f368b82f3a9d2dadd6669d2ea5

Validation Run

  • pnpm --filter openhuman-app format:check
  • pnpm typecheck
  • Focused tests: GGML_NATIVE=OFF cargo test --manifest-path Cargo.toml querit --lib
  • Rust fmt/check (if changed): root cargo fmt check passed via cargo fmt --manifest-path Cargo.toml --check; focused Rust tests passed.
  • N/A: Tauri fmt/check (if changed) — Tauri fmt passed; Tauri cargo check blocked locally by missing cmake and documented below.

Validation Blocked

  • command: pnpm rust:check / pre-push hook cargo check --manifest-path app/src-tauri/Cargo.toml
  • error: failed to execute command: No such file or directory (os error 2); is cmake not installed?
  • impact: Local Tauri cargo check could not complete in this environment. Querit core tests, TypeScript typecheck, formatting checks, and manual local RPC smoke validation passed.

Behavior Changes

  • Intended behavior change: Users can configure Querit as the active search engine and use Querit for web search.
  • User-visible effect: Settings > Search engine shows Querit and a Querit API key editor.

Parity Contract

  • Legacy behavior preserved: Existing Managed, Parallel, Brave, Seltz, and SearXNG search behavior remains unchanged.
  • Guard/fallback/dispatch parity checks: Querit follows the existing effective_engine() key-gated fallback pattern; without a Querit key, search falls back to Managed instead of registering unusable tools.

Duplicate / Superseded PR Handling

  • Duplicate PR(s): N/A
  • Canonical PR: N/A
  • Resolution (closed/superseded/updated): N/A

Summary by CodeRabbit

  • New Features

    • Added Querit as a selectable web search engine and UI to add/manage its API key.
  • Documentation

    • Updated environment/example and settings guidance with Querit instructions and optional env vars to enable it.
  • Localization

    • Added translations for Querit-related labels, descriptions, and placeholders across multiple languages.
  • Tests

    • UI and backend tests expanded to cover Querit configuration, persistence, and search behavior.

Review Change Stack

@MurphyZzzzz MurphyZzzzz requested a review from a team May 27, 2026 10:41
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 27, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds Querit as a new web search provider across backend (tool, config, RPC), frontend (types, UI), translations, tests, and environment documentation.

Changes

Querit Search Engine Integration

Layer / File(s) Summary
Querit Tool Implementation
src/openhuman/integrations/querit.rs
QueritSearchTool implements the Tool trait, including request/response models, filter normalization, response decoding (wrapped and direct shapes), plain and markdown rendering, HTTP error handling, and unit/e2e tests.
Configuration Schema & Engine Selection
src/openhuman/config/schema/tools.rs, src/openhuman/config/schema/mod.rs
Adds SEARCH_ENGINE_QUERIT, a querit credentials block in SearchConfig, SearchEngine::Querit variant, default initialization, and effective_engine logic selecting Querit only when an API key is present (with unit test).
Config Operations & Secrets / Env Overlay
src/openhuman/config/ops.rs, src/openhuman/config/schema/load.rs
Extends SearchSettingsPatch with querit_api_key; updates apply_search_settings and get_search_settings to persist/reflect Querit configuration (empty string clears); integrates querit API key into encrypt/decrypt flows and adds OPENHUMAN_QUERIT_API_KEY/QUERIT_API_KEY env overlay.
Config Re-exports & RPC Schema
src/openhuman/config/mod.rs, src/openhuman/config/schemas.rs
Re-exports SEARCH_ENGINE_QUERIT; adds querit_api_key to RPC payloads and docs; extends update_search_settings schema and wires querit_api_key into the update handler.
Tool Registry & RPC Handlers
src/openhuman/integrations/mod.rs, src/openhuman/tools/ops.rs, src/openhuman/tools/schemas.rs
Exports QueritSearchTool, registers Querit in the tool registry (web_search_tool + querit_search), adds tools_querit_search RPC controller, handler, schema, and tests; updates tool registration tests.
Frontend Types & UI
app/src/utils/tauriCommands/config.ts, app/src/components/settings/panels/SearchPanel.tsx
Adds 'querit' to SearchEngineId, querit_api_key to SearchSettingsUpdate, querit_configured to SearchSettings; extends SearchPanel with Querit engine option, KeyEditor UI, local state, and persistence logic.
Internationalization Support
app/src/lib/i18n/chunks/*, app/src/lib/i18n/en.ts, app/src/lib/i18n/zh-CN.ts
Adds Querit translation strings (label, description, key label, placeholder) and updates local-managed-unavailable messages across language chunks.
Environment Configuration
.env.example
Documents Querit configuration and env vars QUERIT_API_KEY / OPENHUMAN_QUERIT_API_KEY and engine selection guidance.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • tinyhumansai/openhuman#2516: Both PRs extend the unified search-engine selector/engine-driven tool registration in the backend; #2516 added the brave engine while this PR adds querit.
  • tinyhumansai/openhuman#2378: Both PRs touch i18n chunks (e.g., German) and localization wiring used by the search settings UI.

Suggested reviewers

  • graycyrus

"🐰 I found a tiny key tonight,
Querit hops into the searchlight.
From Rust to UI the strings align,
Keys saved, docs updated—what a find!
Hop—new results take joyous flight."

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately and concisely describes the main change: adding a new Querit search provider to the system, which is the primary purpose of this pull request.
Docstring Coverage ✅ Passed Docstring coverage is 97.96% 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.

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


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.

@coderabbitai coderabbitai Bot added feature Net-new user-facing capability or product behavior. rust-core Core Rust runtime in src/: CLI, core_server, shared infrastructure. labels May 27, 2026
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: 3

🧹 Nitpick comments (2)
src/openhuman/tools/schemas.rs (1)

678-682: ⚡ Quick win

Add an explicit error log before returning Querit execution failures.

tool.execute(args) failures are returned to caller, but this branch doesn’t emit a corresponding diagnostics log event with the existing [rpc][tools.querit_search] prefix.

Proposed patch
-        let result = tool
-            .execute(args)
-            .await
-            .map_err(|e| format!("querit search failed: {e:#}"))?;
+        let result = tool.execute(args).await.map_err(|e| {
+            tracing::warn!(
+                query_len = query.chars().count(),
+                max_results,
+                error = %e,
+                "[rpc][tools.querit_search] failed"
+            );
+            format!("querit search failed: {e:#}")
+        })?;

As per coding guidelines, "Log entry/exit, branches, external calls, retries/timeouts, state transitions, and errors with verbose diagnostics using stable grep-friendly prefixes and correlation fields".

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/openhuman/tools/schemas.rs` around lines 678 - 682, The map_err on
tool.execute(args) should log the error with the stable grep-friendly prefix
before returning; capture the error from tool.execute(args) in the closure, emit
an error diagnostics log event using the existing logging facility with the
prefix "[rpc][tools.querit_search]" (include correlation/context fields used in
this module), then return the formatted error string as before — locate the
map_err around tool.execute(args) and replace the inline map_err with a closure
that logs the error and then produces the same formatted error.
app/src/lib/i18n/en.ts (1)

639-639: 💤 Low value

Querit placeholder could show an API key pattern.

The Querit placeholder is generic ('Querit API key') while Parallel and Brave show actual key prefixes (pk_..., BSA...). If Querit keys follow a recognizable pattern, showing it here would improve UX consistency.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@app/src/lib/i18n/en.ts` at line 639, Update the translation entry for
'settings.search.placeholderQuerit' so the placeholder shows the Querit API key
prefix/pattern (e.g., change from 'Querit API key' to something like 'qr_...' or
the actual Querit prefix if you have it) to match the UX of other providers;
update the value in en.ts and mirror the change in any other locale files where
'settings.search.placeholderQuerit' appears.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/openhuman/config/ops.rs`:
- Around line 410-412: The docstring for SearchSettingsPatch.engine is
inaccurate: runtime validation in apply_search_settings rejects empty or unknown
engine values rather than falling back to "managed"; update the comment on the
pub engine: Option<String> field (SearchSettingsPatch.engine) to state that
empty or unrecognized values are rejected by apply_search_settings and must be
one of the allowed engines ("managed" | "parallel" | "brave" | "querit"), so
documentation matches runtime behavior.

In `@src/openhuman/config/schema/load.rs`:
- Around line 1481-1485: The Querit API key loaded into search.querit.api_key is
missing from the secret encryption/decryption paths; update both
decrypt_config_secrets and encrypt_config_secrets to include the same config
path that targets search.querit.api_key so it is processed when secrets.encrypt
is true (i.e., add the search.querit.api_key entry to whatever list/paths those
functions iterate over or the match arms that handle secret fields).

In `@src/openhuman/integrations/querit.rs`:
- Around line 481-486: The code logs raw upstream response body via body_text →
detail (via utf8_safe_prefix_at_byte_boundary) in the tracing::warn call; change
this to never log verbatim body content — instead sanitize or redact sensitive
data before logging: capture the response length and status, compute a safe
summary (e.g., fixed placeholder like "<redacted>" or a digest/hex of the first
N bytes) and log that along with status; update the code around
resp.text().await.unwrap_or_default(), utf8_safe_prefix_at_byte_boundary, and
the tracing::warn call to use the sanitized summary rather than the raw detail.

---

Nitpick comments:
In `@app/src/lib/i18n/en.ts`:
- Line 639: Update the translation entry for 'settings.search.placeholderQuerit'
so the placeholder shows the Querit API key prefix/pattern (e.g., change from
'Querit API key' to something like 'qr_...' or the actual Querit prefix if you
have it) to match the UX of other providers; update the value in en.ts and
mirror the change in any other locale files where
'settings.search.placeholderQuerit' appears.

In `@src/openhuman/tools/schemas.rs`:
- Around line 678-682: The map_err on tool.execute(args) should log the error
with the stable grep-friendly prefix before returning; capture the error from
tool.execute(args) in the closure, emit an error diagnostics log event using the
existing logging facility with the prefix "[rpc][tools.querit_search]" (include
correlation/context fields used in this module), then return the formatted error
string as before — locate the map_err around tool.execute(args) and replace the
inline map_err with a closure that logs the error and then produces the same
formatted error.
🪄 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: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 007c883b-6c12-467c-8976-26395abb6d85

📥 Commits

Reviewing files that changed from the base of the PR and between 996e3ad and fd09dfc.

📒 Files selected for processing (29)
  • .env.example
  • app/src/components/settings/panels/SearchPanel.tsx
  • app/src/lib/i18n/chunks/ar-1.ts
  • app/src/lib/i18n/chunks/bn-1.ts
  • app/src/lib/i18n/chunks/de-1.ts
  • app/src/lib/i18n/chunks/en-1.ts
  • app/src/lib/i18n/chunks/es-1.ts
  • app/src/lib/i18n/chunks/fr-1.ts
  • app/src/lib/i18n/chunks/hi-1.ts
  • app/src/lib/i18n/chunks/id-1.ts
  • app/src/lib/i18n/chunks/it-1.ts
  • app/src/lib/i18n/chunks/ko-1.ts
  • app/src/lib/i18n/chunks/pt-1.ts
  • app/src/lib/i18n/chunks/ru-1.ts
  • app/src/lib/i18n/chunks/zh-CN-1.ts
  • app/src/lib/i18n/en.ts
  • app/src/lib/i18n/zh-CN.ts
  • app/src/utils/tauriCommands/config.ts
  • src/openhuman/config/mod.rs
  • src/openhuman/config/ops.rs
  • src/openhuman/config/schema/load.rs
  • src/openhuman/config/schema/mod.rs
  • src/openhuman/config/schema/tools.rs
  • src/openhuman/config/schemas.rs
  • src/openhuman/integrations/mod.rs
  • src/openhuman/integrations/querit.rs
  • src/openhuman/tools/ops.rs
  • src/openhuman/tools/ops_tests.rs
  • src/openhuman/tools/schemas.rs

Comment thread src/openhuman/config/ops.rs Outdated
Comment thread src/openhuman/config/schema/load.rs
Comment thread src/openhuman/integrations/querit.rs
coderabbitai[bot]
coderabbitai Bot previously approved these changes May 27, 2026
Copy link
Copy Markdown
Contributor

@graycyrus graycyrus left a comment

Choose a reason for hiding this comment

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

Summary

This PR adds Querit as a new web search engine provider. The integration is well-structured and follows existing patterns, but two critical security issues need fixing:

  1. Missing secret encryption for Querit API key — When secrets.encrypt = true, the Querit key is loaded from env but NOT included in encrypt/decrypt paths, leaving it in plaintext.
  2. Error responses can leak sensitive data — Querit error bodies are included in error messages. If Querit echoes queries or context, they'll be exposed.

The docs issue CodeRabbit flagged has been corrected in this PR. Once the two security issues are fixed, this is ready to go.

CI Status

PR Submission Checklist is failing. Most other checks pass or are pending.

Comment thread src/openhuman/config/schema/load.rs
Comment thread src/openhuman/integrations/querit.rs
@coderabbitai coderabbitai Bot added the agent Built-in agents, prompts, orchestration, and agent runtime in src/openhuman/agent/. label May 27, 2026
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: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@app/src/components/settings/panels/SearchPanel.test.tsx`:
- Around line 58-62: The test helper keyEditor should stop using DOM class-based
scoping (closest('.rounded-xl')); update keyEditor to locate the control
container via accessible queries instead (e.g., find the element by
role/aria-label/aria-labelledby or a grouping with an accessible name that
matches the label) and then call within(...) on that accessible container;
modify the keyEditor function to use screen.getByRole/getByLabelText/getByText
combined with role-based ancestor selection (accessible name) instead of
closest('.rounded-xl') so tests rely on behavior/semantics not CSS.
🪄 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: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 82980c57-0f1a-461f-ab09-c329c8c8262e

📥 Commits

Reviewing files that changed from the base of the PR and between aac159a and 3fdb3b4.

📒 Files selected for processing (26)
  • .env.example
  • app/src/components/settings/panels/SearchPanel.test.tsx
  • app/src/components/settings/panels/SearchPanel.tsx
  • app/src/lib/i18n/chunks/ar-1.ts
  • app/src/lib/i18n/chunks/bn-1.ts
  • app/src/lib/i18n/chunks/de-1.ts
  • app/src/lib/i18n/chunks/en-1.ts
  • app/src/lib/i18n/chunks/es-1.ts
  • app/src/lib/i18n/chunks/fr-1.ts
  • app/src/lib/i18n/chunks/hi-1.ts
  • app/src/lib/i18n/chunks/id-1.ts
  • app/src/lib/i18n/chunks/it-1.ts
  • app/src/lib/i18n/chunks/ko-1.ts
  • app/src/lib/i18n/chunks/pt-1.ts
  • app/src/lib/i18n/chunks/ru-1.ts
  • app/src/lib/i18n/chunks/zh-CN-1.ts
  • app/src/lib/i18n/en.ts
  • app/src/utils/tauriCommands/config.ts
  • src/openhuman/config/mod.rs
  • src/openhuman/config/ops.rs
  • src/openhuman/config/schema/load.rs
  • src/openhuman/config/schema/tools.rs
  • src/openhuman/config/schemas.rs
  • src/openhuman/integrations/querit.rs
  • src/openhuman/tools/ops.rs
  • src/openhuman/tools/ops_tests.rs
✅ Files skipped from review due to trivial changes (10)
  • src/openhuman/config/mod.rs
  • app/src/lib/i18n/chunks/fr-1.ts
  • app/src/lib/i18n/chunks/zh-CN-1.ts
  • app/src/lib/i18n/chunks/pt-1.ts
  • app/src/lib/i18n/chunks/it-1.ts
  • app/src/lib/i18n/chunks/bn-1.ts
  • .env.example
  • app/src/lib/i18n/chunks/ar-1.ts
  • app/src/lib/i18n/chunks/en-1.ts
  • app/src/lib/i18n/en.ts
🚧 Files skipped from review as they are similar to previous changes (14)
  • app/src/lib/i18n/chunks/ru-1.ts
  • app/src/lib/i18n/chunks/hi-1.ts
  • app/src/utils/tauriCommands/config.ts
  • app/src/lib/i18n/chunks/es-1.ts
  • src/openhuman/tools/ops_tests.rs
  • app/src/lib/i18n/chunks/id-1.ts
  • src/openhuman/config/schema/load.rs
  • app/src/components/settings/panels/SearchPanel.tsx
  • src/openhuman/config/schemas.rs
  • app/src/lib/i18n/chunks/ko-1.ts
  • app/src/lib/i18n/chunks/de-1.ts
  • src/openhuman/config/ops.rs
  • src/openhuman/tools/ops.rs
  • src/openhuman/config/schema/tools.rs

Comment thread app/src/components/settings/panels/SearchPanel.test.tsx Outdated
@coderabbitai coderabbitai Bot added the working A PR that is being worked on by the team. label May 27, 2026
coderabbitai[bot]
coderabbitai Bot previously approved these changes May 27, 2026
@MurphyZzzzz MurphyZzzzz requested a review from graycyrus May 27, 2026 14:30
@graycyrus
Copy link
Copy Markdown
Contributor

@MurphyZzzzz unresolved review feedback — please address before we review.

@graycyrus
Copy link
Copy Markdown
Contributor

Unresolved review feedback from coderabbitai[bot] — please address before we review.

graycyrus
graycyrus previously approved these changes May 27, 2026
Copy link
Copy Markdown
Contributor

@graycyrus graycyrus left a comment

Choose a reason for hiding this comment

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

All prior security issues fixed:

  1. Querit API key now included in both decrypt_config_secrets and encrypt_config_secrets paths — properly encrypted when secrets.encrypt=true.
  2. Error response bodies no longer leaked in error messages — now a generic status-only message, plus test coverage verifying responses don't expose sensitive data.

CI is 100% green across all checks (build, coverage, E2E, tests). Code quality looks solid.

Ready to merge.

@oxoxDev oxoxDev assigned oxoxDev and unassigned oxoxDev May 28, 2026
@oxoxDev oxoxDev self-requested a review May 28, 2026 18:07
oxoxDev
oxoxDev previously approved these changes May 28, 2026
Copy link
Copy Markdown
Contributor

@oxoxDev oxoxDev left a comment

Choose a reason for hiding this comment

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

LGTM as 2nd maintainer pass. @graycyrus's 2 security blockers (encrypt/decrypt path inclusion + HTTP body leak) are both verified fixed; CodeRabbit iterated to APPROVED; CI all green; tests + precedent solid.

Verified independently

  • Encrypt/decryptsearch.querit.api_key included in both decrypt_config_secrets (load.rs:461-465) and encrypt_config_secrets (load.rs:574-578), mirroring parallel/brave sibling pattern. Plaintext keys persisted under secrets.encrypt=true now encrypted as enc2:.
  • HTTP body leak — non-2xx path bails with status only (querit.rs:487); body only used for body_len in tracing::warn!. Negative test test_execute_non_success_status_does_not_expose_response_body asserts a deliberately-sensitive mock body never reaches the error message.
  • Query log redactiontracing::debug!(query_len = query.chars().count(), max_results, ...) logs length only, never query content. Matches the redact-paths/IDs hygiene applied across the codebase.
  • Module registrationintegrations/mod.rs adds pub mod querit; + re-exports QueritSearchTool. Standard.
  • Tool registration — gated on SearchEngine::Querit (tools/ops.rs:452-470), registers BOTH web_search_tool AND querit_search. Matches sibling-engine pattern.
  • Engine enum extensionapply_search_settings validates "managed" | "parallel" | "brave" | "querit" (ops.rs:1015), rejects unknowns. Public read-API exposes querit_configured: bool only, never the key.
  • max_results.clamp(1, 20) — defensive.
  • 12 unit tests in querit.rs covering request shaping, response parsing, missing-key behavior, error-body redaction.
  • i18n — 13 locales touched (en + 12 chunk-1 files), mechanical placeholder-copy per CLAUDE.md rules.
  • PR template adherence — body has all 6 required headings; N/A items correctly use - [x] N/A: reason (avoids the trap from PR #2851).

Residual nit (NOT blocking, just flagging for awareness)

querit.rs:495-498 app-level error path bails with search_resp.error_msg interpolated. Different code path from the HTTP-non-2xx fix. If Querit's error_msg ever echoes user query/context back (typical of validation errors), it'd leak. The HTTP path is safe; the app-level path inherits Querit's discipline. Optional follow-up: add a sibling negative test feeding a mock query-echoing error_msg, or replace the interpolation with a generic string. Either fine — depends on Querit's actual error_msg behavior.

Ready to ship.

@oxoxDev oxoxDev self-requested a review May 28, 2026 18:30
@MurphyZzzzz MurphyZzzzz dismissed stale reviews from oxoxDev and graycyrus via b4ecaea May 29, 2026 02:25
@MurphyZzzzz
Copy link
Copy Markdown
Contributor Author

I've resolved the merge conflicts and pushed the updated branch. Could you please take another look when you have a chance? @graycyrus @oxoxDev

coderabbitai[bot]
coderabbitai Bot previously approved these changes May 29, 2026
@graycyrus
Copy link
Copy Markdown
Contributor

Code looks great — both security issues are fixed and fully verified by me and oxoxDev. However, the Rust Core Coverage job is failing. That needs to be resolved before I can approve.

Let me know what the coverage issue is and we can get this across the line!

@MurphyZzzzz
Copy link
Copy Markdown
Contributor Author

Code looks great — both security issues are fixed and fully verified by me and oxoxDev. However, the Rust Core Coverage job is failing. That needs to be resolved before I can approve.

Let me know what the coverage issue is and we can get this across the line!

This looks like an unrelated flaky Rust test in the coverage job. I reproduced the focused test locally and it passed. Could someone with Actions permissions please re-run the failed job? @graycyrus

@MurphyZzzzz
Copy link
Copy Markdown
Contributor Author

Code looks great — both security issues are fixed and fully verified by me and oxoxDev. However, the Rust Core Coverage job is failing. That needs to be resolved before I can approve.
Let me know what the coverage issue is and we can get this across the line!

This looks like an unrelated flaky Rust test in the coverage job. I reproduced the focused test locally and it passed. Could someone with Actions permissions please re-run the failed job? @graycyrus

The failing coverage job is not failing because of diff coverage or the Querit changes directly. The command cargo llvm-cov -p openhuman --lcov --output-path lcov-core.info runs the Rust test suite before producing LCOV, and one unrelated Rust unit test failed during that phase:

openhuman::memory_tools::tools::put::tests::execute_success_path_persists_rule_in_isolated_workspace

Failure path:

  • The test calls MemoryToolsPutTool::execute(...) with tool_name = "bash".
  • MemoryToolsPutTool creates a ToolMemoryRule via ToolMemoryRule::new(...).
  • ToolMemoryRule::new(...) generates a random UUID v4 string for rule.id.
  • ToolMemoryStore::put_rule(...) stores the rule under:
    • namespace: tool-bash
    • key: rule/<uuid-v4>
  • The memory document write path now rejects namespace/key values when safety::pii::has_likely_pii(...) returns true.
  • In this CI run, the randomly generated UUID-derived key appears to have matched the PII detector, so the write failed with:
    document namespace/key cannot contain personal identifiers

Relevant code path:

  • src/openhuman/memory_tools/tools/put.rs
  • src/openhuman/memory_tools/types.rs
    • ToolMemoryRule::generate_id() currently uses uuid::Uuid::new_v4().to_string()
  • src/openhuman/memory_tools/store.rs
    • stores with ToolMemoryRule::storage_key(&rule.id)
  • src/openhuman/memory_store/unified/documents.rs
    • rejects PII-like namespace/key values before persisting

I pulled the latest PR branch locally and ran the focused test:

GGML_NATIVE=OFF cargo test --manifest-path Cargo.toml execute_success_path_persists_rule_in_isolated_workspace --lib -- --nocapture

It passed locally, which supports that this is a randomness-triggered flake rather than a deterministic Querit regression.

Copy link
Copy Markdown
Contributor

@graycyrus graycyrus left a comment

Choose a reason for hiding this comment

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

All prior security issues resolved + latest commit adds even more redaction. Code is excellent.

What's fixed since last review:

  • New commit (18c36f3) further hardens error redaction: application-level Querit errors now only expose error_code, not error_msg (with a comprehensive test to prevent regression).
  • All HTTP and application-level error paths now safe from data exposure.
  • Secret encryption/decryption paths all correct.

Status:

  • CodeRabbit: APPROVED ✓
  • Code quality: Excellent ✓
  • Security audit: Clean ✓
  • All review threads: Resolved ✓
  • Blocker: Many CI checks still PENDING (not failed, just not complete yet).

I'll APPROVE as soon as CI completes. Code is ready—just waiting on the test suite to finish running.

@MurphyZzzzz
Copy link
Copy Markdown
Contributor Author

I don't have permission to re-run the upstream GitHub Actions job.
This failure looks like CI runner disk exhaustion (No space left on device) rather than a code failure.
Could a maintainer please re-run the failed coverage job?

@senamakel
Copy link
Copy Markdown
Member

I don't have permission to re-run the upstream GitHub Actions job. This failure looks like CI runner disk exhaustion (No space left on device) rather than a code failure. Could a maintainer please re-run the failed coverage job?

yes. i'll watch this and if it passes, will merge. thanks brother

Copy link
Copy Markdown
Contributor

@graycyrus graycyrus left a comment

Choose a reason for hiding this comment

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

looks good! code is excellent, all prior security fixes in place, and CodeRabbit already approved. CI still has a few jobs pending (core smoke test, Rust coverage, E2E, Windows tests), but no failures so far.

once those complete green, this is ready to roll. nice work on the Querit integration—the error redaction hardening and secret encryption handling are solid.

@senamakel senamakel merged commit 5a5cd43 into tinyhumansai:main May 29, 2026
30 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

agent Built-in agents, prompts, orchestration, and agent runtime in src/openhuman/agent/. feature Net-new user-facing capability or product behavior. rust-core Core Rust runtime in src/: CLI, core_server, shared infrastructure. working A PR that is being worked on by the team.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants