Files
daily-notification-plugin/docs/plugin-requirements-implementation.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 Requirements & Implementation Directive

Author: Matthew Raymer
Date: November 2025
Status: Active Requirements - Implementation Guide

Purpose

This document defines the rules the plugin must follow to behave predictably across Android and iOS platforms. It specifies:

  • Persistence requirements
  • Recovery strategies
  • JS/TS API contract and caveats
  • Missed alarm handling
  • Platform-specific requirements
  • Testing requirements

This document should be updated after exploration findings are documented.

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


1. Core Requirements

1.1 Plugin Behavior Guarantees

The plugin must guarantee the following behaviors:

Behavior Android iOS Implementation Required
Notification fires after swipe/termination Yes Yes OS-guaranteed (verify)
Notification fires after reboot ⚠️ Only if rescheduled Yes Android: Boot receiver required
Missed alarm detection Required Required Both: App launch recovery
Force stop recovery Required N/A Android: App restart recovery
Exact timing With permission ⚠️ ±180s tolerance Android: Permission check

1.2 Plugin Behavior Limitations

The plugin cannot guarantee:

Limitation Platform Reason
Notification after Force Stop (Android) Android OS hard kill
App code execution on iOS notification fire iOS OS limitation
Background execution timing (iOS) iOS System-controlled
Exact timing (iOS) iOS ±180s tolerance

2. Persistence Requirements

2.1 Required Persistence Items

The plugin must persist the following for each scheduled alarm/notification:

Field Type Required Purpose
alarm_id String Yes Unique identifier
trigger_time Long/TimeInterval Yes When to fire
repeat_rule String/Enum Yes NONE, DAILY, WEEKLY, CUSTOM
channel_id String Yes Notification channel (Android)
priority String/Int Yes Notification priority
title String Yes Notification title
body String Yes Notification body
sound_enabled Boolean Yes Sound preference
vibration_enabled Boolean Yes Vibration preference
payload String/JSON ⚠️ Optional Additional content
created_at Long/TimeInterval Yes Creation timestamp
updated_at Long/TimeInterval Yes Last update timestamp
enabled Boolean Yes Whether alarm is active

2.2 Storage Implementation

Android:

  • Primary: Room database (DailyNotificationDatabase)
  • Location: android/src/main/java/com/timesafari/dailynotification/
  • Entities: Schedule, NotificationContentEntity, ContentCache

iOS:

  • Primary: UNUserNotificationCenter (OS-managed)
  • Secondary: Plugin storage (UserDefaults, CoreData, or files)
  • Location: ios/Plugin/
  • Component: DailyNotificationStorage?

2.3 Persistence Validation

The plugin must:

  • Validate persistence on every alarm schedule
  • Log persistence failures
  • Handle persistence errors gracefully
  • Provide recovery mechanism if persistence fails

3. Recovery Requirements

3.1 Required Recovery Points

The plugin must implement recovery at the following points:

3.1.1 Boot Event (Android Only)

Trigger: BOOT_COMPLETED broadcast

Required Actions:

  1. Load all enabled alarms from persistent storage
  2. Reschedule each alarm using AlarmManager
  3. Detect missed alarms (trigger_time < now)
  4. Generate missed alarm events/notifications
  5. Log recovery actions

Code Reference: BootReceiver.kt line 24

Implementation Status: ☐ Implemented / ☐ Missing


3.1.2 App Cold Start

Trigger: App launched from terminated state

Required Actions:

  1. Load all enabled alarms from persistent storage
  2. Verify active alarms match stored alarms
  3. Detect missed alarms (trigger_time < now)
  4. Reschedule future alarms
  5. Generate missed alarm events/notifications
  6. Log recovery actions

Implementation Status: ☐ Implemented / ☐ Missing

Code Location: Check plugin initialization (DailyNotificationPlugin.load() or equivalent)


3.1.3 App Warm Start

Trigger: App returning from background

Required Actions:

  1. Verify active alarms are still scheduled
  2. Detect missed alarms (trigger_time < now)
  3. Reschedule if needed
  4. Log recovery actions

Implementation Status: ☐ Implemented / ☐ Missing


3.1.4 User Taps Notification

Trigger: User interaction with notification

Required Actions:

  1. Launch app (OS handles)
  2. Detect if notification was missed
  3. Handle notification action
  4. Update alarm state if needed

Implementation Status: ☐ Implemented / ☐ Missing


3.2 Missed Alarm Handling

The plugin must detect and handle missed alarms:

Definition: An alarm is "missed" if:

  • trigger_time < now
  • Alarm was not fired (or firing status unknown)
  • Alarm is still enabled

