Shell runs a script you approve.
Version 1.33.0 ·
An agent can run one script under Cupertino's grants once you click Run once by hand, and Safari can submit forms, wait for pages, and tell a dead extension from an idle one.
Share this release
Shell runs a script you approve. An agent can run one script under Cupertino's grants once you click Run once by hand, and Safari can submit forms, wait for pages, and tell a dead extension from an idle one. https://cupertino.mgcrea.io/changelog/1.33.0/
Added
Experimental: Mail and Messages serve the draft MCP Events extension.
events/list,events/pollandevents/streamoffermail.receivedandmessages.receivedevents, by poll with a cursor or pushed over stdio, following SEP-3415. Off by default behindAPPLE_MAIL_ALLOW_EVENTSandAPPLE_MESSAGES_ALLOW_EVENTS, and served on the 2026-07-28 protocol only. The arguments are the watch filter, a sender is required, and an event carries envelope metadata only. Watches are unchanged. The extension is a draft and no client consumes it yet, Claude Code included.Safari can submit a form and wait for a page.
apple_safari_submitsubmits the form an element belongs to, as pressing Enter would, after the form's own validation, and names the fields that fail it.apple_safari_wait_forwaits until some text appears on a page, or leaves it.apple_safari_page_elementstakesquery,kindandinViewOnly, applied before its cap.read_page,page_elements,find_codesandwait_forread the frontmost tab when nourlis given.Shell: an agent can run a script with Cupertino's access, after you approve it.
apple_shell_runruns one script, in zsh, bash, python3, node, AppleScript or JXA, as Cupertino's own child, so it holds every grant Cupertino holds, Full Disk Access among them when Cupertino has it. Before each run a window shows you the whole script and the agent's reason. Don't run is the default, Return and Escape mean it, and only a click by hand on Run once runs it, so VoiceOver can't approve a run. You can let a connection stop asking for 30 minutes, or turn asking off, and a run with no window still shows a card you can stop it from. Shell arrives off, and turning it on, or turning asking off, takes a confirming click that another program can't fake by writing Cupertino's preferences. Every request, refusals included, leaves a line in a run record that keeps a hash of the script and never its text or output. Timeouts, Esc in the client and quitting Cupertino stop the script and everything still in its process group. Scripts start without your shell startup files, with the system's PATH plus Homebrew's, so an interpreter from nvm or pyenv needs the script to set it up, where the window shows it. See docs/shell.md.
Changed
Safari matches more open tabs to history. A tab whose history row only exists with a query added (
/plus5beside/plus5?variant=…) now matches, ashistoryMatch: "query-added".Safari pulls large network bodies faster by queueing the next chunks instead of waiting a second between each, and
read_pageno longer parses every stored capture to find one.
Fixed
Safari diagnostics no longer call a dead extension working.
workingwas true whenever the extension had ever run, including beside a newest capture 7.5 hours old. The extension now stamps a heartbeat per site while a page is open, and diagnostics report astate(never-ran,never-captured,stale,capturing,answering), which sites are answering, and what the server cannot tell apart.read_pageandpage_elementsnow say which case a timeout is: the extension running nowhere, running but not on this site, or running on this site with no page on that exact URL. A site set to Deny, or an extension switched off, in the half minute before the command is named as having just stopped, not as still running.A Debug build of the app no longer updates itself into a second copy of the release. The copy registered the Safari extension a second time, and Safari ran no Cupertino extension until the extra copies were removed.