Problem
Total Recall is purely reactive — you have to open the window and look. There's no way to be notified when a specific app balloons or when system pressure escalates, so memory problems often go unnoticed until the machine becomes sluggish.
Proposed Solution
Let users define alert rules that fire macOS notifications via UNUserNotificationCenter. Alerts are created contextually by right-clicking any group row in the main list — no separate settings screen needed to get started.
Context Menu UX
Right-clicking a group row opens the existing context menu, extended with an Alerts submenu. The submenu is context-aware: it shows the group's current memory, pre-computed suggestions, and any already-active alerts for that group.
Example — right-clicking Google Chrome at 1.2 GB:
Google Chrome
──────────────────────────────
Copy PID
Quit
Force Quit
──────────────────────────────
Alerts
├─ Alert if Chrome exceeds 1.3 GB (+10% — add) ← suggested
├─ Alert if Chrome exceeds 1.5 GB (+25% — add) ← suggested
├─ Alert if Chrome exceeds 2.0 GB (add) ← suggested round number
└─ Alert if pressure goes Warning (add) ← system-level suggestion
If alerts already exist for the group, they appear at the top of the submenu with a checkmark and a "Remove" action:
Alerts
├─ ✓ Chrome > 1.3 GB [Remove]
├─ Add: Chrome > 1.5 GB
└─ Add: Chrome > 2.0 GB
Suggested Thresholds (auto-computed from current footprint)
| Suggestion |
Threshold |
| "+10%" |
currentFootprint × 1.10, rounded to nearest 100 MB |
| "+25%" |
currentFootprint × 1.25, rounded |
| "Round number" |
Next round GB boundary above current (e.g. current=1.2 GB → suggest 2 GB) |
| "Pressure Warning" |
System-level, always shown regardless of which group is right-clicked |
| "Pressure Critical" |
System-level, always shown |
Alert Rule Model
struct AlertRule: Codable, Identifiable {
let id: UUID
var groupIdentifier: String? // nil = any group / system-level
var groupDisplayName: String // for display in notifications
var metric: AlertMetric // .footprint, .resident, .pressureLevel
var threshold: UInt64 // bytes, or pressure level raw value
var cooldownMinutes: Int // default 5
var createdAt: Date
}
enum AlertMetric: String, Codable {
case footprint, resident, pressureLevel
}
Rules are stored in UserDefaults (small, no file I/O needed). Evaluated inside the existing AppState refresh loop on every full poll tick.
Notification Behavior
- Use
UNUserNotificationCenter; request authorization on first rule creation
- Notification title:
"Total Recall: \(groupName)", body: "Memory footprint reached \(formatted threshold)"
- Per-rule cooldown (default 5 min) prevents spam — store
lastFiredAt alongside the rule
- Tapping the notification brings the Total Recall window to front with that group selected
Implementation Notes
- Add
AlertRule and AlertStore to TotalRecallCore/DataLayer/
- Extend the context menu in
GroupRowView / ProcessRowView with the Alerts submenu
- Threshold suggestions computed at menu-build time from the group's current
physFootprint
AlertStore exposes rules(for groupIdentifier:) so the submenu can show existing alerts inline
- A full Alerts management UI (list/edit/delete all rules) can be a follow-up; the context menu covers the primary add flow
Problem
Total Recall is purely reactive — you have to open the window and look. There's no way to be notified when a specific app balloons or when system pressure escalates, so memory problems often go unnoticed until the machine becomes sluggish.
Proposed Solution
Let users define alert rules that fire macOS notifications via
UNUserNotificationCenter. Alerts are created contextually by right-clicking any group row in the main list — no separate settings screen needed to get started.Context Menu UX
Right-clicking a group row opens the existing context menu, extended with an Alerts submenu. The submenu is context-aware: it shows the group's current memory, pre-computed suggestions, and any already-active alerts for that group.
Example — right-clicking Google Chrome at 1.2 GB:
If alerts already exist for the group, they appear at the top of the submenu with a checkmark and a "Remove" action:
Suggested Thresholds (auto-computed from current footprint)
currentFootprint × 1.10, rounded to nearest 100 MBcurrentFootprint × 1.25, roundedAlert Rule Model
Rules are stored in
UserDefaults(small, no file I/O needed). Evaluated inside the existingAppStaterefresh loop on every full poll tick.Notification Behavior
UNUserNotificationCenter; request authorization on first rule creation"Total Recall: \(groupName)", body:"Memory footprint reached \(formatted threshold)"lastFiredAtalongside the ruleImplementation Notes
AlertRuleandAlertStoretoTotalRecallCore/DataLayer/GroupRowView/ProcessRowViewwith the Alerts submenuphysFootprintAlertStoreexposesrules(for groupIdentifier:)so the submenu can show existing alerts inline