Data Storage¶
Where Patcher writes on your Mac, and how to inspect, modify, or reset each piece.
Application Support Directory¶
Everything Patcher writes outside of the keychain and the patch-data cache lives under ~/Library/Application Support/Patcher/:
~/Library/Application Support/Patcher/
├── com.liquidzoo.patcher.plist # Configuration (this page)
├── .labels/ # Cached label scripts
├── unmatched_apps.json # Titles with no label match
├── fonts/ # Custom PDF report fonts (if any)
├── logo.png # Custom PDF report logo (if any)
└── logs/ # LaunchAgent stdout/stderr (if scheduled)
To wipe this directory entirely, use patcherctl reset full. To wipe just the patch-data cache (separate location, see below), use patcherctl reset cache.
Property List File¶
The property list at ~/Library/Application Support/Patcher/com.liquidzoo.patcher.plist stores persistent configuration such as UI customization for PDF/HTML reports, setup state, and integration toggles.
UserInterfaceSettingsUI settings dict
header_textHeader text
footer_textFooter text
font_nameFont name
reg_font_pathRegular font path
bold_font_pathBold font path
logo_pathLogo path
header_colorHTML header color
setup_completedSetup completion
enable_installomatorInstallomator toggle
interpreter_pathPython interpreter path initially used to store credentials in Keychain
See also
For customization commands, see customizing reports.
Installomator Toggle¶
The enable_installomator boolean controls whether Patcher matches Jamf titles against Installomator labels. When false, the package skips Installomator-sourced matching entirely on every invocation. See Disabling Installomator Matching for the full behavior breakdown and the command to flip it.
Full Example¶
<?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>UserInterfaceSettings</key>
<dict>
<key>header_text</key>
<string>AnyOrg Patch Report</string>
<key>footer_text</key>
<string>Made with <3 from IT</string>
<key>font_name</key>
<string>Assistant</string>
<key>reg_font_path</key>
<string>/Users/jappleseed/Library/Application Support/Patcher/fonts/Assistant-Regular.ttf</string>
<key>bold_font_path</key>
<string>/Users/jappleseed/Library/Application Support/Patcher/fonts/Assistant-Bold.ttf</string>
<key>header_color</key>
<string>#6432bdff</string>
<key>logo_path</key>
<string>/Users/jappleseed/Library/Application Support/Patcher/logo.png</string>
</dict>
<key>setup_completed</key>
<true/>
<key>enable_installomator</key>
<true/>
<key>interpreter_path</key>
<string>/usr/local/bin/managed_python3</string>
</dict>
</plist>
Patch Data Cache¶
Patch report data fetched from Jamf is cached at ~/Library/Caches/Patcher/. This lets Patcher’s analysis reuse the latest report without re-fetching it, and it’s what trend analysis reads across when comparing multiple snapshots over time.
Note
To skip caching entirely on a per-invocation basis, construct PatcherClient with disable_cache=True.
Credentials in Keychain¶
Jamf credentials live in the macOS login keychain under the service name Patcher:
Account |
Value |
|---|---|
|
Jamf Pro instance URL |
|
Jamf API client ID |
|
Jamf API client secret |
|
Current OAuth access token (managed by Patcher) |
|
Token expiration timestamp (managed by Patcher) |
The CLI’s setup wizard writes the first three and the TokenManager manages the last two automatically.
Security
Patcher stores these values on disk in plaintext. Both the client secret and bearer token are wrapped in pydantic.SecretStr so accidental repr, model_dump, or traceback rendering shows the masked placeholder rather than the secret. Library code reaching the raw value calls .get_secret_value() explicitly (see PatcherClient.fetch_patches and the OAuth refresh path in TokenManager.fetch_token).