Install any skill in seconds. Free to start, no credit card required.
Get Started Free →Generates, validates, and installs macOS LaunchAgent plist files for scheduling recurring tasks and daemons. Triggered when a user asks to create a LaunchAgent, schedule a script, automate a recurring macOS task, or set up a background daemon. Uses the com.berna namespace and validates plist syntax before writing. Always confirms before loading.
| Test case | Without → With | Effect | Δ tokens | Δ turns |
|---|---|---|---|---|
| case-01 | ✗→✓ | ▲ Improved | 106% | 0% |
| case-02 | ✗→✓ | ▲ Improved | 71% | 0% |
| case-03 | ✗→✓ | ▲ Improved | 87% | 0% |
| case-07 | ✗→✓ | ▲ Improved | 86% | 0% |
| case-09 | ✗→✓ | ▲ Improved | 50% | 0% |
Generate, validate, and install macOS LaunchAgent plist files for scheduled tasks and daemons.
All agents use the com.berna. namespace:
com.berna.<descriptive-name>.plistExamples:
com.berna.secret-scanner-daily.plistcom.berna.wispr-flow-watchdog.plistcom.berna.git-backup-hourly.plistThe Label value inside the plist MUST match the filename (minus .plist).
Gather these inputs from the user (or infer from context):
| Parameter | Required | Default | |--------------------|----------|--------------------------------------------| | Script path | Yes | — | | Schedule type | Yes | interval or calendar | | Interval (seconds) | If interval | — | | Calendar day | If calendar | — (0=Sun, 1=Mon, …, 6=Sat) | | Calendar hour | If calendar | — | | Calendar minute | If calendar | 0 | | Log output path | No | ~/Reports/maintenance/<name>.log | | KeepAlive | No | false (true for daemons) | | RunAtLoad | No | true | | Environment vars | No | — | | WatchPaths | No | — (for file-triggered agents) |
xml<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> <plist version="1.0"> <dict> <key>Label</key> <string>com.berna.AGENT_NAME</string> <key>ProgramArguments</key> <array> <string>/bin/bash</string> <string>/path/to/script.sh</string> </array> <key>StartInterval</key> <integer>SECONDS</integer> <key>RunAtLoad</key> <true/> <key>StandardOutPath</key> <string>/Users/bbmisa/Reports/maintenance/AGENT_NAME.log</string> <key>StandardErrorPath</key> <string>/Users/bbmisa/Reports/maintenance/AGENT_NAME.log</string> </dict> </plist>
Replace StartInterval with:
xml<key>StartCalendarInterval</key> <dict> <key>Hour</key> <integer>HOUR</integer> <key>Minute</key> <integer>MINUTE</integer> <!-- Optional: Day (0=Sunday), Weekday, Month --> </dict>
For multiple schedules, use an array of dicts:
xml<key>StartCalendarInterval</key> <array> <dict> <key>Hour</key> <integer>9</integer> <key>Minute</key> <integer>0</integer> </dict> <dict> <key>Hour</key> <integer>17</integer> <key>Minute</key> <integer>0</integer> </dict> </array>
KeepAlive (for daemons):
xml<key>KeepAlive</key> <true/>
Environment Variables:
xml<key>EnvironmentVariables</key> <dict> <key>PATH</key> <string>/opt/homebrew/bin:/usr/local/bin:/usr/bin:/bin</string> <key>CUSTOM_VAR</key> <string>value</string> </dict>
WatchPaths (file-triggered):
xml<key>WatchPaths</key> <array> <string>/path/to/watched/file</string> </array>
Always validate the plist before writing:
bashplutil -lint /path/to/generated.plist
Expected output: <file>: OK
If validation fails, fix the XML and re-validate before proceeding.
bash# Ensure target directory exists mkdir -p ~/Library/LaunchAgents # Write the plist (tool writes the file) # Target: ~/Library/LaunchAgents/com.berna.<name>.plist
bashlaunchctl load ~/Library/LaunchAgents/com.berna.<name>.plist
bashlaunchctl list | grep com.berna.<name>
A successful load shows the agent with a PID (if running) or status code.
bashlaunchctl list | grep com.berna
bashlaunchctl unload ~/Library/LaunchAgents/com.berna.<name>.plist
bashlaunchctl unload ~/Library/LaunchAgents/com.berna.<name>.plist launchctl load ~/Library/LaunchAgents/com.berna.<name>.plist
bashtail -f ~/Reports/maintenance/<name>.log
bashlaunchctl list | grep com.berna.<name> # Column 1: PID (- if not running), Column 2: last exit status (0 = success)
| Schedule | StartInterval | StartCalendarInterval | |----------------|---------------|--------------------------------| | Every 5 min | 300 | — | | Every 30 min | 1800 | — | | Every hour | 3600 | — | | Daily at 9 AM | — | Hour: 9, Minute: 0 | | Weekdays 8 AM | — | Weekday: 1-5, Hour: 8 | | Weekly Sunday | — | Weekday: 0, Hour: 3 | | Monthly 1st | — | Day: 1, Hour: 0 |
plutil -lint before writing to ~/Library/LaunchAgents/mkdir -p ~/Reports/maintenance before setting log paths/opt/homebrew/bin in PATHOther measured skills in the registry, with their headline benchmark lift.