ecoseek

Security posture

EcoSeek is pre-alpha. This document describes the current security posture — what is implemented, what is tested, and what remains open. If a rule here conflicts with code in the repository, the rule wins and the code is a bug.

Last updated: 2026-05-18, after P0 stabilization.

For the complete threat model with 24 scenarios, 12 assets, 6 threat actor profiles, and risk matrix, see the full-stack threat model in the knowledgebase.

No secrets in the repository

BYOK key rules

For users who supply their own keys (e.g. DeepSeek):

  1. Custody. Keys are stored locally on the user’s machine using Fernet encryption (AES-128-CBC + HMAC-SHA256). The keystore prefers the OS keychain (macOS Keychain, Linux Secret Service, Windows Credential Manager) and falls back to an encrypted file at ~/.config/ecoseek/keys.json. Keys are never committed, logged, or transmitted to EcoSeek infrastructure.
  2. Fail-closed. If the cryptography library is not installed, the keystore raises KeystoreCryptoUnavailable with an actionable error message. It never silently downgrades to base64 or plaintext storage.
  3. Scope. A key is bound to the local keystore instance. It is not synced, backed up to a third party, or transmitted to any service other than the provider it targets.
  4. Lifecycle. Keys can be managed via CLI: python -m sources.keystore {set|get|list|delete}. Revocation is immediate.
  5. Visibility. The keystore can list which keys are stored without exposing key material.
  6. Lab-managed exception. In lab-managed mode, the lab’s operator holds the keys on behalf of users. Users still never see raw keys.

Implementation: agenticSeek PR #23, agenticSeek PR #33. 41 keystore tests.

AgenticPlug auth model

GitHub proves who the user is. AgenticPlug decides what the user can do.

Dual-layer authentication

  1. Client obtains a GitHub access token via Device Flow.
  2. Client exchanges the GitHub token for an opaque AgenticPlug session ID.
  3. AgenticPlug verifies the GitHub token against GitHub’s API, maps the identity to a role (admin, operator, read_only), and issues a 128-bit crypto-random session ID.
  4. All subsequent requests use only the session ID. Raw GitHub tokens are rejected as bearer tokens.

Session security

Role-based access control

Approval workflow

Six capabilities are approval-gated: hpc.submit, hpc.cancel, hpc.write, hpc.delete, hpc.credential, hpc.systemd. The authorizer runs before the approval gate — read_only users get forbidden before any approval request is created. SHA-256 request binding prevents approving one action and executing another. Approvals expire after a configurable TTL (default 15 min).

Implementation: AgenticPlug PRs #49, #57, #58, #66, #67, #68, #74. 600+ tests.

Risky actions are gated

The following are considered risky and must go through the gateway:

The gateway makes an explicit, auditable decision based on the caller, the requested action, and the active policy. “Allow all” is not a valid default — the gateway fails closed when no policy matches.

Client-side security

Path traversal protection

Tool.save_block() resolves all paths against the agent’s work_dir using os.path.realpath() + os.path.commonpath(). Blocked: ../ traversal, absolute paths outside work_dir, symlink escapes. Re-validates after directory creation to close TOCTOU windows. Error messages omit host paths.

Implementation: agenticSeek PR #33. 12 jail tests.

Unsafe command filtering

safety.py maintains allowlists/blocklists for shell commands. P0 fix corrected a missing comma that concatenated "route" and "--force" into a single entry, bypassing both filters.

Implementation: agenticSeek PR #33. 11 safety tests.

Known client gaps

HPC log containment

Three-layer defense for remote file access:

  1. Input validation: 8 independent checks (length cap, null byte rejection, percent-decoding, segment-wise .. check, absolute path, POSIX allowlist, path.resolve, local realpath).
  2. Remote symlink resolution: readlink -f over SSH before tail catches remote symlinks escaping allowed roots. Fails closed on SSH failure, timeout, or non-POSIX output.
  3. Shell safety: All SSH commands use execFileSync with argument arrays, not string concatenation.

HPC_ALLOWED_LOG_PATHS validated at startup; invalid entries (including /) prevent the connector from starting.

Implementation: AgenticPlug PRs #69, #74. 29 symlink tests + 86 HPC tests.

Threat model summary

Layer Threats Status
Client API key theft, raw token misuse, sandbox escape Partial — keystore implemented, sandbox not fully hardened
Gateway Unauth access, session hijack, role escalation, scope bypass, approval bypass, replay Implemented and tested (600+ tests)
Compute Path traversal, job injection, token leak, SSH credential exposure Implemented with defense in depth
Infrastructure Supply chain, GitHub OAuth, workstation compromise, SQLite corruption Minimal deps, WAL mode, process controls
Human Secrets in git, tokens in chat, misconfigured allowlists Process controls, startup validation, TruffleHog

For the complete catalog with mitigations, residual risk, and recommendations, see the full-stack threat model.

Reporting

EcoSeek does not yet have a dedicated public security contact. Until one is published here, report suspected issues by opening a private issue in the relevant repository, or contacting the maintainers directly through the channel they used to invite you to the project.