Required Actions:

  1. Detect missed alarms during recovery
  2. Generate missed alarm event/notification
  3. Reschedule future occurrences (if repeating)
  4. Log missed alarm for debugging
  5. Update alarm state (mark as missed or reschedule)

Implementation Requirements:

  • Must run on app launch (cold/warm start)
  • Must run on boot (Android)
  • Must not duplicate missed alarm notifications
  • Must handle timezone changes

Code Location: To be implemented in recovery logic


4. JS/TS API Contract

4.1 API Guarantees

The plugin must document and guarantee the following behaviors to JavaScript/TypeScript developers:

4.1.1 scheduleDailyNotification(options)

Guarantees:

  • Notification will fire if app is swiped from recents
  • Notification will fire if app is terminated by OS
  • ⚠️ Notification will fire after reboot only if:
    • Android: Boot receiver is registered and working
    • iOS: Automatic (OS handles)
  • Notification will NOT fire after Android Force Stop until app is opened
  • ⚠️ iOS notifications have ±180s timing tolerance

Caveats:

  • Android requires SCHEDULE_EXACT_ALARM permission on Android 12+
  • Android requires RECEIVE_BOOT_COMPLETED permission for reboot recovery
  • iOS requires notification authorization

Error Codes:

  • EXACT_ALARM_PERMISSION_REQUIRED - Android 12+ exact alarm permission needed
  • NOTIFICATIONS_DENIED - Notification permission denied
  • SCHEDULE_FAILED - Scheduling failed (check logs)

4.1.2 scheduleDailyReminder(options)

Guarantees:

  • Same as scheduleDailyNotification() above
  • Static reminder (no content dependency)
  • Fires even if content fetch fails

4.1.3 getNotificationStatus()

Guarantees:

  • Returns current notification status
  • Includes pending notifications
  • Includes last notification time
  • May include missed alarm information

4.2 API Warnings

The plugin must document the following warnings:

Android:

  • "Notifications will not fire after device reboot unless the app is opened at least once"
  • "Force Stop will prevent all notifications until the app is manually opened"
  • "Exact alarm permission is required on Android 12+ for precise timing"

iOS:

  • "Notifications have ±180 seconds timing tolerance"
  • "App code does not run when notifications fire (unless user interacts)"
  • "Background execution is system-controlled and not guaranteed"

Cross-Platform:

  • "Missed alarms are detected on app launch, not at trigger time"
  • "Repeating alarms must be rescheduled for each occurrence"

4.3 API Error Handling

The plugin must:

  • Return clear error messages
  • Include error codes for programmatic handling
  • Open system settings when permission is needed
  • Provide actionable guidance in error messages

Example Error Response:

{
  code: "EXACT_ALARM_PERMISSION_REQUIRED",
  message: "Exact alarm permission required. Please grant 'Alarms & reminders' permission in Settings, then try again.",
  action: "opened_settings" // or "permission_denied"
}

5. Platform-Specific Requirements

5.1 Android Requirements

5.1.1 Permissions

Required Permissions:

  • RECEIVE_BOOT_COMPLETED - Boot receiver
  • SCHEDULE_EXACT_ALARM - Android 12+ (API 31+) for exact alarms
  • POST_NOTIFICATIONS - Android 13+ (API 33+) for notifications

Permission Handling:

  • Check permission before scheduling
  • Request permission if not granted
  • Open system settings if permission denied
  • Provide clear error messages

Code Reference: DailyNotificationPlugin.kt line 1309


5.1.2 Manifest Entries

Required Manifest Entries:

<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM" />
<uses-permission android:name="android.permission.POST_NOTIFICATIONS" />

<receiver
    android:name="com.timesafari.dailynotification.BootReceiver"
    android:enabled="true"
    android:exported="true">
    <intent-filter>
        <action android:name="android.intent.action.BOOT_COMPLETED" />
        <action android:name="android.intent.action.LOCKED_BOOT_COMPLETED" />
    </intent-filter>
</receiver>

<receiver
    android:name="com.timesafari.dailynotification.DailyNotificationReceiver"
    android:enabled="true"
    android:exported="false">
    <intent-filter>
        <action android:name="com.timesafari.daily.NOTIFICATION" />
    </intent-filter>
</receiver>

Location: Test app manifest: test-apps/android-test-app/app/src/main/AndroidManifest.xml


5.1.3 Notification Channels

Required Channels:

  • timesafari.daily - Primary notification channel
  • daily_reminders - Reminder notifications (if used)

Channel Configuration:

  • Importance: HIGH (for alarms), DEFAULT (for reminders)
  • Sound: Enabled by default
  • Vibration: Enabled by default
  • Show badge: Enabled

