Puts a VIDEO OR IMAGE FILE FROM THE USER'S OWN MACHINE onto their aicut account so the generation tools can use it (every other tool takes a URL). It returns an upload target in two forms, a ready-to-run `curl_template` for you and a `browser_upload_url` for the user; then you call `confirm_upload`. A FILE IN THE AICUT SANDBOX (`sandbox_exec`) IS THE EXCEPTION to the two warnings here: call this, then run the `curl_template` INSIDE `sandbox_exec`, which reaches `upload.host`. CANNOT RUN A SHELL COMMAND ON THE USER'S OWN MACHINE (claude.ai, ChatGPT, Claude Desktop, the mobile apps)? YOU ARE ON THE WRONG TOOL: call `upload_media_widget` and stop. This tool is for an agent that can run a command there (Claude Code, Cursor, a terminal, a script). WHEN: the user refers to a file on their computer ('upscale the clip in my Downloads'). NOT when it is already a URL (public https, or an earlier generation): pass that straight to the tool that needs it. TWO ROUTES, PICK BEFORE YOU START. The `curl_template` needs your environment to reach `upload.host`; a SANDBOXED CODE ENVIRONMENT (claude.ai's code sandbox) CANNOT (the curl dies with HTTP code `000`; no retry fixes it): there, DO NOT RUN THE CURL: give the user the `browser_upload_url` as a link, say in one line that opening it lets their own browser send the file, wait for them to say it is done, then `confirm_upload`. On the user's own machine (Claude Code, Cursor, a terminal) run the curl. Never report an upload that did not happen. SEQUENCE: (1) `upload_media` with the file's content type and size in bytes; (2) move the bytes by exactly one route: run the `curl_template` with the real path for `<FILE_PATH>` (it prints the body, then an HTTP status; 204 with an empty body is success) or hand the user `browser_upload_url` and wait; (3) `confirm_upload` with the `id`. The `url` is not real media until the confirm returns: never pass it to a generation tool before then. `browser_upload_url`: an aicut page where the user picks the file; 15 minutes, retryable, carries no key, cannot spend; private. PUT IT IN A MARKDOWN LINK, EXACTLY ONCE, NEVER AS TEXT: it is about 900 characters of base64, so write `[Open the upload page](<the whole url>)` with short anchor text (everything after the `#` IS the upload, so the whole url goes inside the parentheses). DO NOT REPEAT IT: if they have not finished, say so in one line without the link, and do not call `upload_media` again (a second call within 15 minutes with the SAME type and size returns the SAME target). SUBSTITUTING THE PATH IS YOUR RESPONSIBILITY: it is a shell command on the USER'S OWN MACHINE. `<FILE_PATH>` sits inside single quotes, so an ordinary path pastes as-is, but a path containing a SINGLE QUOTE would break out and run whatever follows: quote it properly or have the user rename the file. ACCEPTED TYPES: `video/mp4` and `video/quicktime` up to 50 MB (an MP4 up to 500 MB from the sandbox while a studio run is open); `image/png`, `image/jpeg` and `image/webp` up to 20 MB. WebM, AVIF, HEIC, TIFF and GIF are not accepted: re-encode to MP4 or PNG / JPEG. `bytes` MUST BE THE FILE'S REAL SIZE, read off disk (`stat -c%s` on Linux, `stat -f%z` on macOS): it is signed as a hard limit and charged against the daily media allowance. Costs no tokens. OUTPUT: `browser_upload_url` is the ONE url that may reach the conversation (browser route only, as a markdown link). `url` serves nothing until `confirm_upload` returns: never show or pass it. Do not paste the raw JSON, the reservation id, the signed fields or the curl command.