Files
daily-notification-plugin/API.md
Matthew Raymer 37753bb051 docs: add comprehensive integration guides and diagnostic method documentation
Add integration guides and update API documentation with new Android
diagnostic methods. Emphasize critical NotifyReceiver registration
requirement that was causing notification delivery failures.

Documentation Updates:
- API.md: Document isAlarmScheduled(), getNextAlarmTime(), testAlarm()
- README.md: Add Quick Integration section and Android diagnostic methods
- notification-testing-procedures.md: Add BroadcastReceiver troubleshooting

New Integration Guides:
- QUICK_INTEGRATION.md: Step-by-step guide for human developers
- AI_INTEGRATION_GUIDE.md: Machine-readable guide with verification steps
- TODO.md: Task tracking for pending improvements

Key Improvements:
- Explicit NotifyReceiver registration requirement highlighted
- Complete troubleshooting flow for BroadcastReceiver issues
- Diagnostic method examples for debugging alarm scheduling
- AI-friendly integration instructions with verification commands

Fixes notification delivery issues caused by missing NotifyReceiver
registration in host app AndroidManifest.xml files.
2025-11-06 10:08:18 +00:00

10 KiB

TimeSafari Daily Notification Plugin API Reference

Author: Matthew Raymer
Version: 2.2.0
Last Updated: 2025-11-06 09:51:00 UTC

Overview

This API reference provides comprehensive documentation for the TimeSafari Daily Notification Plugin, optimized for native-first architecture supporting Android, iOS, and Electron platforms.

Platform Support

  • Android: WorkManager + AlarmManager + SQLite
  • iOS: BGTaskScheduler + UNUserNotificationCenter + Core Data
  • Electron: Desktop notifications + SQLite/LocalStorage
  • Web (PWA): Removed for native-first focus

DailyNotificationPlugin Interface

Configuration

configure(options: ConfigureOptions): Promise<void>

Configure the plugin with storage, TTL, and optimization settings.

Parameters:

  • options.storage: 'shared' | 'tiered' - Storage mode
  • options.ttlSeconds: number - TTL in seconds (default: 1800)
  • options.prefetchLeadMinutes: number - Prefetch lead time (default: 15)
  • options.enableETagSupport: boolean - Enable ETag conditional requests
  • options.enableErrorHandling: boolean - Enable advanced error handling
  • options.enablePerformanceOptimization: boolean - Enable performance optimization

Core Methods

scheduleDailyNotification(options: NotificationOptions): Promise<void>

Schedule a daily notification with content fetching.

Parameters:

  • options.url: string - Content endpoint URL
  • options.time: string - Time in HH:MM format
  • options.title: string - Notification title
  • options.body: string - Notification body
  • options.sound: boolean - Enable sound (optional)
  • options.retryConfig: RetryConfiguration - Custom retry settings (optional)

getLastNotification(): Promise<NotificationResponse | null>

Get the last scheduled notification.

cancelAllNotifications(): Promise<void>

Cancel all scheduled notifications.

Platform-Specific Methods

Android Only

getExactAlarmStatus(): Promise<ExactAlarmStatus>

Get exact alarm permission and capability status.

requestExactAlarmPermission(): Promise<void>

Request exact alarm permission from user.

openExactAlarmSettings(): Promise<void>

Open exact alarm settings in system preferences.

getRebootRecoveryStatus(): Promise<RecoveryStatus>

Get reboot recovery status and statistics.

isAlarmScheduled(options: { triggerAtMillis: number }): Promise<{ scheduled: boolean; triggerAtMillis: number }>

Check if an alarm is scheduled for a specific trigger time. Useful for debugging and verification.

Parameters:

  • options.triggerAtMillis: number - The trigger time in milliseconds (Unix timestamp)

Returns:

  • scheduled: boolean - Whether the alarm is currently scheduled
  • triggerAtMillis: number - The trigger time that was checked

Example:

