Files
daily-notification-plugin/docs/plugin-behavior-exploration-template.md
Matthew Raymer 6aa9140f67 docs: add comprehensive alarm/notification behavior documentation
- Add platform capability reference (Android & iOS OS-level facts)
- Add plugin behavior exploration template (executable test matrices)
- Add plugin requirements & implementation directive
- Add Android-specific implementation directive with detailed test procedures
- Add exploration findings from code inspection
- Add improvement directive for refining documentation structure
- Add Android alarm persistence directive (OS capabilities)

All documents include:
- File locations, function references, and line numbers
- Detailed test procedures with ADB commands
- Cross-platform comparisons
- Implementation checklists and code examples
2025-11-21 07:30:25 +00:00

16 KiB

Plugin Behavior Exploration Template

Author: Matthew Raymer
Date: November 2025
Status: Active Exploration Template

Purpose

This document provides an executable template for exploring and documenting the current plugin's alarm/schedule/notification behavior on Android and iOS.

Use this template to:

  1. Test plugin behavior across different scenarios
  2. Document expected vs actual results
  3. Identify gaps between current behavior and platform capabilities
  4. Generate findings for the Plugin Requirements document

Reference: See Platform Capability Reference for OS-level facts.


0. Quick Reference: Platform Capabilities

Android: See Platform Capability Reference - Android Section

iOS: See Platform Capability Reference - iOS Section

Key Differences:

  • Android: Alarms wiped on reboot; must reschedule
  • iOS: Notifications persist across reboot automatically
  • Android: App code runs when alarm fires
  • iOS: App code does NOT run when notification fires (unless user interacts)

1. Android Exploration

1.1 Code-Level Inspection Checklist

Source Locations:

  • Plugin: android/src/main/java/com/timesafari/dailynotification/
  • Test App: test-apps/android-test-app/
  • Manifest: test-apps/android-test-app/app/src/main/AndroidManifest.xml
Task File/Function Line Status Notes
Locate main plugin class DailyNotificationPlugin.kt 1302 scheduleDailyNotification()
Identify alarm scheduling NotifyReceiver.kt 92 scheduleExactNotification()
Check AlarmManager usage NotifyReceiver.kt 219, 223, 231 setAlarmClock(), setExactAndAllowWhileIdle(), setExact()
Check WorkManager usage FetchWorker.kt 31 scheduleFetch()
Check notification display DailyNotificationWorker.java 200+ displayNotification()
Check boot receiver BootReceiver.kt 24 onReceive() handles BOOT_COMPLETED
Check persistence DailyNotificationPlugin.kt 1393+ Room database storage
Check exact alarm permission DailyNotificationPlugin.kt 1309 canScheduleExactAlarms()
Check manifest permissions AndroidManifest.xml - RECEIVE_BOOT_COMPLETED, SCHEDULE_EXACT_ALARM

1.2 Behavior Testing Matrix

Test 1: Base Case

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule alarm 2 minutes in future - Alarm scheduled
2 Leave app in foreground/background - -
3 Wait for trigger time Alarm fires Notification displayed
4 Check logs - No errors

Code Reference: NotifyReceiver.scheduleExactNotification() line 92


Test 2: Swipe from Recents

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule alarm 2-5 minutes in future - Alarm scheduled
2 Swipe app away from recents - -
3 Wait for trigger time Alarm fires (OS resurrects process) Notification displayed
4 Check app state on wake Cold start App process recreated
5 Check logs - No errors

Code Reference: NotifyReceiver.scheduleExactNotification() uses setAlarmClock() line 219

Platform Behavior: OS-guaranteed (Android AlarmManager)


Test 3: OS Kill (Memory Pressure)

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule alarm 2-5 minutes in future - Alarm scheduled
2 Force kill via adb shell am kill <package> - -
3 Wait for trigger time Alarm fires Notification displayed
4 Check logs - No errors

Platform Behavior: OS-guaranteed (Android AlarmManager)


