feat(agents): add azd ai agent delete command#8519
Conversation
b8eb03e to
adac334
Compare
📋 Prioritization NoteThanks for the contribution! The linked issue isn't in the current milestone yet. |
There was a problem hiding this comment.
Pull request overview
Adds a new azd ai agent delete [name] command to the Azure AI Agents extension to delete a hosted agent (optionally force-deleting when active sessions exist), and wires the underlying client operation + error codes needed to support the UX.
Changes:
- Add
agent deletecobra command and action implementation (including--forceand--output json/none). - Extend
AgentClient.DeleteAgentto include aforcequery parameter and add URL/404 tests. - Introduce delete-specific external error codes + operation name and register the new command in the root command tree.
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
| cli/azd/extensions/azure.ai.agents/internal/pkg/agents/agent_api/operations.go | Extends DeleteAgent API call to include force query parameter. |
| cli/azd/extensions/azure.ai.agents/internal/pkg/agents/agent_api/operations_test.go | Adds tests for force=true/false query encoding and 404 behavior. |
| cli/azd/extensions/azure.ai.agents/internal/exterrors/codes.go | Adds delete operation name and delete-specific validation error codes. |
| cli/azd/extensions/azure.ai.agents/internal/cmd/root.go | Registers the new delete command under the extension root. |
| cli/azd/extensions/azure.ai.agents/internal/cmd/delete.go | Implements the new agent delete command, confirmation prompt, error mapping, output formatting, and env-var cleanup. |
| cli/azd/extensions/azure.ai.agents/internal/cmd/delete_test.go | Adds basic command shape tests (args + --force flag presence/default). |
Implements `azd ai agent delete [name]` to delete a hosted agent via the
Foundry API. Key behaviors:
- Default: force=false (fails if agent has active sessions)
- --force: terminates active sessions and force-deletes
- Confirmation prompt before deletion (skipped with --no-prompt)
- Agent name auto-resolved from azure.yaml / azd environment
- Cleans up AGENT_{KEY}_NAME, _VERSION, _ENDPOINT env vars on success
- Supports --output json for structured output
- Handles 404 (not found) and 409 (active sessions) gracefully
Also updates the DeleteAgent client method in operations.go to accept
a force parameter matching the Vienna API's ?force= query parameter.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
|
Addressed Copilot review comments: Comment 1 (name resolution): This follows the same pattern as \show, \invoke, \monitor, and \session\ commands they all pass the positional arg to Comment 2 (cancellation handling): Fixed now returns \�xterrors.Cancelled()\ instead of printing to stdout. Consistent with the rest of the codebase. Comment 3 (test coverage): Added error classification tests for 404 \CodeAgentNotFound, 409 \CodeAgentHasActiveSessions\ (verifying suggestion mentions --force), and 500 \ServiceError. Same pattern as session_test.go. |
Move error classification logic from inline switch in Run() to a package-level classifyDeleteError function. Tests call it directly instead of duplicating the logic. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
|
|
||
| // Confirmation prompt (skip in --no-prompt mode) | ||
| if !a.flags.noPrompt { | ||
| message := fmt.Sprintf("Delete agent %q and all its versions?", agentName) |
There was a problem hiding this comment.
Do we support deleting specific versions in the API?
| return err | ||
| } | ||
|
|
||
| agentName := info.AgentName |
There was a problem hiding this comment.
Is this block necessary? If we can't find the agent service in the project, will we run into other issues later on attempting the delete?
|
|
||
| switch a.flags.output { | ||
| case "json": | ||
| data, jsonErr := json.MarshalIndent(result, "", " ") |
There was a problem hiding this comment.
Is there actually a valid json response coming from delete? Aren't deletes usually just an empty response with 200 status code?
| // cleanupEnvVars removes AGENT_{KEY}_NAME, AGENT_{KEY}_VERSION, and | ||
| // AGENT_{KEY}_ENDPOINT from the azd environment after a successful delete. | ||
| // The SDK has no DeleteValue API, so we set values to empty string as a workaround. | ||
| func (a *DeleteAction) cleanupEnvVars(ctx context.Context, azdClient *azdext.AzdClient, serviceName string) { |
There was a problem hiding this comment.
We should also attempt to clean up any saved conversation/session IDs. We should have similar handling already existing in our postdown hook, so can look there to see if we can reuse any code.
Summary
Adds
azd ai agent delete [name]command to delete a hosted agent from the Foundry service.Fixes #8520
CLI Help
Behavior
azd ai agent deleteazd ai agent delete my-agentazd ai agent delete --forceazd ai agent delete --output jsonazd ai agent show--forceorazd ai agent sessions deleteAPI Mapping (Vienna)
Source:
AgentController.cs:649-[FromQuery] bool force = falseNote: No
[FoundryFeatures(...)]gate on DeleteAgent (management-plane operation).Changes
cmd/delete.gocmd/delete_test.gocmd/root.gonewDeleteCommandagent_api/operations.goforce boolparam toDeleteAgent()agent_api/operations_test.goexterrors/codes.goOpDeleteAgent,CodeAgentNotFound,CodeAgentHasActiveSessionsTesting
DeleteAgentcallers - there were none)--forceflag registered with default=falseDeleteAgentclient sends correctforce=true/force=falsein URL query