Your browser sucks, JavaScript disabled! Gunnar's console needs JavaScript and WebAssembly. Git over SSH on port 2222 does not.

nordisk/znippy

plugins/native/znippy-plugin-git/tests/twin_runtime_limits.rs

//! **The runtime doors a twin turns down, with NO environment set.**
//!
//! gunnar's twin learns it is a twin at RUNTIME (`Bootstrap.BecomeTwin` over gRPC), long after
//! its process started, and it cannot answer by setting a variable: edition 2024 makes
//! `set_var` unsafe and gunnar forbids `unsafe`. Until these setters existed the only place
//! the answer fit was the kernel command line — which made a twin a differently-installed box,
//! and the owner ruling of 2026-09-21 is that a twin is installed from the SAME medium with no
//! per-box parameter.
//!
//! So each door is asserted here twice: the setter is honoured, and the value reaches the
//! thing that spends the memory — [`ResolveLimits::for_indexer`], which is the struct
//! `GitStore`'s absorb hands `resolve_streaming` (`git_ops.rs`), and the policy/budget a store
//! opens with.
//!
//! This binary sets NO environment variable, on purpose: `ZNIPPY_GIT_RESOLVE_WORKERS` and
//! `ZNIPPY_GIT_RESOLVE_LOOKAHEAD_BYTES` are read once per PROCESS, so a test that set one
//! would decide the answer for every other test beside it. The other half of the contract —
//! an explicit variable still wins over a code-set default — is a separate binary,
//! `twin_runtime_limits_env_wins.rs`, for exactly that reason.

use std::sync::atomic::AtomicBool;

use znippy_plugin_git::exploded_arrow::ExplodePolicy;
use znippy_plugin_git::resolve::{DEFAULT_LOOKAHEAD_BYTES, ResolveLimits};
use znippy_plugin_git::{
    explode_default, set_explode_budget_default, set_explode_default,
    set_resolve_lookahead_default, set_resolve_workers_default,
};

/// The twin's measured numbers (gunnar `twin_snapshot_memory.rs`, 2026-09-15).
const TWIN_WORKERS: usize = 2;
const TWIN_LOOKAHEAD: u64 = 16 << 20;
const TWIN_EXPLODE_BUDGET: u64 = 16 << 20;

/// Every test in this binary shares one process, and the resolver's environment doors answer
/// once per process — so the defaults are set ONCE, before anything reads them, and every test
/// below asserts against that one setting rather than racing to install its own.
fn become_a_twin() {
    static ONCE: std::sync::Once = std::sync::Once::new();
    ONCE.call_once(|| {
        set_explode_default(ExplodePolicy::Off);
        set_explode_budget_default(Some(TWIN_EXPLODE_BUDGET));
        set_resolve_workers_default(TWIN_WORKERS);
        set_resolve_lookahead_default(TWIN_LOOKAHEAD);
    });
}

/// ★ **The resolver is two workers wide and holds 16 MiB, because code said so.**
///
/// Asserted on [`ResolveLimits::for_indexer`] and not on `workers_from_env`, because
/// `for_indexer` is what `GitStore`'s absorb actually builds (`git_ops.rs`, `resolve_streaming`
/// takes it) — one worker per core, each inflating a whole blob, is the +133 MiB the twin
/// could not afford.
///
/// Seen RED by neutralising `set_resolve_workers_default` (make its body `let _ = workers;`):
/// `workers` comes back as this box's core count, 16, and `lookahead_bytes` as 32 MiB.
#[test]
fn the_resolver_takes_its_width_and_lookahead_from_the_setters() {
    become_a_twin();
    let cancel = AtomicBool::new(false);
    let progress = znippy_plugin_git::progress::IndexProgress::new("twin-runtime-limits");
    let dog = std::sync::Arc::new(znippy_plugin_git::memguard::MemWatchdog::from_env());
    let spill = || 0u64;
    let limits = ResolveLimits::for_indexer("twin", &cancel, &progress, dog, &spill);

    assert_eq!(
        limits.workers, TWIN_WORKERS,
        "the resolver width the indexer will run at is not what set_resolve_workers_default said"
    );
    assert_eq!(
        limits.lookahead_bytes, TWIN_LOOKAHEAD,
        "the bytes the workers may run ahead by is not what set_resolve_lookahead_default said"
    );
    assert_ne!(
        limits.lookahead_bytes, DEFAULT_LOOKAHEAD_BYTES,
        "the assertion above would pass on the shipped default; it must not be able to"
    );
}

/// ★ **A store opened now explodes nothing.**
///
/// [`ExplodePolicy::from_env`] is what `GitStore::open` calls once per store open, so this is
/// the value every repository the twin applies will carry.
///
/// Seen RED by neutralising `set_explode_default`: `Commits`, the shipped default.
#[test]
fn a_store_opened_after_the_setter_carries_the_policy_it_set() {
    become_a_twin();
    assert_eq!(explode_default(), ExplodePolicy::Off);
    assert_eq!(
        ExplodePolicy::from_env().unwrap(),
        ExplodePolicy::Off,
        "the policy a store opens with is not what set_explode_default said"
    );
}

/// The two budget guards move one process-wide atomic between them, and `cargo test` runs them
/// on two threads. One lock, so neither reads the other's half-step.
static BUDGET_LOCK: std::sync::Mutex<()> = std::sync::Mutex::new(());

/// ★ **And its exploded pool is capped at 16 MiB**, not at a tenth of the filesystem.
///
/// [`znippy_plugin_git::exploded_cache::budget_from_env`] takes the store's directory because
/// its default is derived from that filesystem's size — the assertion is that the setter beats
/// that derivation, which on this box would hand back gigabytes.
///
/// Seen RED by neutralising `set_explode_budget_default`: the filesystem-derived figure.
#[test]
fn the_explode_budget_comes_from_the_setter_and_not_from_the_filesystem() {
    become_a_twin();
    let _g = BUDGET_LOCK.lock().unwrap_or_else(|e| e.into_inner());
    let dir = std::env::temp_dir();
    assert_eq!(
        znippy_plugin_git::exploded_cache::budget_from_env(&dir).unwrap(),
        TWIN_EXPLODE_BUDGET,
        "the budget a store opens with is not what set_explode_budget_default said"
    );
    assert_ne!(
        znippy_plugin_git::exploded_cache::default_budget(&dir),
        TWIN_EXPLODE_BUDGET,
        "this filesystem's derived budget happens to equal the twin's figure, so the assertion \
         above proves nothing here — pick another number"
    );
}

/// ★ **`None` gives the filesystem back**, so the doors are reversible and a test that sets
/// one is not a process that can never be a primary again.
#[test]
fn clearing_the_explode_budget_default_restores_the_filesystem_derived_one() {
    become_a_twin();
    let _g = BUDGET_LOCK.lock().unwrap_or_else(|e| e.into_inner());
    let dir = std::env::temp_dir();
    set_explode_budget_default(None);
    let back = znippy_plugin_git::exploded_cache::budget_from_env(&dir).unwrap();
    // Put the twin's figure back before any other test in this binary looks.
    set_explode_budget_default(Some(TWIN_EXPLODE_BUDGET));
    assert_eq!(back, znippy_plugin_git::exploded_cache::default_budget(&dir));
}