Test 4: Device Reboot

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule alarm 10 minutes in future - Alarm scheduled
2 Reboot device - -
3 Do NOT open app Alarm does NOT fire No notification
4 Wait past scheduled time No automatic firing No notification
5 Open app manually - Plugin detects missed alarm
6 Check missed alarm handling - Missed alarm detected
7 Check rescheduling - Future alarms rescheduled

Code Reference:

  • Boot receiver: BootReceiver.kt line 24
  • Rescheduling: BootReceiver.kt line 38+

Platform Behavior: Plugin-guaranteed (must implement boot receiver)

Expected Plugin Behavior: Plugin must reschedule from database on boot


Test 5: Android Force Stop

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule alarm - Alarm scheduled
2 Go to Settings → Apps → [App] → Force Stop All alarms removed All alarms removed
3 Wait for trigger time Alarm does NOT fire No notification
4 Open app again - Plugin detects missed alarm
5 Check recovery - Missed alarm detected
6 Check rescheduling - Future alarms rescheduled

Platform Behavior: Not allowed (Android hard kill)

Expected Plugin Behavior: Plugin must detect and recover on app restart


Test 6: Exact Alarm Permission (Android 12+)

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Revoke exact alarm permission - -
2 Attempt to schedule alarm - Plugin requests permission
3 Check settings opened - Settings opened
4 Grant permission - -
5 Schedule alarm - Alarm scheduled
6 Verify alarm fires Alarm fires Notification displayed

Code Reference: DailyNotificationPlugin.kt line 1309, 1314-1324


1.3 Persistence Investigation

Item Expected Actual Code Reference Notes
Alarm ID stored Yes DailyNotificationPlugin.kt line 1393+
Trigger time stored Yes Room database
Repeat rule stored Yes Schedule entity
Channel/priority stored Yes NotificationContentEntity
Payload stored Yes ContentCache
Time created/modified Yes Entity timestamps

Storage Location: Room database (DailyNotificationDatabase)


1.4 Recovery Points Investigation

Recovery Point Expected Behavior Actual Behavior Code Reference Notes
Boot event Reschedule all alarms BootReceiver.kt line 24
App cold start Detect missed alarms Check plugin initialization
App warm start Verify active alarms Check plugin initialization
Background fetch return ⚠️ May reschedule FetchWorker.kt
User taps notification Launch app Notification intent

2. iOS Exploration

2.1 Code-Level Inspection Checklist

Source Locations:

  • Plugin: ios/Plugin/
  • Test App: test-apps/ios-test-app/
  • Alternative: Check ios-2 branch
Task File/Function Line Status Notes
Locate main plugin class DailyNotificationPlugin.swift 506 scheduleUserNotification()
Identify notification scheduling DailyNotificationScheduler.swift 133 scheduleNotification()
Check UNUserNotificationCenter usage DailyNotificationScheduler.swift 185 notificationCenter.add()
Check trigger types DailyNotificationScheduler.swift 172 UNCalendarNotificationTrigger
Check BGTaskScheduler usage DailyNotificationPlugin.swift 495 scheduleBackgroundFetch()
Check persistence DailyNotificationPlugin.swift 35 storage: DailyNotificationStorage?
Check app launch recovery DailyNotificationPlugin.swift 42 load() method

2.2 Behavior Testing Matrix

Test 1: Base Case

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule notification 2-5 minutes in future - Notification scheduled
2 Leave app backgrounded - -
3 Wait for trigger time Notification fires Notification displayed
4 Check logs - No errors

Code Reference: DailyNotificationScheduler.scheduleNotification() line 133


Test 2: Swipe App Away

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule notification 2-5 minutes in future - Notification scheduled
2 Swipe app away from app switcher - -
3 Wait for trigger time Notification fires (OS handles) Notification displayed
4 Check app state App terminated App not running

Platform Behavior: OS-guaranteed (iOS UNUserNotificationCenter)


Test 3: Device Reboot

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule notification for future time - Notification scheduled
2 Reboot device - -
3 Do NOT open app Notification fires (OS persists) Notification displayed
4 Check notification timing On time (±180s tolerance) On time

