mirror of
https://github.com/farion1231/cc-switch.git
synced 2026-08-02 10:21:16 +08:00
feat(usage): add Hermes Agent tracking + fix zero-cost bug + perf
Hermes: - Parse ~/.hermes/state.db sessions (incl. profiles/*/state.db) into proxy_request_logs with data_source='hermes_session', WAL-aware incremental sync, Hermes-reported cost preferred over model_pricing fallback Zero-cost bug (dashboard showed \$0 totals): - GPT-5.5 family default pricing (~83% of affected rows used GPT-5.5) - find_model_pricing_row: ASCII-lowercase normalization so "OpenAI/GPT-5.5@HIGH" matches seeded "gpt-5.5" - Startup cost backfill in async task: scan rows where total_cost <= 0 but tokens > 0, recompute via model_pricing in a single transaction Performance: - Add (app_type, created_at DESC) covering index for dashboard range queries - Add expression index on COALESCE(data_source, 'proxy') so dedup EXISTS subqueries use index lookup instead of full scan; drop superseded idx_request_logs_dedup_lookup Refactor: - row_to_request_log_detail helper (3-way de-dup; fixes cost_multiplier \"1\" vs \"1.0\" drift between callers) - Promote get_sync_state/update_sync_state to shared session_usage module (4 copies -> 1) - run_step helper in lib.rs replaces 9 if-let-Err blocks - maybe_backfill_log_costs returns bool to skip duplicate total_cost parsing in caller
This commit is contained in:
+44
-42
@@ -924,28 +924,35 @@ pub fn run() {
|
||||
tauri::async_runtime::spawn(async move {
|
||||
const SESSION_SYNC_INTERVAL_SECS: u64 = 60;
|
||||
|
||||
fn run_step<T>(name: &str, result: Result<T, crate::error::AppError>) {
|
||||
if let Err(e) = result {
|
||||
log::warn!("{name} failed: {e}");
|
||||
}
|
||||
}
|
||||
|
||||
let db = &db_for_session_sync;
|
||||
|
||||
// 首次同步
|
||||
if let Err(e) =
|
||||
crate::services::session_usage::sync_claude_session_logs(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Session usage initial sync failed: {e}");
|
||||
}
|
||||
if let Err(e) =
|
||||
crate::services::session_usage_codex::sync_codex_usage(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Codex usage initial sync failed: {e}");
|
||||
}
|
||||
if let Err(e) =
|
||||
crate::services::session_usage_gemini::sync_gemini_usage(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Gemini usage initial sync failed: {e}");
|
||||
}
|
||||
run_step(
|
||||
"Usage cost startup backfill",
|
||||
db.backfill_missing_usage_costs(),
|
||||
);
|
||||
run_step(
|
||||
"Session usage initial sync",
|
||||
crate::services::session_usage::sync_claude_session_logs(db),
|
||||
);
|
||||
run_step(
|
||||
"Codex usage initial sync",
|
||||
crate::services::session_usage_codex::sync_codex_usage(db),
|
||||
);
|
||||
run_step(
|
||||
"Gemini usage initial sync",
|
||||
crate::services::session_usage_gemini::sync_gemini_usage(db),
|
||||
);
|
||||
run_step(
|
||||
"Hermes usage initial sync",
|
||||
crate::services::session_usage_hermes::sync_hermes_usage(db),
|
||||
);
|
||||
|
||||
// 定期同步
|
||||
let mut interval = tokio::time::interval(std::time::Duration::from_secs(
|
||||
@@ -954,27 +961,22 @@ pub fn run() {
|
||||
interval.tick().await; // skip immediate first tick
|
||||
loop {
|
||||
interval.tick().await;
|
||||
if let Err(e) =
|
||||
crate::services::session_usage::sync_claude_session_logs(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Session usage periodic sync failed: {e}");
|
||||
}
|
||||
if let Err(e) =
|
||||
crate::services::session_usage_codex::sync_codex_usage(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Codex usage periodic sync failed: {e}");
|
||||
}
|
||||
if let Err(e) =
|
||||
crate::services::session_usage_gemini::sync_gemini_usage(
|
||||
&db_for_session_sync,
|
||||
)
|
||||
{
|
||||
log::warn!("Gemini usage periodic sync failed: {e}");
|
||||
}
|
||||
run_step(
|
||||
"Session usage periodic sync",
|
||||
crate::services::session_usage::sync_claude_session_logs(db),
|
||||
);
|
||||
run_step(
|
||||
"Codex usage periodic sync",
|
||||
crate::services::session_usage_codex::sync_codex_usage(db),
|
||||
);
|
||||
run_step(
|
||||
"Gemini usage periodic sync",
|
||||
crate::services::session_usage_gemini::sync_gemini_usage(db),
|
||||
);
|
||||
run_step(
|
||||
"Hermes usage periodic sync",
|
||||
crate::services::session_usage_hermes::sync_hermes_usage(db),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user