Lifei/UI parameter input (#5222)

This commit is contained in:
Lifei Zhou
2025-10-20 10:05:54 +11:00
committed by GitHub
parent 6c3e07e9c7
commit 8b53a5696e
27 changed files with 717 additions and 1250 deletions
+53 -6
View File
@@ -1,4 +1,7 @@
use crate::routes::errors::ErrorResponse;
use crate::routes::recipe_utils::{apply_recipe_to_agent, build_recipe_with_parameter_values};
use crate::state::AppState;
use axum::extract::State;
use axum::routing::post;
use axum::{
extract::Path,
@@ -6,6 +9,7 @@ use axum::{
routing::{delete, get, put},
Json, Router,
};
use goose::recipe::Recipe;
use goose::session::session_manager::SessionInsights;
use goose::session::{Session, SessionManager};
use serde::{Deserialize, Serialize};
@@ -34,6 +38,11 @@ pub struct UpdateSessionUserRecipeValuesRequest {
user_recipe_values: HashMap<String, String>,
}
#[derive(Debug, Serialize, ToSchema)]
pub struct UpdateSessionUserRecipeValuesResponse {
recipe: Recipe,
}
#[derive(Deserialize, ToSchema)]
#[serde(rename_all = "camelCase")]
pub struct ImportSessionRequest {
@@ -151,10 +160,10 @@ async fn update_session_description(
("session_id" = String, Path, description = "Unique identifier for the session")
),
responses(
(status = 200, description = "Session user recipe values updated successfully"),
(status = 200, description = "Session user recipe values updated successfully", body = UpdateSessionUserRecipeValuesResponse),
(status = 401, description = "Unauthorized - Invalid or missing API key"),
(status = 404, description = "Session not found"),
(status = 500, description = "Internal server error")
(status = 404, description = "Session not found", body = ErrorResponse),
(status = 500, description = "Internal server error", body = ErrorResponse)
),
security(
("api_key" = [])
@@ -163,16 +172,54 @@ async fn update_session_description(
)]
// Update session user recipe parameter values
async fn update_session_user_recipe_values(
State(state): State<Arc<AppState>>,
Path(session_id): Path<String>,
Json(request): Json<UpdateSessionUserRecipeValuesRequest>,
) -> Result<StatusCode, StatusCode> {
) -> Result<Json<UpdateSessionUserRecipeValuesResponse>, ErrorResponse> {
SessionManager::update_session(&session_id)
.user_recipe_values(Some(request.user_recipe_values))
.apply()
.await
.map_err(|_| StatusCode::INTERNAL_SERVER_ERROR)?;
.map_err(|err| ErrorResponse {
message: err.to_string(),
status: StatusCode::INTERNAL_SERVER_ERROR,
})?;
Ok(StatusCode::OK)
let session = SessionManager::get_session(&session_id, false)
.await
.map_err(|err| ErrorResponse {
message: err.to_string(),
status: StatusCode::INTERNAL_SERVER_ERROR,
})?;
let recipe = session.recipe.ok_or_else(|| ErrorResponse {
message: "Recipe not found".to_string(),
status: StatusCode::NOT_FOUND,
})?;
let user_recipe_values = session.user_recipe_values.unwrap_or_default();
match build_recipe_with_parameter_values(&recipe, user_recipe_values).await {
Ok(Some(recipe)) => {
let agent = state
.get_agent_for_route(session_id.clone())
.await
.map_err(|status| ErrorResponse {
message: format!("Failed to get agent: {}", status),
status,
})?;
if let Some(prompt) = apply_recipe_to_agent(&agent, &recipe, false).await {
agent.extend_system_prompt(prompt).await;
}
Ok(Json(UpdateSessionUserRecipeValuesResponse { recipe }))
}
Ok(None) => Err(ErrorResponse {
message: "Missing required parameters".to_string(),
status: StatusCode::BAD_REQUEST,
}),
Err(e) => Err(ErrorResponse {
message: e.to_string(),
status: StatusCode::INTERNAL_SERVER_ERROR,
}),
}
}
#[utoipa::path(