mirror of
https://github.com/harivansh-afk/sandbox-agent.git
synced 2026-04-15 07:04:48 +00:00
Fix Foundry UI bugs: org names, sessions, and repo selection (#250)
* Fix Foundry auth: migrate to Better Auth adapter, fix access token retrieval - Remove @ts-nocheck from better-auth.ts, auth-user/index.ts, app-shell.ts and fix all type errors - Fix getAccessTokenForSession: read GitHub token directly from account record instead of calling Better Auth's internal /get-access-token endpoint which returns 403 on server-side calls - Re-implement workspaceAuth helper functions (workspaceAuthColumn, normalizeAuthValue, workspaceAuthClause, workspaceAuthWhere) that were accidentally deleted - Remove all retry logic (withRetries, isRetryableAppActorError) - Implement CORS origin allowlist from configured environment - Document cachedAppWorkspace singleton pattern - Add inline org sync fallback in buildAppSnapshot for post-OAuth flow - Add no-retry rule to CLAUDE.md Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * Add Foundry dev panel from fix-git-data branch Port the dev panel component that was left out when PR #243 was replaced by PR #247. Adapted to remove runtime/mock-debug references that don't exist on the current branch. - Toggle with Shift+D, persists visibility to localStorage - Shows context, session, GitHub sync status sections - Dev-only (import.meta.env.DEV) Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * Add full Docker image defaults, fix actor deadlocks, and improve dev experience - Add Dockerfile.full and --all flag to install-agent CLI for pre-built images - Centralize Docker image constant (FULL_IMAGE) pinned to 0.3.1-full - Remove examples/shared/Dockerfile{,.dev} and daytona snapshot example - Expand Docker docs with full runnable Dockerfile - Fix self-deadlock in createWorkbenchSession (fire-and-forget provisioning) - Audit and convert 12 task actions from wait:true to wait:false - Add bun --hot for dev backend hot reload - Remove --force from pnpm install in dev Dockerfile for faster startup - Add env_file support to compose.dev.yaml for automatic credential loading - Add mock frontend compose config and dev panel - Update CLAUDE.md with wait:true policy and dev environment setup Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * WIP: async action fixes and interest manager Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * Fix Foundry UI bugs: org names, hanging sessions, and wrong repo creation - Fix org display name using GitHub description instead of name field - Fix createWorkbenchSession hanging when sandbox is provisioning - Fix auto-session creation retry storm on errors - Fix task creation using wrong repo due to React state race conditions - Remove Bun hot-reload from backend Dockerfile (causes port drift) - Add GitHub sync/install status to dev panel Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
58c54156f1
commit
d8b8b49f37
88 changed files with 9252 additions and 1933 deletions
|
|
@ -79,7 +79,7 @@ pub enum Command {
|
|||
Opencode(OpencodeArgs),
|
||||
/// Manage the sandbox-agent background daemon.
|
||||
Daemon(DaemonArgs),
|
||||
/// Install or reinstall an agent without running the server.
|
||||
/// Install or reinstall one agent, or `all` supported agents, without running the server.
|
||||
InstallAgent(InstallAgentArgs),
|
||||
/// Inspect locally discovered credentials.
|
||||
Credentials(CredentialsArgs),
|
||||
|
|
@ -295,7 +295,10 @@ pub struct AcpCloseArgs {
|
|||
|
||||
#[derive(Args, Debug)]
|
||||
pub struct InstallAgentArgs {
|
||||
agent: String,
|
||||
#[arg(required_unless_present = "all", conflicts_with = "all")]
|
||||
agent: Option<String>,
|
||||
#[arg(long, conflicts_with = "agent")]
|
||||
all: bool,
|
||||
#[arg(long, short = 'r')]
|
||||
reinstall: bool,
|
||||
#[arg(long = "agent-version")]
|
||||
|
|
@ -946,24 +949,73 @@ fn load_json_payload(
|
|||
}
|
||||
|
||||
fn install_agent_local(args: &InstallAgentArgs) -> Result<(), CliError> {
|
||||
let agent_id = AgentId::parse(&args.agent)
|
||||
.ok_or_else(|| CliError::Server(format!("unsupported agent: {}", args.agent)))?;
|
||||
if args.all && (args.agent_version.is_some() || args.agent_process_version.is_some()) {
|
||||
return Err(CliError::Server(
|
||||
"--agent-version and --agent-process-version are only supported for single-agent installs"
|
||||
.to_string(),
|
||||
));
|
||||
}
|
||||
|
||||
let agents = resolve_install_agents(args)?;
|
||||
|
||||
let manager = AgentManager::new(default_install_dir())
|
||||
.map_err(|err| CliError::Server(err.to_string()))?;
|
||||
|
||||
let result = manager
|
||||
.install(
|
||||
agent_id,
|
||||
InstallOptions {
|
||||
reinstall: args.reinstall,
|
||||
version: args.agent_version.clone(),
|
||||
agent_process_version: args.agent_process_version.clone(),
|
||||
},
|
||||
)
|
||||
.map_err(|err| CliError::Server(err.to_string()))?;
|
||||
if agents.len() == 1 {
|
||||
let result = manager
|
||||
.install(
|
||||
agents[0],
|
||||
InstallOptions {
|
||||
reinstall: args.reinstall,
|
||||
version: args.agent_version.clone(),
|
||||
agent_process_version: args.agent_process_version.clone(),
|
||||
},
|
||||
)
|
||||
.map_err(|err| CliError::Server(err.to_string()))?;
|
||||
let output = install_result_json(result);
|
||||
return write_stdout_line(&serde_json::to_string_pretty(&output)?);
|
||||
}
|
||||
|
||||
let output = json!({
|
||||
let mut results = Vec::with_capacity(agents.len());
|
||||
for agent_id in agents {
|
||||
let result = manager
|
||||
.install(
|
||||
agent_id,
|
||||
InstallOptions {
|
||||
reinstall: args.reinstall,
|
||||
version: None,
|
||||
agent_process_version: None,
|
||||
},
|
||||
)
|
||||
.map_err(|err| CliError::Server(err.to_string()))?;
|
||||
results.push(json!({
|
||||
"agent": agent_id.as_str(),
|
||||
"result": install_result_json(result),
|
||||
}));
|
||||
}
|
||||
|
||||
write_stdout_line(&serde_json::to_string_pretty(
|
||||
&json!({ "agents": results }),
|
||||
)?)
|
||||
}
|
||||
|
||||
fn resolve_install_agents(args: &InstallAgentArgs) -> Result<Vec<AgentId>, CliError> {
|
||||
if args.all {
|
||||
return Ok(AgentId::all().to_vec());
|
||||
}
|
||||
|
||||
let agent = args
|
||||
.agent
|
||||
.as_deref()
|
||||
.ok_or_else(|| CliError::Server("missing agent: provide <AGENT> or --all".to_string()))?;
|
||||
|
||||
AgentId::parse(agent)
|
||||
.map(|agent_id| vec![agent_id])
|
||||
.ok_or_else(|| CliError::Server(format!("unsupported agent: {agent}")))
|
||||
}
|
||||
|
||||
fn install_result_json(result: sandbox_agent_agent_management::agents::InstallResult) -> Value {
|
||||
json!({
|
||||
"alreadyInstalled": result.already_installed,
|
||||
"artifacts": result.artifacts.into_iter().map(|artifact| json!({
|
||||
"kind": format!("{:?}", artifact.kind),
|
||||
|
|
@ -971,9 +1023,7 @@ fn install_agent_local(args: &InstallAgentArgs) -> Result<(), CliError> {
|
|||
"source": format!("{:?}", artifact.source),
|
||||
"version": artifact.version,
|
||||
})).collect::<Vec<_>>()
|
||||
});
|
||||
|
||||
write_stdout_line(&serde_json::to_string_pretty(&output)?)
|
||||
})
|
||||
}
|
||||
|
||||
#[derive(Serialize)]
|
||||
|
|
@ -1416,6 +1466,60 @@ fn write_stderr_line(text: &str) -> Result<(), CliError> {
|
|||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn resolve_install_agents_expands_all() {
|
||||
assert_eq!(
|
||||
resolve_install_agents(&InstallAgentArgs {
|
||||
agent: None,
|
||||
all: true,
|
||||
reinstall: false,
|
||||
agent_version: None,
|
||||
agent_process_version: None,
|
||||
})
|
||||
.unwrap(),
|
||||
AgentId::all().to_vec()
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn resolve_install_agents_supports_single_agent() {
|
||||
assert_eq!(
|
||||
resolve_install_agents(&InstallAgentArgs {
|
||||
agent: Some("codex".to_string()),
|
||||
all: false,
|
||||
reinstall: false,
|
||||
agent_version: None,
|
||||
agent_process_version: None,
|
||||
})
|
||||
.unwrap(),
|
||||
vec![AgentId::Codex]
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn resolve_install_agents_rejects_unknown_agent() {
|
||||
assert!(resolve_install_agents(&InstallAgentArgs {
|
||||
agent: Some("nope".to_string()),
|
||||
all: false,
|
||||
reinstall: false,
|
||||
agent_version: None,
|
||||
agent_process_version: None,
|
||||
})
|
||||
.is_err());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn resolve_install_agents_rejects_positional_all() {
|
||||
assert!(resolve_install_agents(&InstallAgentArgs {
|
||||
agent: Some("all".to_string()),
|
||||
all: false,
|
||||
reinstall: false,
|
||||
agent_version: None,
|
||||
agent_process_version: None,
|
||||
})
|
||||
.is_err());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_last_event_id_header_sets_header_when_provided() {
|
||||
let client = HttpClient::builder().build().expect("build client");
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue