Skip to content

Fix actor isolation crash on macOS 26 (Tahoe)#2

Closed
nickj wants to merge 1 commit into
openclaw:mainfrom
nickj:fix/macos26-actor-isolation
Closed

Fix actor isolation crash on macOS 26 (Tahoe)#2
nickj wants to merge 1 commit into
openclaw:mainfrom
nickj:fix/macos26-actor-isolation

Conversation

@nickj
Copy link
Copy Markdown

@nickj nickj commented Jan 6, 2026

Summary

Fixes the crash reported in #1 where any command accessing reminders fails with:

Incorrect actor executor assumption; expected 'RemindCore.RemindersStore' executor.

Root Cause

The fetchReminders callback from EventKit.fetchReminders(matching:) runs on an arbitrary thread. Inside that callback, we were calling self.item(from: reminder) which accesses actor-isolated state (self.calendar). Swift 6's strict concurrency checking enforces this at runtime on macOS 26.

Fix

Capture the calendar before entering the callback closure, then use it directly inside. This avoids accessing actor-isolated state from the non-isolated callback context.

Before:

eventStore.fetchReminders(matching: predicate) { reminders in
  let mapped = (reminders ?? []).map { reminder in
    self.item(from: reminder)  // ❌ Accesses actor from wrong executor
  }
  continuation.resume(returning: mapped)
}

After:

let cal = self.calendar  // ✅ Capture on actor executor
eventStore.fetchReminders(matching: predicate) { reminders in
  let mapped = (reminders ?? []).map { reminder in
    ReminderItem(
      // ... use captured `cal` instead of self.calendar
    )
  }
  continuation.resume(returning: mapped)
}

Testing

  • All existing tests pass
  • Manually verified on macOS 26.2 (Tahoe) with Swift 6.2.3
  • remindctl list, remindctl today, remindctl upcoming all work correctly

Fixes #1

The fetchReminders callback from EventKit runs on an arbitrary thread,
but was accessing actor-isolated state (self.item(from:)) which causes
a runtime crash in Swift 6's strict concurrency checking.

Fix: Capture the calendar before entering the callback, then use it
directly inside to avoid actor isolation violations.

Fixes openclaw#1
@steipete
Copy link
Copy Markdown
Collaborator

Thank you! Reviewing...

@steipete
Copy link
Copy Markdown
Collaborator

Thanks! Closing in favor of #3 (merged). #3 keeps the callback boundary Sendable-only and does ReminderItem construction back on the actor.

@steipete steipete closed this Jan 11, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Crash on macOS 26 (Tahoe): Incorrect actor executor assumption

2 participants