const result = await DailyNotification.isAlarmScheduled({
  triggerAtMillis: 1762421400000
});
console.log(`Alarm scheduled: ${result.scheduled}`);
getNextAlarmTime(): Promise<{ scheduled: boolean; triggerAtMillis?: number }>

Get the next scheduled alarm time from AlarmManager. Requires Android 5.0+ (API 21+).

Returns:

  • scheduled: boolean - Whether any alarm is scheduled
  • triggerAtMillis: number | undefined - The next alarm trigger time (if scheduled)

Example:

const result = await DailyNotification.getNextAlarmTime();
if (result.scheduled) {
  const nextAlarm = new Date(result.triggerAtMillis);
  console.log(`Next alarm: ${nextAlarm.toLocaleString()}`);
}
testAlarm(options?: { secondsFromNow?: number }): Promise<{ scheduled: boolean; secondsFromNow: number; triggerAtMillis: number }>

Schedule a test alarm that fires in a few seconds. Useful for verifying alarm delivery works correctly.

Parameters:

  • options.secondsFromNow: number (optional) - Seconds from now to fire the alarm (default: 5)

Returns:

  • scheduled: boolean - Whether the alarm was scheduled successfully
  • secondsFromNow: number - The delay used
  • triggerAtMillis: number - The trigger time in milliseconds

Example:

const result = await DailyNotification.testAlarm({ secondsFromNow: 10 });
console.log(`Test alarm scheduled for ${result.secondsFromNow} seconds`);

Management Methods

maintainRollingWindow(): Promise<void>

Manually trigger rolling window maintenance.

getRollingWindowStats(): Promise<RollingWindowStats>

Get rolling window statistics and status.

Optimization Methods

optimizeDatabase(): Promise<void>

Optimize database performance with indexes and settings.

optimizeMemory(): Promise<void>

Optimize memory usage and perform cleanup.

optimizeBattery(): Promise<void>

Optimize battery usage and background CPU.

Metrics and Monitoring

getPerformanceMetrics(): Promise<PerformanceMetrics>

Get comprehensive performance metrics.

getErrorMetrics(): Promise<ErrorMetrics>

Get error handling metrics and statistics.

getNetworkMetrics(): Promise<NetworkMetrics>

Get network efficiency metrics (ETag support).

getMemoryMetrics(): Promise<MemoryMetrics>

Get memory usage metrics and statistics.

getObjectPoolMetrics(): Promise<ObjectPoolMetrics>

Get object pooling efficiency metrics.

Utility Methods

resetPerformanceMetrics(): Promise<void>

Reset all performance metrics to zero.

resetErrorMetrics(): Promise<void>

Reset error handling metrics.

clearRetryStates(): Promise<void>

Clear all retry states and operations.

cleanExpiredETags(): Promise<void>

Clean expired ETag cache entries.

Data Types

ConfigureOptions

interface ConfigureOptions {
  storage?: 'shared' | 'tiered';
  ttlSeconds?: number;
  prefetchLeadMinutes?: number;
  enableETagSupport?: boolean;
  enableErrorHandling?: boolean;
  enablePerformanceOptimization?: boolean;
  maxRetries?: number;
  baseRetryDelay?: number;
  maxRetryDelay?: number;
  backoffMultiplier?: number;
  memoryWarningThreshold?: number;
  memoryCriticalThreshold?: number;
  objectPoolSize?: number;
  maxObjectPoolSize?: number;
}

NotificationOptions

interface NotificationOptions {
  url: string;
  time: string;
  title: string;
  body: string;
  sound?: boolean;
  retryConfig?: RetryConfiguration;
}

ExactAlarmStatus (Android)

interface ExactAlarmStatus {
  supported: boolean;
  enabled: boolean;
  canSchedule: boolean;
  fallbackWindow: string;
}

PerformanceMetrics

