Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
d625e58
chore(deps): bump agent-client-protocol from 0.11.1 to 0.12.1 (#9381)
dependabot[bot] May 23, 2026
8689fdf
chore(deps): bump image from 0.24.9 to 0.25.10 (#9383)
dependabot[bot] May 23, 2026
ce004f7
fix(agents): serialize per-session agent creation to stop duplicate M…
fresh3nough May 23, 2026
c4d64d1
Fix desktop chat search session limiting (#9366)
angiejones May 24, 2026
e1cc44f
Build summon instructions per turn (#9329)
DOsinga May 25, 2026
ba16de9
docs: stats update (#9410)
angiejones May 25, 2026
a11843a
Simplify UI customization (#9353)
DOsinga May 26, 2026
6d544e7
chore(deps): bump qs from 6.14.2 to 6.15.2 in /evals/open-model-gym/m…
dependabot[bot] May 26, 2026
bf0da95
Add Turkish desktop locale (#9392)
seneroner77-cmd May 26, 2026
27dc0d5
Improve dependency hygiene (#9360)
jh-block May 26, 2026
dcdc7f6
fix(desktop): stop the main window growing taller on every launch (#9…
officialasishkumar May 26, 2026
b332f50
Russian language support (#9406)
besdar May 26, 2026
b0cd61a
chore(release): bump version to 1.36.0 (minor) (#9417)
github-actions[bot] May 26, 2026
7dc904e
add databricks ai gateway provider (#9274)
baxen May 26, 2026
1749354
Prefer goose aliases for Databricks v2 inventory (#9430)
baxen May 27, 2026
794402d
fix(ci): build linux x86_64 standard inside manylinux_2_28 for glibc …
88plug May 27, 2026
d90b349
feat: add /model slash command to CLI for session model switching (#8…
baxen May 27, 2026
27b41d9
local inference: stricter GGUF requirements, auto detection of tool c…
jh-block May 27, 2026
d017295
fix: tolerate missing responses output (#9449)
angiejones May 27, 2026
4f43ae4
fix(ui): preserve pending env vars in Add Extension form (#9285)
williams145 May 27, 2026
10ac6b1
feat: make tool output size limit configurable via GOOSE_MAX_TOOL_RES…
DOsinga May 27, 2026
1125e8d
fix: make azure api-version query param optional (#9221)
DOsinga May 27, 2026
35d1fc7
fix(desktop): start new chat in current window from recipe param moda…
michaelneale May 27, 2026
a18b92e
fix(desktop): refresh provider list in Switch Models picker (#9408)
officialasishkumar May 27, 2026
4c88f4b
feat(providers): add Alibaba (Qwen via DashScope) declarative provide…
jezweb May 27, 2026
e9b0d92
feat(providers): add Perplexity as a declarative OpenAI-compatible pr…
jliounis May 27, 2026
c9945bc
chore(deps): bump sha2 from 0.10.9 to 0.11.0 (#8963)
dependabot[bot] May 27, 2026
9c403b1
refactor: convert desktop v1 and goose-server extensions to ACP+ (#9448)
alexhancock May 27, 2026
27d68ba
doc: Add Scaleway provider (#9423)
Quentinchampenois May 28, 2026
d10d009
CLI to list skills with token counts (#9326)
jamadeo May 28, 2026
2116f88
feat: add `tui` feature flag to gate the tui command (#9428)
r0x0d May 28, 2026
1cb5cb0
Add Scholar Sidekick MCP extension (#9433)
mlava May 28, 2026
104cc17
Add ACP session system prompt setter (#9478)
baxen May 29, 2026
a3bdb91
fix(acp): forward ACP server context window size to clients (#9455)
matt2e May 29, 2026
25ff547
Expose raw provider supported models over ACP (#9475)
baxen May 29, 2026
ee2273c
chore: sync upstream aaif-goose/goose@main into apemind-agent (2026-0…
earayu May 29, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 49 additions & 0 deletions crates/goose-sdk/src/custom_requests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,37 @@ pub struct UpdateWorkingDirRequest {
pub working_dir: String,
}

/// How a session system prompt update should be applied.
#[derive(Debug, Default, Clone, Copy, PartialEq, Eq, Serialize, Deserialize, JsonSchema)]
#[serde(rename_all = "snake_case")]
pub enum SessionSystemPromptMode {
/// Replace Goose's base system prompt with the provided text.
Set,
/// Append the provided text under Goose's "Additional Instructions" section.
#[default]
Append,
}

/// Set, append, or clear system prompt text for a session.
///
/// `mode: "set"` replaces Goose's base system prompt. `mode: "append"` adds an
/// instruction under "Additional Instructions". Reusing a key replaces the
/// previous value for that mode/key; sending empty text clears it.
#[derive(Debug, Default, Clone, Serialize, Deserialize, JsonSchema, JsonRpcRequest)]
#[request(
method = "_goose/unstable/session/system-prompt/set",
response = EmptyResponse
)]
#[serde(rename_all = "camelCase")]
pub struct SetSessionSystemPromptRequest {
pub session_id: String,
#[serde(default)]
pub mode: SessionSystemPromptMode,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub key: Option<String>,
pub text: String,
}

/// Delete a session.
#[derive(Debug, Default, Clone, Serialize, Deserialize, JsonSchema, JsonRpcRequest)]
#[request(method = "session/delete", response = EmptyResponse)]
Expand Down Expand Up @@ -1091,6 +1122,24 @@ pub struct ListProvidersResponse {
pub entries: Vec<ProviderInventoryEntryDto>,
}

/// List the raw model identifiers returned by a provider's live supported-models API.
#[derive(Debug, Default, Clone, Serialize, Deserialize, JsonSchema, JsonRpcRequest)]
#[request(
method = "_goose/unstable/providers/supported-models/list",
response = ProviderSupportedModelsListResponse
)]
#[serde(rename_all = "camelCase")]
pub struct ProviderSupportedModelsListRequest {
pub provider_id: String,
}

#[derive(Debug, Default, Clone, Serialize, Deserialize, JsonSchema, JsonRpcResponse)]
#[serde(rename_all = "camelCase")]
pub struct ProviderSupportedModelsListResponse {
pub provider_id: String,
pub models: Vec<String>,
}

/// Trigger a background refresh of provider inventories.
#[derive(Debug, Default, Clone, Serialize, Deserialize, JsonSchema, JsonRpcRequest)]
#[request(
Expand Down
10 changes: 10 additions & 0 deletions crates/goose/acp-meta.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,11 @@
"requestType": "UpdateWorkingDirRequest_unstable",
"responseType": "EmptyResponse"
},
{
"method": "_goose/unstable/session/system-prompt/set",
"requestType": "SetSessionSystemPromptRequest_unstable",
"responseType": "EmptyResponse"
},
{
"method": "session/delete",
"requestType": "DeleteSessionRequest",
Expand Down Expand Up @@ -65,6 +70,11 @@
"requestType": "ListProvidersRequest_unstable",
"responseType": "ListProvidersResponse_unstable"
},
{
"method": "_goose/unstable/providers/supported-models/list",
"requestType": "ProviderSupportedModelsListRequest_unstable",
"responseType": "ProviderSupportedModelsListResponse_unstable"
},
{
"method": "_goose/unstable/providers/catalog/list",
"requestType": "ProviderCatalogListRequest_unstable",
Expand Down
103 changes: 103 additions & 0 deletions crates/goose/acp-schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,49 @@
"x-side": "agent",
"x-method": "_goose/unstable/session/working-dir/update"
},
"SetSessionSystemPromptRequest_unstable": {
"type": "object",
"properties": {
"sessionId": {
"type": "string"
},
"mode": {
"$ref": "#/$defs/SessionSystemPromptMode",
"default": "append"
},
"key": {
"type": [
"string",
"null"
]
},
"text": {
"type": "string"
}
},
"required": [
"sessionId",
"text"
],
"description": "Set, append, or clear system prompt text for a session.\n\n`mode: \"set\"` replaces Goose's base system prompt. `mode: \"append\"` adds an\ninstruction under \"Additional Instructions\". Reusing a key replaces the\nprevious value for that mode/key; sending empty text clears it.",
"x-side": "agent",
"x-method": "_goose/unstable/session/system-prompt/set"
},
"SessionSystemPromptMode": {
"oneOf": [
{
"type": "string",
"const": "set",
"description": "Replace Goose's base system prompt with the provided text."
},
{
"type": "string",
"const": "append",
"description": "Append the provided text under Goose's \"Additional Instructions\" section."
}
],
"description": "How a session system prompt update should be applied."
},
"DeleteSessionRequest": {
"type": "object",
"properties": {
Expand Down Expand Up @@ -525,6 +568,40 @@
],
"description": "A single model in provider inventory."
},
"ProviderSupportedModelsListRequest_unstable": {
"type": "object",
"properties": {
"providerId": {
"type": "string"
}
},
"required": [
"providerId"
],
"description": "List the raw model identifiers returned by a provider's live supported-models API.",
"x-side": "agent",
"x-method": "_goose/unstable/providers/supported-models/list"
},
"ProviderSupportedModelsListResponse_unstable": {
"type": "object",
"properties": {
"providerId": {
"type": "string"
},
"models": {
"type": "array",
"items": {
"type": "string"
}
}
},
"required": [
"providerId",
"models"
],
"x-side": "agent",
"x-method": "_goose/unstable/providers/supported-models/list"
},
"ProviderCatalogListRequest_unstable": {
"type": "object",
"properties": {
Expand Down Expand Up @@ -2640,6 +2717,15 @@
"description": "Params for _goose/unstable/session/working-dir/update",
"title": "UpdateWorkingDirRequest_unstable"
},
{
"allOf": [
{
"$ref": "#/$defs/SetSessionSystemPromptRequest_unstable"
}
],
"description": "Params for _goose/unstable/session/system-prompt/set",
"title": "SetSessionSystemPromptRequest_unstable"
},
{
"allOf": [
{
Expand Down Expand Up @@ -2703,6 +2789,15 @@
"description": "Params for _goose/unstable/providers/list",
"title": "ListProvidersRequest_unstable"
},
{
"allOf": [
{
"$ref": "#/$defs/ProviderSupportedModelsListRequest_unstable"
}
],
"description": "Params for _goose/unstable/providers/supported-models/list",
"title": "ProviderSupportedModelsListRequest_unstable"
},
{
"allOf": [
{
Expand Down Expand Up @@ -3167,6 +3262,14 @@
],
"title": "ListProvidersResponse_unstable"
},
{
"allOf": [
{
"$ref": "#/$defs/ProviderSupportedModelsListResponse_unstable"
}
],
"title": "ProviderSupportedModelsListResponse_unstable"
},
{
"allOf": [
{
Expand Down
38 changes: 36 additions & 2 deletions crates/goose/src/acp/provider.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ use std::future::Future;
use std::path::PathBuf;
use std::process::Stdio;
use std::sync::{
atomic::{AtomicBool, Ordering},
atomic::{AtomicBool, AtomicU64, Ordering},
Arc, Mutex,
};
use std::thread::JoinHandle;
Expand Down Expand Up @@ -144,6 +144,11 @@ pub struct AcpProvider {
Arc<TokioMutex<HashMap<String, oneshot::Sender<PermissionConfirmation>>>>,
pending_tool_updates: Arc<Mutex<HashMap<String, AccumulatedToolCall>>>,
handoff_context_sent: AtomicBool,
/// Latest `size` reported by the ACP server in a `session/update` →
/// `usage_update` notification. 0 means no real update has arrived yet,
/// in which case `get_model_config()` falls back to the static model
/// configuration's context limit.
context_size: Arc<AtomicU64>,

tx: Option<mpsc::Sender<ClientRequest>>,
loop_thread: Option<JoinHandle<()>>,
Expand Down Expand Up @@ -222,10 +227,12 @@ impl AcpProvider {
let goose_mode_shared = Arc::new(Mutex::new(goose_mode));
let pending_tool_updates: Arc<Mutex<HashMap<String, AccumulatedToolCall>>> =
Arc::new(Mutex::new(HashMap::new()));
let context_size = Arc::new(AtomicU64::new(0));
let client_loop = AcpClientLoop::new(
config,
goose_mode_shared.clone(),
pending_tool_updates.clone(),
context_size.clone(),
);
let loop_thread = spawn_client_loop(run(client_loop, rx, init_tx));

Expand Down Expand Up @@ -273,6 +280,7 @@ impl AcpProvider {
pending_confirmations: Arc::new(TokioMutex::new(HashMap::new())),
pending_tool_updates,
handoff_context_sent: AtomicBool::new(false),
context_size,
tx: Some(tx),
loop_thread: Some(loop_thread),
})
Expand Down Expand Up @@ -370,7 +378,12 @@ impl Provider for AcpProvider {
}

fn get_model_config(&self) -> ModelConfig {
self.model.clone()
let mut model = self.model.clone();
let size = self.context_size.load(Ordering::Relaxed);
if size > 0 {
model.context_limit = Some(size as usize);
}
model
}

async fn update_mode(&self, session_id: &str, mode: GooseMode) -> Result<(), ProviderError> {
Expand Down Expand Up @@ -629,19 +642,22 @@ struct AcpClientLoop {
goose_mode: Arc<Mutex<GooseMode>>,
prompt_response_tx: Arc<Mutex<Option<mpsc::Sender<AcpUpdate>>>>,
pending_tool_updates: Arc<Mutex<HashMap<String, AccumulatedToolCall>>>,
context_size: Arc<AtomicU64>,
}

impl AcpClientLoop {
fn new(
config: AcpProviderConfig,
goose_mode: Arc<Mutex<GooseMode>>,
pending_tool_updates: Arc<Mutex<HashMap<String, AccumulatedToolCall>>>,
context_size: Arc<AtomicU64>,
) -> Self {
Self {
config,
goose_mode,
prompt_response_tx: Arc::new(Mutex::new(None)),
pending_tool_updates,
context_size,
}
}

Expand Down Expand Up @@ -695,6 +711,7 @@ impl AcpClientLoop {
goose_mode,
prompt_response_tx,
pending_tool_updates,
context_size,
} = self;
let notification_callback = config.notification_callback.clone();
let reverse_modes = reverse_mode_mapping(&config.mode_mapping);
Expand All @@ -707,6 +724,7 @@ impl AcpClientLoop {
let reverse_modes = reverse_modes.clone();
let goose_mode = goose_mode.clone();
let pending_tool_updates = pending_tool_updates.clone();
let context_size = context_size.clone();
async move |notification: SessionNotification, _cx| {
if let Some(ref cb) = notification_callback {
cb(notification.clone());
Expand Down Expand Up @@ -740,6 +758,9 @@ impl AcpClientLoop {
}
}
}
SessionUpdate::UsageUpdate(usage) => {
context_size.store(usage.size, Ordering::Relaxed);
}
_ => {}
}
if let Some(tx) = prompt_response_tx
Expand Down Expand Up @@ -1529,6 +1550,7 @@ mod tests {
pending_confirmations: Arc::new(TokioMutex::new(HashMap::new())),
pending_tool_updates: Arc::new(Mutex::new(HashMap::new())),
handoff_context_sent: AtomicBool::new(false),
context_size: Arc::new(AtomicU64::new(0)),
tx,
loop_thread: None,
}
Expand Down Expand Up @@ -1633,6 +1655,18 @@ mod tests {
assert!(!later_claim.include_context);
}

#[test]
fn get_model_config_surfaces_captured_context_size() {
let provider = test_provider();
assert_eq!(
provider.get_model_config().context_limit(),
crate::model::DEFAULT_CONTEXT_LIMIT
);

provider.context_size.store(200_000, Ordering::Relaxed);
assert_eq!(provider.get_model_config().context_limit(), 200_000);
}

#[tokio::test]
async fn failed_first_prompt_send_rolls_back_handoff_context_claim() {
let (tx, rx) = mpsc::channel(1);
Expand Down
16 changes: 16 additions & 0 deletions crates/goose/src/acp/server/custom_dispatch.rs
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,14 @@ impl GooseAcpAgent {
self.on_update_working_dir(req).await
}

#[custom_method(SetSessionSystemPromptRequest)]
async fn dispatch_set_session_system_prompt(
&self,
req: SetSessionSystemPromptRequest,
) -> Result<EmptyResponse, agent_client_protocol::Error> {
self.on_set_session_system_prompt(req).await
}

#[custom_method(DeleteSessionRequest)]
async fn dispatch_delete_session(
&self,
Expand Down Expand Up @@ -114,6 +122,14 @@ impl GooseAcpAgent {
self.on_list_providers(req).await
}

#[custom_method(ProviderSupportedModelsListRequest)]
async fn dispatch_list_provider_supported_models(
&self,
req: ProviderSupportedModelsListRequest,
) -> Result<ProviderSupportedModelsListResponse, agent_client_protocol::Error> {
self.on_list_provider_supported_models(req).await
}

#[custom_method(ProviderCatalogListRequest)]
async fn dispatch_list_provider_catalog(
&self,
Expand Down
Loading
Loading