Skip to content

feat: AI chat phase 5 (saved-query chips, user-defined slash commands)#1068

Merged
datlechin merged 2 commits intomainfrom
feat/chat-saved-queries-and-custom-slash
May 7, 2026
Merged

feat: AI chat phase 5 (saved-query chips, user-defined slash commands)#1068
datlechin merged 2 commits intomainfrom
feat/chat-saved-queries-and-custom-slash

Conversation

@datlechin
Copy link
Copy Markdown
Member

Summary

Closes the remaining items in the AI Chat umbrella (#1047):

  • 5a — Saved-query chips. Type @ and pick a saved SQL query. The chip carries the favorite's name; on send the chip resolves to the query body wrapped in a SQL code block under a ## Saved Query: <name> header.
  • 5b — User-defined slash commands. Author your own commands in Settings -> AI -> Custom Slash Commands. Templates support {{query}} (current editor query), {{schema}} (active schema), {{database}} (active database name), and {{body}} (text typed after the command in the composer).

Changes

5a — Saved query chips

  • ContextItem.savedQuery(id:name:) carries the name alongside the id (Codable migration: missing name decodes as empty string).
  • AIChatViewModel.cachedSavedQueries: [UUID: SQLFavorite] populated on attach + on connection load.
  • primeAttachmentData now handles .savedQuery by looking up the favorite via SQLFavoriteManager.shared.fetchFavorite(id:).
  • resolveSavedQueryAttachment(id:fallbackName:) formats the cached favorite as ## Saved Query: <name>\n\``sql\n\n````.
  • loadSavedQueries() populates a per-connection list. The chat panel's .task(id: connection.id) invokes it on open and on connection change.
  • mentionCandidates(forQuery:) includes saved queries (filtered by name, alphabetical) sharing the popover budget with tables (each gets up to half of the 10-slot cap).

5b — User-defined slash commands

  • CustomSlashCommand model (Codable, Identifiable): id, name, description, promptTemplate.
  • CustomSlashCommandStorage is @Observable @MainActor, persists to UserDefaults under ai.customSlashCommands.v1, and exposes add / update / delete / command(named:).
  • CustomSlashCommandRenderer does mechanical placeholder substitution — {{query}}, {{schema}}, {{database}}, {{body}}. Unknown placeholders pass through unchanged.
  • AIChatViewModel.runCustomSlashCommand(_:body:) mirrors the built-in slash command flow: appends an invocation ChatTurn, renders the template, sends through sendWithContext.
  • The composer's slash menu now lists built-ins, then a Custom section with the user's commands. Items hide when command.isValid is false (empty name or template).
  • Settings: CustomSlashCommandsSection slots into AISettingsView between the existing context section and privacy section. List rows show /<name> · description with Edit and Delete actions; an editor sheet handles add/edit with name, description, and a multi-line template field. Footer documents the available variables.

Schema as a substitution variable

{{schema}} is currently passed nil in runCustomSlashCommand because rendering the schema synchronously is awkward (it requires the column/foreign-key data we fetch on demand). For v1, users who want schema in their template should attach the schema chip via @Schema and reference it in the message naturally. A followup can wire ensureSchemaLoaded + AISchemaContext.buildSchemaSection into the renderer if that turns out to be a common pattern.

Risk

Low. New surface area is additive — no existing flows changed shape.

  • ContextItem.savedQuery enum case shape changed (UUID(UUID, String)). Decoder defaults name to empty for older payloads, which then resolves through the chip's fallbackName path. No persisted-data breakage.
  • Custom commands persist to a fresh UserDefaults key; no migration needed.

CHANGELOG

Two new [Unreleased] / Added lines covering 5a and 5b.

Lint

swiftlint lint --strict clean across all 817 files.

Test plan

  • Save 2-3 favorites for a connection. Open chat, type @, pick one. Chip shows the favorite's name. Send. AI receives the SQL.
  • Open Settings -> AI -> Custom Slash Commands. Click Add. Name review, description SQL injection check, template Review this query for SQL injection: {{query}}. Save.
  • In chat with editor query open, click the slash menu, pick /review. Confirm AI receives the rendered prompt with the editor query substituted.
  • Edit the command from settings; confirm slash menu picks up the change.
  • Delete the command; confirm it disappears from the slash menu.
  • Restart the app; confirm both saved chips (when re-attached) and custom commands persist.

Umbrella status

This closes the implementation scope of #1047. Remaining followups (separate issues): write-side tools with safe-mode flow, Apple Intelligence transport (#1048), token cost surfacing.

@chatgpt-codex-connector
Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@datlechin datlechin merged commit 1256927 into main May 7, 2026
2 checks passed
@datlechin datlechin deleted the feat/chat-saved-queries-and-custom-slash branch May 7, 2026 07:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant