cherri
Skill0 starsChanged 43 days agoMITView on GitHub
The Cherri programming language - write, compile, and debug iOS Shortcuts as code (.cherri files). Use for ANY task touching a .cherri file or a Shortcuts-as-code repo, writing or modifying an iOS/macOS Shortcut programmatically, or questions about Cherri syntax, actions, includes, glyphs, or compile errors. Bundles the complete cherrilang.org/language docs as local references - consult them instead of guessing syntax or searching the web.
In this repository34 other files it gives its agents.
- afkSkill
- apple-contactsSkill
- apple-devSkill
- apple-notesSkill
- apple-photosSkill
- bug-huntSkill
- catch-upSkill
- chrome-controlSkill
- claude-sessionsSkill
- coordinatorSkill
- discountsSkill
- forge-skillSkill
- groupmeSkill
- herdr-crewSkill
- iconsSkill
- imsgSkill
- language-selectionSkill
- laterSkill
- mac-controlSkill
- nix-mechanicsSkill
- notion-cliSkill
- posthogSkill
- quotaSkill
- redditSkill
- rustSkill
- scoutSkill
- semverSkill
- social-contentSkill
- spotifySkill
- travelSkill
- validate-ideaSkill
- verdictSkill
- web-reconSkill
- whatsappSkill
The file
We split this skill into the rules it gives an agent
1 rule. About 0 are common, 1 is distinctive, and 0 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈1
Distinctive · estimate
This author's own choices. Worth a look.
0
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Distinctive: line 62
Read the file matching the problem, per the table below.
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
Cherri
Last updated: 2026-08-11 (docs synced from cherrilang.org source repo). If today is more than 3 months past this date, offer to run Self-Update.
Cherri is a language that compiles to .shortcut files for the Apple Shortcuts app. If the shortcuts live in a dedicated repo, see that repo's AGENTS.md for repo-specific mechanics (secrets/constants pipeline, folder layout).
Toolchain
With the cherri binary installed, it is self-documenting - use these before reaching for the references:
cherri file.cherri --skip-sign # compile (unsigned; signing needs contact with Apple servers)
cherri --action=showNotification # full docs for one action (any action, incl. required include)
cherri --glyph=music # validate/suggest icon glyph names
cherri --docs=<query> # search the documentation
cherri file.cherri -d # also emit the .plist - grep it to verify compiled actionsA shortcuts repo can wrap compilation (placeholder substitution for constants and secrets, plist post-patches); follow its AGENTS.md. When placeholders resolve from a secret store your shell cannot read, compile-validate a scratch copy with the placeholders replaced by dummies:
sed -E -e 's|<<(secret|constant):([A-Za-z_0-9]+)>>|DUMMY_\2|g' file.cherri > /tmp/check.cherri && cherri /tmp/check.cherri --skip-signSyntax cheat sheet
#define name My Shortcut // metadata directives first
#define color blue
#define glyph shazam // must be a valid glyph - verify with cherri --glyph=
#define from sharesheet // accepts share-sheet input (read via ShortcutInput global)
#include 'actions/web' // most actions need an include; the compile error names it
@mutable = "value" // variables; interpolate with "{mutable}"
const Fixed = getName(@x) // immutable; fewer compiled actions
@declared: text // type-only declaration (assign later, e.g. in if branches)
if @textVar == "yes" && @other contains "x" { ... } else { ... }
repeat i for 20 { ... } // count can be a variable
for item in @list { ... }Gotchas (hard-won - read before writing code)
- HTTP responses are not dictionaries.
jsonRequest/formRequest/downloadURLreturn "Contents of URL".@resp['key']compiles to an inline aggrandizement that silently reads NOTHING at runtime. Always coerce:@d = getDictionary(@resp)thengetValue(@d, "key"). Walk nested keys one level at a time (no dotted paths), and coerce list items too:getDictionary(getFirstItem(...)). Verify with-d: the .plist should showdetect.dictionary+getvalueforkey;WFPropertyVariableAggrandizementon a response means it's broken. - Conditions require
@on variables (if @var == "x"), despite doc examples showing bare names. The compiler errors otherwise. containsText()hardcodes a^anchor onto its pattern - prepend.*for a real contains match. Thecontainsconditional operator has no such quirk.- Missing include? The compile error names the exact
#includeto add. Core actions (showNotification,alert,prompt, …) need none. show()blocks the flow with a modal;showNotification(body, ?title)is async - prefer notifications for fire-and-forget status.- JSON
nullreads back as empty text -"{value}"of a null is"", testable withif !@var. nothing()after unused action outputs frees runtime memory; statement blocks add it automatically at their end.- File-typed form values are inexpressible in cherri v2.3 - dictionary items only support text/number/bool/array/dict, so a multipart file upload (
formRequestwith a file field) compiles to an empty form value that silently uploads nothing. The working structure isWFItemType: 5+WFTokenAttachmentParameterState; post-patch the compiled plist into that shape in your compile pipeline. embedFile()resolves paths relative to cherri's CWD, not the source file - run the compiler from the.cherrifile's directory or asset references likeassets/foo.mp3fail when compiling from the repo root. (base64Filefrom the docs doesn't exist in cherri v2.3; the action isembedFile.)
References (complete cherrilang.org/language docs, local)
Read the file matching the problem, per the table below.
| Topic | File |
Variables, constants, globals (ShortcutInput, …) | references/variables-constants-globals.md |
| If/else, repeat, for, menus | references/control-flow.md, references/menus.md |
| Types, enums, operators, functions | references/types.md, references/enums.md, references/operators.md, references/functions.md |
Metadata #defines (name, color, glyph, from…) | references/definitions.md |
| Includes & the package manager | references/includes.md, references/package-manager.md |
| Custom action definitions | references/action-definitions.md |
| Raw actions (use any Shortcuts action Cherri lacks) | references/raw-actions.md |
| Copy-paste blocks, import questions/actions, vcards | references/copy-paste.md, references/import-questions.md, references/import-actions.md, references/vcards.md |
| Best practices (performance, memory) | references/best-practices.md |
| Standard actions by category (web, media, text, device, scripting-ish basics, macOS-only, …) | references/standard/*.md - e.g. web.md, media.md, text.md, basic.md, builtin.md, stdlib.md |
Self-Update
- Re-download the docs: list
language/andlanguage/standard/inelectrikmilk/cherrilang.org(gh api repos/electrikmilk/cherrilang.org/contents/language), fetch each.mdfromhttps://raw.githubusercontent.com/electrikmilk/cherrilang.org/main/language/..., strip the Jekyll frontmatter/TOC, and write them intoreferences/(same filenames,standard/subdir preserved). - Skim the changelog/releases since the Last-updated date; fold breaking syntax changes into the cheat sheet and gotchas.
- Bump the Last-updated date.
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

