fix: 6 bugs found during fresh-eyes code review
1. cache: record diagnostic miss before early-return on modified()/duration_since() failure
2. dump-state: resolve all cache_dir template vars ({cache_version}, {config_hash})
3. config: remove dead breakpoint_hysteresis field from GlobalConfig (breakpoints.hysteresis is used)
4. config: align Rust Default cache_dir with defaults.json template
5. vcs: apply branch truncation in render_stale_cache (--no-shell path)
6. vcs: fix jj prefetch retry on already-failed command (flatten→unwrap_or_else)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -229,6 +229,7 @@ fn main() {
|
|||||||
vcs_type,
|
vcs_type,
|
||||||
project_dir,
|
project_dir,
|
||||||
&session,
|
&session,
|
||||||
|
&config_hash,
|
||||||
&ctx,
|
&ctx,
|
||||||
);
|
);
|
||||||
return;
|
return;
|
||||||
@@ -404,6 +405,7 @@ fn dump_state_output(
|
|||||||
vcs: section::VcsType,
|
vcs: section::VcsType,
|
||||||
project_dir: &str,
|
project_dir: &str,
|
||||||
session_id: &str,
|
session_id: &str,
|
||||||
|
config_hash: &str,
|
||||||
ctx: &RenderContext,
|
ctx: &RenderContext,
|
||||||
) {
|
) {
|
||||||
// Render all sections with per-section timing
|
// Render all sections with per-section timing
|
||||||
@@ -468,7 +470,10 @@ fn dump_state_output(
|
|||||||
"cache": cache_diags,
|
"cache": cache_diags,
|
||||||
"paths": {
|
"paths": {
|
||||||
"project_dir": project_dir,
|
"project_dir": project_dir,
|
||||||
"cache_dir": config.global.cache_dir.replace("{session_id}", session_id),
|
"cache_dir": config.global.cache_dir
|
||||||
|
.replace("{session_id}", session_id)
|
||||||
|
.replace("{cache_version}", &config.global.cache_version.to_string())
|
||||||
|
.replace("{config_hash}", config_hash),
|
||||||
},
|
},
|
||||||
"session_id": session_id,
|
"session_id": session_id,
|
||||||
});
|
});
|
||||||
|
|||||||
16
src/cache.rs
16
src/cache.rs
@@ -95,8 +95,20 @@ impl Cache {
|
|||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
let modified = meta.modified().ok()?;
|
let modified = match meta.modified().ok() {
|
||||||
let age = SystemTime::now().duration_since(modified).ok()?;
|
Some(m) => m,
|
||||||
|
None => {
|
||||||
|
self.record_diag(key, false, None);
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
let age = match SystemTime::now().duration_since(modified).ok() {
|
||||||
|
Some(a) => a,
|
||||||
|
None => {
|
||||||
|
self.record_diag(key, false, None);
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
};
|
||||||
let age_ms = age.as_millis() as u64;
|
let age_ms = age.as_millis() as u64;
|
||||||
let effective_ttl = self.jittered_ttl(key, ttl);
|
let effective_ttl = self.jittered_ttl(key, ttl);
|
||||||
if age < effective_ttl {
|
if age < effective_ttl {
|
||||||
|
|||||||
@@ -69,7 +69,6 @@ pub struct GlobalConfig {
|
|||||||
pub shell_env: HashMap<String, String>,
|
pub shell_env: HashMap<String, String>,
|
||||||
pub cache_version: u32,
|
pub cache_version: u32,
|
||||||
pub drop_strategy: String,
|
pub drop_strategy: String,
|
||||||
pub breakpoint_hysteresis: u16,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for GlobalConfig {
|
impl Default for GlobalConfig {
|
||||||
@@ -80,7 +79,7 @@ impl Default for GlobalConfig {
|
|||||||
vcs: "auto".into(),
|
vcs: "auto".into(),
|
||||||
width: None,
|
width: None,
|
||||||
width_margin: 4,
|
width_margin: 4,
|
||||||
cache_dir: "/tmp/claude-sl-{session_id}".into(),
|
cache_dir: "/tmp/claude-sl-{session_id}-{cache_version}-{config_hash}".into(),
|
||||||
cache_gc_days: 7,
|
cache_gc_days: 7,
|
||||||
cache_gc_interval_hours: 24,
|
cache_gc_interval_hours: 24,
|
||||||
cache_ttl_jitter_pct: 10,
|
cache_ttl_jitter_pct: 10,
|
||||||
@@ -100,7 +99,6 @@ impl Default for GlobalConfig {
|
|||||||
shell_env: HashMap::new(),
|
shell_env: HashMap::new(),
|
||||||
cache_version: 1,
|
cache_version: 1,
|
||||||
drop_strategy: "tiered".into(),
|
drop_strategy: "tiered".into(),
|
||||||
breakpoint_hysteresis: 2,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -30,7 +30,13 @@ pub fn render(ctx: &RenderContext) -> Option<SectionOutput> {
|
|||||||
|
|
||||||
/// Serve stale cached VCS data without running any commands.
|
/// Serve stale cached VCS data without running any commands.
|
||||||
fn render_stale_cache(ctx: &RenderContext) -> Option<SectionOutput> {
|
fn render_stale_cache(ctx: &RenderContext) -> Option<SectionOutput> {
|
||||||
let branch = ctx.cache.get_stale("vcs_branch")?;
|
let branch_raw = ctx.cache.get_stale("vcs_branch")?;
|
||||||
|
let trunc = &ctx.config.sections.vcs.truncate;
|
||||||
|
let branch = if trunc.enabled && trunc.max > 0 {
|
||||||
|
crate::format::truncate(&branch_raw, trunc.max, &trunc.style)
|
||||||
|
} else {
|
||||||
|
branch_raw
|
||||||
|
};
|
||||||
let branch_glyph = glyph::glyph("branch", &ctx.config.glyphs);
|
let branch_glyph = glyph::glyph("branch", &ctx.config.glyphs);
|
||||||
let raw = format!("{branch_glyph}{branch}");
|
let raw = format!("{branch_glyph}{branch}");
|
||||||
let ansi = if ctx.color_enabled {
|
let ansi = if ctx.color_enabled {
|
||||||
@@ -164,13 +170,8 @@ fn render_jj(
|
|||||||
let branch_ttl = Duration::from_secs(ttl.branch);
|
let branch_ttl = Duration::from_secs(ttl.branch);
|
||||||
|
|
||||||
let branch = ctx.cache.get("vcs_branch", branch_ttl).or_else(|| {
|
let branch = ctx.cache.get("vcs_branch", branch_ttl).or_else(|| {
|
||||||
// Use prefetched result if available
|
// Use prefetched result if available, otherwise exec
|
||||||
let out = ctx
|
let out = ctx.shell_results.get("vcs").cloned().unwrap_or_else(|| {
|
||||||
.shell_results
|
|
||||||
.get("vcs")
|
|
||||||
.cloned()
|
|
||||||
.flatten()
|
|
||||||
.or_else(|| {
|
|
||||||
shell::exec_gated(
|
shell::exec_gated(
|
||||||
ctx.shell_config,
|
ctx.shell_config,
|
||||||
"jj",
|
"jj",
|
||||||
|
|||||||
Reference in New Issue
Block a user