fix(dashboard,server): restore code change ledger UI and enrich model schema parity and pagination

This commit is contained in:
Riz Ashraf committed 2026-10-07 13:14:33 +01:00
1 parent 3b146f91c2
commit 73c3d41c87
9 files changed
+297 -19

No files matched your search

+119
View File
@@ -235,6 +235,26 @@ pub fn create_router(app_state: Arc<AppState>) -> Router {
}
}),
)
.route(
"/api/ledger",
get({
let state_clone = app_state.handler.state.clone();
move |axum::extract::Query(params): axum::extract::Query<
std::collections::HashMap<String, String>,
>| async move {
let limit = params
.get("limit")
.and_then(|l| l.parse::<usize>().ok())
.unwrap_or(100);
let json = state_clone.code.ledger.read_with(|items| {
let recent: Vec<_> = items.iter().rev().take(limit).collect();
serde_json::to_string(&recent).unwrap_or_else(|_| "[]".to_string())
});
([(axum::http::header::CONTENT_TYPE, "application/json")], json)
}
}),
)
.route(
"/api/tech_debts",
get({
@@ -265,6 +285,26 @@ pub fn create_router(app_state: Arc<AppState>) -> Router {
}
}),
)
.route(
"/api/session_summaries",
get({
let state_clone = app_state.handler.state.clone();
move |axum::extract::Query(params): axum::extract::Query<
std::collections::HashMap<String, String>,
>| async move {
let limit = params
.get("limit")
.and_then(|l| l.parse::<usize>().ok())
.unwrap_or(100);
let json = state_clone.telemetry.session_summaries.read_with(|items| {
let recent: Vec<_> = items.iter().rev().take(limit).collect();
serde_json::to_string(&recent).unwrap_or_else(|_| "[]".to_string())
});
([(axum::http::header::CONTENT_TYPE, "application/json")], json)
}
}),
)
.route(
"/api/milestones",
get({
@@ -789,4 +829,83 @@ mod tests {
assert!(js_str.contains("/api/activity/stream"));
assert!(js_str.contains("parseActivityPayload"));
}
#[tokio::test]
async fn test_ledger_endpoint() {
let (app, app_state, _dir) = setup_app().await;
app_state.handler.state.code.ledger.modify(|l| {
l.push(crate::models::CodeChange {
timestamp: 1728000000,
file_path: "src/main.rs".to_string(),
description: "Test commit 1".to_string(),
git_commit: Some("abc1234".to_string()),
..Default::default()
});
l.push(crate::models::CodeChange {
timestamp: 1728000100,
file_path: "src/lib.rs".to_string(),
description: "Test commit 2".to_string(),
git_commit: Some("def5678".to_string()),
..Default::default()
});
});
let request = Request::builder()
.uri("/api/ledger?limit=1")
.body(Body::empty())
.unwrap();
let response = app.oneshot(request).await.unwrap();
assert_eq!(response.status(), StatusCode::OK);
let body_bytes = axum::body::to_bytes(response.into_body(), usize::MAX)
.await
.unwrap();
let changes: Vec<crate::models::CodeChange> = serde_json::from_slice(&body_bytes).unwrap();
assert_eq!(changes.len(), 1);
assert_eq!(changes[0].description, "Test commit 2");
}
#[tokio::test]
async fn test_session_summaries_endpoint() {
let (app, app_state, _dir) = setup_app().await;
app_state
.handler
.state
.telemetry
.session_summaries
.modify(|summaries| {
summaries.push(crate::models::SessionSummary {
session_id: Some("session-1".to_string()),
summary: "Session 1 summary".to_string(),
namespace: "test".to_string(),
timestamp: 100,
..Default::default()
});
summaries.push(crate::models::SessionSummary {
session_id: Some("session-2".to_string()),
summary: "Session 2 summary".to_string(),
namespace: "test".to_string(),
timestamp: 200,
..Default::default()
});
});
let request = Request::builder()
.uri("/api/session_summaries?limit=1")
.body(Body::empty())
.unwrap();
let response = app.oneshot(request).await.unwrap();
assert_eq!(response.status(), StatusCode::OK);
let body_bytes = axum::body::to_bytes(response.into_body(), usize::MAX)
.await
.unwrap();
let summaries: Vec<crate::models::SessionSummary> = serde_json::from_slice(&body_bytes).unwrap();
assert_eq!(summaries.len(), 1);
assert_eq!(summaries[0].summary, "Session 2 summary");
}
}