interface PerformanceMetrics {
  overallScore: number;
  databasePerformance: number;
  memoryEfficiency: number;
  batteryEfficiency: number;
  objectPoolEfficiency: number;
  totalDatabaseQueries: number;
  averageMemoryUsage: number;
  objectPoolHits: number;
  backgroundCpuUsage: number;
  totalNetworkRequests: number;
  recommendations: string[];
}

ErrorMetrics

interface ErrorMetrics {
  totalErrors: number;
  networkErrors: number;
  storageErrors: number;
  schedulingErrors: number;
  permissionErrors: number;
  configurationErrors: number;
  systemErrors: number;
  unknownErrors: number;
  cacheHitRatio: number;
}

Error Handling

All methods return promises that reject with descriptive error messages. The plugin includes comprehensive error categorization and retry logic.

Common Error Types

  • Network Errors: Connection timeouts, DNS failures
  • Storage Errors: Database corruption, disk full
  • Permission Errors: Missing exact alarm permission
  • Configuration Errors: Invalid parameters, unsupported settings
  • System Errors: Out of memory, platform limitations

Platform Differences

Android

  • Requires SCHEDULE_EXACT_ALARM permission for precise timing
  • Falls back to windowed alarms (±10m) if exact permission denied
  • Supports reboot recovery with broadcast receivers
  • Full performance optimization features

iOS

  • Uses BGTaskScheduler for background prefetch
  • Limited to 64 pending notifications
  • Automatic background task management
  • Battery optimization built-in

Electron

  • Desktop notification support
  • SQLite or LocalStorage fallback
  • Native desktop notification APIs
  • Cross-platform desktop compatibility

TimeSafari-Specific Integration Examples

Basic TimeSafari Integration

import { DailyNotification } from '@timesafari/daily-notification-plugin';
import { TimeSafariIntegrationService } from '@timesafari/daily-notification-plugin';

// Initialize TimeSafari integration
const integrationService = TimeSafariIntegrationService.getInstance();

// Configure with TimeSafari-specific settings
await integrationService.initialize({
  activeDid: 'did:example:timesafari-user-123',
  storageAdapter: timeSafariStorageAdapter,
  endorserApiBaseUrl: 'https://endorser.ch/api/v1'
});

// Schedule TimeSafari community notifications
await DailyNotification.scheduleDailyNotification({
  title: 'New Community Update',
  body: 'You have new offers and project updates',
  time: '09:00',
  channel: 'timesafari_community_updates'
});

TimeSafari Community Features

// Fetch community data with rate limiting
const communityService = new TimeSafariCommunityIntegrationService();

await communityService.initialize({
  maxRequestsPerMinute: 30,
  maxRequestsPerHour: 1000,
  basePollingIntervalMs: 300000, // 5 minutes
  adaptivePolling: true
});

// Fetch community data
const bundle = await communityService.fetchCommunityDataWithRateLimit({
  activeDid: 'did:example:timesafari-user-123',
  fetchOffersToPerson: true,
  fetchOffersToProjects: true,
  fetchProjectUpdates: true,
  starredPlanIds: ['plan-1', 'plan-2', 'plan-3']
});

DID-Signed Payloads

// Generate DID-signed notification payloads
const samplePayloads = integrationService.generateSampleDidPayloads();

for (const payload of samplePayloads) {
  // Verify signature
  const isValid = await integrationService.verifyDidSignature(
    JSON.stringify(payload.payload),
    payload.signature
  );
  
  console.log(`Payload ${payload.type} signature valid: ${isValid}`);
}

Privacy-Preserving Storage

// Configure privacy-preserving storage
const storageAdapter = new TimeSafariStorageAdapterImpl(
  nativeStorage, 
  'timesafari_notifications'
);

// Store with TTL and redaction
await storageAdapter.store('community_data', bundle, 3600); // 1 hour TTL

// Get data retention policy
const policy = integrationService.getDataRetentionPolicy();
console.log('Data retention policy:', policy);