Code Reference: ChannelManager.java or NotifyReceiver.kt line 454


5.1.4 Alarm Scheduling

Required API Usage:

  • setAlarmClock() for Android 5.0+ (preferred)
  • setExactAndAllowWhileIdle() for Android 6.0+ (fallback)
  • setExact() for older versions (fallback)

Code Reference: NotifyReceiver.kt line 219, 223, 231


5.2 iOS Requirements

5.2.1 Permissions

Required Permissions:

  • Notification authorization (requested at runtime)

Permission Handling:

  • Request permission before scheduling
  • Handle authorization status
  • Provide clear error messages

5.2.2 Background Tasks

Required Background Task Identifiers:

  • com.timesafari.dailynotification.fetch - Background fetch
  • com.timesafari.dailynotification.notify - Notification task (if used)

Background Task Registration:

  • Register in Info.plist:
    <key>BGTaskSchedulerPermittedIdentifiers</key>
    <array>
        <string>com.timesafari.dailynotification.fetch</string>
    </array>
    

Code Reference: DailyNotificationPlugin.swift line 31-32


5.2.3 Notification Scheduling

Required API Usage:

  • UNUserNotificationCenter.add() - Schedule notifications
  • UNCalendarNotificationTrigger - Calendar-based triggers (preferred)
  • UNTimeIntervalNotificationTrigger - Time interval triggers

Code Reference: DailyNotificationScheduler.swift line 185


5.2.4 Notification Categories

Required Categories:

  • DAILY_NOTIFICATION - Primary notification category

Category Configuration:

  • Actions: Configure as needed
  • Options: Custom sound, custom actions

Code Reference: DailyNotificationScheduler.swift line 62+


6. Testing Requirements

6.1 Required Test Scenarios

The plugin must be tested for:

Android:

  • Base case (alarm fires on time)
  • Swipe from recents
  • OS kill (memory pressure)
  • Device reboot (with and without app launch)
  • Force stop (with app restart)
  • Exact alarm permission (Android 12+)
  • Boot receiver functionality
  • Missed alarm detection

iOS:

  • Base case (notification fires on time)
  • Swipe app away
  • Device reboot (without app launch)
  • Hard termination and relaunch
  • Background execution limits
  • Missed notification detection

Cross-Platform:

  • Timezone changes
  • Clock adjustments
  • Multiple simultaneous alarms
  • Repeating alarms
  • Alarm cancellation

6.2 Test Harness Requirements

Required Test Tools:

  • Real devices (not just emulators)
  • ADB commands for Android testing
  • Xcode for iOS testing
  • Log monitoring tools

Required Test Documentation:

  • Test results matrix
  • Log snippets for failures
  • Screenshots/videos for UI issues
  • Performance metrics

7. Versioning Requirements

7.1 Breaking Changes

Any change to alarm behavior is breaking and requires:

  • MAJOR version bump (semantic versioning)
  • Migration guide for existing users
  • Deprecation warnings (if applicable)
  • Clear changelog entry

7.2 Non-Breaking Changes

Non-breaking changes include:

  • Bug fixes
  • Performance improvements
  • Additional features (backward compatible)
  • Documentation updates

8. Implementation Checklist

8.1 Android Implementation

  • Boot receiver registered in manifest
  • Boot receiver reschedules alarms from database
  • Exact alarm permission checked and requested
  • Notification channels created
  • Alarm scheduling uses correct API (setAlarmClock preferred)
  • Persistence implemented (Room database)
  • Missed alarm detection on app launch
  • Force stop recovery on app restart
  • Error handling and user guidance

8.2 iOS Implementation

  • Notification authorization requested
  • Background tasks registered in Info.plist
  • Notification scheduling uses UNUserNotificationCenter
  • Calendar triggers used (not just time interval)
  • Plugin-side persistence (if needed for missed detection)
  • Missed notification detection on app launch
  • Background task limitations documented
  • Error handling and user guidance

8.3 Cross-Platform Implementation

  • JS/TS API contract documented
  • Platform-specific caveats documented
  • Error codes standardized
  • Test scenarios covered
  • Migration guide (if breaking changes)

9. Open Questions / TODOs

To be filled after exploration:

Question Platform Priority Status
Does boot receiver work correctly? Android High
Is missed alarm detection implemented? Both High
Are all required fields persisted? Both Medium
Is force stop recovery implemented? Android High
Does iOS plugin persist state separately? iOS Medium


Version History

  • v1.0 (November 2025): Initial requirements document
    • Persistence requirements
    • Recovery requirements
    • JS/TS API contract
    • Platform-specific requirements
    • Testing requirements