Platform Behavior: OS-guaranteed (iOS persists calendar/time triggers)

Note: Only calendar and time-based triggers persist. Location triggers do not.


Test 4: Hard Termination & Relaunch

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule repeating notifications - Notifications scheduled
2 Terminate app via Xcode/switcher - -
3 Allow some triggers to occur Notifications fire Notifications displayed
4 Reopen app - Plugin checks for missed events
5 Check missed event detection ⚠️ May detect Plugin-specific
6 Check state recovery ⚠️ May recover Plugin-specific

Platform Behavior: OS-guaranteed for notifications; Plugin-guaranteed for missed event detection


Test 5: Background Execution Limits

Step Action Expected (OS) Expected (Plugin) Actual Result Notes
1 Schedule BGTaskScheduler task - Task scheduled
2 Wait for system to execute ⚠️ System-controlled ⚠️ May not execute
3 Check execution timing ⚠️ Not guaranteed ⚠️ Not guaranteed
4 Check time budget ⚠️ ~30 seconds ⚠️ Limited time

Code Reference: DailyNotificationPlugin.scheduleBackgroundFetch() line 495

Platform Behavior: System-controlled (not guaranteed)


2.3 Persistence Investigation

Item Expected Actual Code Reference Notes
Notification ID stored Yes (in UNUserNotificationCenter) UNNotificationRequest
Plugin-side storage ⚠️ May not exist DailyNotificationStorage?
Trigger time stored Yes (in trigger) UNCalendarNotificationTrigger
Repeat rule stored Yes (in trigger) repeats: true/false
Payload stored Yes (in userInfo) notificationContent.userInfo

Storage Location:

  • Primary: UNUserNotificationCenter (OS-managed)
  • Secondary: Plugin storage (if implemented)

2.4 Recovery Points Investigation

Recovery Point Expected Behavior Actual Behavior Code Reference Notes
Boot event Notifications fire automatically OS handles
App cold start ⚠️ May detect missed notifications Check load() method
App warm start ⚠️ May verify pending notifications Check plugin initialization
Background fetch ⚠️ May reschedule BGTaskScheduler
User taps notification App launched Notification action

3. Cross-Platform Comparison

3.1 Observed Behavior Summary

Scenario Android (Observed) iOS (Observed) Platform Difference
Swipe/termination Both should work
Reboot iOS auto, Android manual
Force stop N/A Android only
App code on trigger Android yes, iOS no
Background execution Android more flexible

4. Findings & Gaps

4.1 Android Gaps

Gap Severity Description Recommendation
Boot recovery ☐ High/Medium/Low Does plugin reschedule on boot? Implement if missing
Missed alarm detection ☐ High/Medium/Low Does plugin detect missed alarms? Implement if missing
Force stop recovery ☐ High/Medium/Low Does plugin recover after force stop? Implement if missing
Persistence completeness ☐ High/Medium/Low Are all required fields persisted? Verify and add if missing

4.2 iOS Gaps

Gap Severity Description Recommendation
Missed notification detection ☐ High/Medium/Low Does plugin detect missed notifications? Implement if missing
Plugin-side persistence ☐ High/Medium/Low Does plugin persist state separately? Consider if needed
Background task reliability ☐ High/Medium/Low Can plugin rely on BGTaskScheduler? Document limitations

5. Deliverables from This Exploration

After completing this exploration, generate:

  1. ALARMS_BEHAVIOR_MATRIX.md - Completed test results
  2. PLUGIN_ALARM_LIMITATIONS.md - Documented limitations and gaps
  3. Annotated code pointers - Code locations with findings
  4. Open Questions / TODOs - Unresolved issues


Notes for Explorers

  • Fill in checkboxes (☐) as you complete each test
  • Document actual results in "Actual Result" columns
  • Add notes for any unexpected behavior
  • Reference code locations when documenting findings
  • Update "Findings & Gaps" section as you discover issues
  • Use platform capability reference to understand expected OS behavior