# Building the DailyNotification Plugin **Author**: Matthew Raymer **Last Updated**: 2025-10-21 09:03:53 UTC **Version**: 1.0.0 ## Overview This document provides comprehensive instructions for building the DailyNotification Capacitor plugin using various methods, including Android Studio, command line, and integration testing. ## Table of Contents - [Quick Start](#quick-start) - [Prerequisites](#prerequisites) - [Build Methods](#build-methods) - [Android Studio Setup](#android-studio-setup) - [Command Line Building](#command-line-building) - [Testing Strategies](#testing-strategies) - [Development Workflow](#development-workflow) - [Troubleshooting](#troubleshooting) - [Project Structure](#project-structure) ## Quick Start ### For Plugin Development ```bash # Build plugin source code ./scripts/build-native.sh --platform android # Test in Capacitor app cd /path/to/test-capacitor-app npx cap sync android npx cap run android ``` ### For Android Studio ```bash # 1. Open Android Studio # 2. File → Open → /path/to/daily-notification-plugin/android # 3. Wait for Gradle sync # 4. Build → Make Project (Ctrl+F9) ``` ## Prerequisites ### Required Software - **Android Studio** (latest stable version) - for Android development - **Java 11+** (for Kotlin compilation) - **Android SDK** with API level 21+ - **Xcode** (latest stable version) - for iOS development (macOS only) - **Xcode Command Line Tools** - required for iOS builds (includes `xcodebuild`, `sqlite3`, etc.) - **Node.js** 16+ (for TypeScript compilation) - **npm** or **yarn** (for dependency management) ### Required Tools - **Gradle Wrapper** (included in project) - **Kotlin** (configured in build.gradle) - **TypeScript** (for plugin interface) - **CocoaPods** - for iOS dependency management ### iOS-Specific Prerequisites **Xcode Command Line Tools** are required for iOS builds. The build script will verify these are installed: ```bash # Install Xcode Command Line Tools (if not already installed) xcode-select --install ``` **Verification:** ```bash # Check if Command Line Tools are configured xcode-select -p # Verify xcodebuild is available xcodebuild -version # Verify sqlite3 is available (part of Command Line Tools) sqlite3 --version ``` **Note:** The build script automatically checks for Command Line Tools and will fail with clear error messages if they're missing. ### System Requirements - **RAM**: 4GB minimum, 8GB recommended - **Storage**: 2GB free space - **OS**: Windows 10+, macOS 10.14+, or Linux (iOS development requires macOS) ## Build Methods ### Method 1: Automated Build Script (Recommended) The project includes an automated build script that handles both TypeScript and native compilation: ```bash # Build all platforms ./scripts/build-native.sh # Build specific platform ./scripts/build-native.sh --platform android ./scripts/build-native.sh --platform ios # Build with verbose output ./scripts/build-native.sh --verbose ``` **What it does:** 1. Compiles TypeScript to JavaScript 2. Bundles plugin code with Rollup 3. Builds native Android/iOS code 4. Handles plugin development project detection 5. Provides helpful warnings and guidance ### Method 2: Manual Command Line #### TypeScript Compilation ```bash # Clean previous builds npm run clean # Build TypeScript and bundle npm run build # Watch mode for development npm run build:watch ``` #### Android Native Build ```bash # Navigate to Android directory cd android # Build plugin library (recommended for plugin development) ./gradlew :plugin:assembleRelease # Build test app (requires proper Capacitor integration) ./gradlew :app:assembleRelease # Build all modules ./gradlew build # Run tests ./gradlew test ``` #### iOS Native Build ```bash # Navigate to iOS directory cd ios # Install CocoaPods dependencies pod install # Build using Xcode (command line) xcodebuild -workspace DailyNotificationPlugin.xcworkspace -scheme DailyNotificationPlugin -configuration Release ``` ### Method 3: Android Studio See [Android Studio Setup](#android-studio-setup) for detailed instructions. ## Android Studio Setup ### Opening the Project #### Important: Open the Correct Directory ```bash # ✅ CORRECT: Open the android/ folder File → Open → /path/to/daily-notification-plugin/android # ❌ WRONG: Don't open the root project folder # This will cause Gradle sync issues ``` ### Initial Configuration #### 1. Gradle Sync - Android Studio will prompt to sync Gradle - Click **"Sync Now"** or use the sync button in the toolbar - Wait for sync to complete (may take a few minutes) #### 2. SDK Configuration ``` File → Project Structure → SDK Location - Android SDK: /path/to/Android/Sdk - JDK Location: /path/to/jdk-11 ``` #### 3. Gradle Settings ``` File → Settings → Build → Gradle - Use Gradle from: 'gradle-wrapper.properties' file - Gradle JVM: Project SDK (Java 11) ``` #### 4. Kotlin Configuration ``` File → Settings → Languages & Frameworks → Kotlin - Target JVM version: 1.8 - Language version: 1.5 ``` ### Building in Android Studio #### Build Commands ```bash # Build the project Build → Make Project (Ctrl+F9) # Clean and rebuild Build → Clean Project Build → Rebuild Project # Generate signed APK/AAR Build → Generate Signed Bundle / APK ``` #### Build Output The built plugin AAR will be located at: ``` android/build/outputs/aar/android-release.aar ``` ### Project Structure in Android Studio When opened correctly, you'll see: ``` android/ ├── app/ # Main Android test app │ ├── build.gradle # App build configuration │ ├── src/main/java/ # MainActivity.java │ ├── src/main/assets/ # Capacitor assets (HTML/JS) │ └── build/outputs/apk/ # Built APK files ├── plugin/ # Plugin library module │ ├── build.gradle # Plugin build configuration │ ├── src/main/java/ │ │ └── com/timesafari/dailynotification/ │ │ ├── DailyNotificationPlugin.java │ │ ├── DailyNotificationWorker.java │ │ ├── DailyNotificationScheduler.java │ │ └── ... │ └── build/outputs/aar/ │ └── plugin-release.aar # Built plugin AAR ├── build.gradle # Root build file ├── settings.gradle # Project settings ├── gradle.properties # Gradle properties └── gradle/wrapper/ # Gradle wrapper files ``` **Note**: There's also a separate Vue 3 test app at `test-apps/daily-notification-test/android/` with its own Android module. ### Important Distinctions #### Standard Capacitor Plugin Structure The plugin now follows the standard Capacitor Android structure: - **Plugin Code**: `android/src/main/java/...` - **Plugin Build**: `android/build.gradle` - **Test App**: `test-apps/android-test-app/app/` (separate from plugin) This structure is compatible with Capacitor's auto-generated files and requires no path fixes. ❌ **Test plugin without host app** (needs Capacitor runtime) ## Command Line Building ### TypeScript Build Process #### 1. Clean Previous Builds ```bash npm run clean # Removes: dist/, build/, out/ ``` #### 2. Compile TypeScript ```bash npm run build # Compiles: src/ → dist/ # Bundles: dist/plugin.js, dist/esm/index.js ``` #### 3. Watch Mode (Development) ```bash npm run build:watch # Automatically rebuilds on file changes ``` ### Android Native Build Process #### 1. Navigate to Android Directory ```bash cd android ``` #### 2. Build Commands ```bash # Build all variants ./gradlew build # Build debug variant ./gradlew assembleDebug # Build release variant ./gradlew assembleRelease # Clean build ./gradlew clean build # Run tests ./gradlew test ``` #### 3. Build Outputs ```bash # Plugin AAR files android/build/outputs/aar/ ├── android-debug.aar └── android-release.aar # Test results android/build/reports/tests/test/index.html ``` ### iOS Native Build Process **Prerequisites:** Ensure Xcode Command Line Tools are installed (see [Prerequisites](#prerequisites) section). The build script will verify this automatically. #### 1. Navigate to iOS Directory ```bash cd ios ``` #### 2. Install Dependencies ```bash pod install ``` **Note:** If you encounter issues with `pod install`, ensure Xcode Command Line Tools are properly configured: ```bash xcode-select --install # Install if missing xcode-select -p # Verify installation path ``` #### 3. Build Commands ```bash # Build using Xcode command line xcodebuild -workspace DailyNotificationPlugin.xcworkspace \ -scheme DailyNotificationPlugin \ -configuration Release \ -destination generic/platform=iOS # Build for simulator xcodebuild -workspace DailyNotificationPlugin.xcworkspace \ -scheme DailyNotificationPlugin \ -configuration Debug \ -destination 'platform=iOS Simulator,name=iPhone 14' ``` ## Testing Strategies ### Unit Testing #### Android Unit Tests ```bash # Run all tests ./gradlew test # Run specific test class ./gradlew test --tests "DailyNotificationPluginTest" # Run tests with coverage ./gradlew test jacocoTestReport ``` #### iOS Unit Tests ```bash # Run tests using Xcode xcodebuild test -workspace DailyNotificationPlugin.xcworkspace \ -scheme DailyNotificationPlugin \ -destination 'platform=iOS Simulator,name=iPhone 14' ``` ### Test Apps Within Project #### Vue 3 Test Application The project includes a comprehensive Vue 3 test app for interactive plugin testing: ```bash # Navigate to Vue 3 test app cd test-apps/daily-notification-test # Install dependencies npm install # Build Vue 3 app npm run build # Add Capacitor platforms npm install @capacitor/android @capacitor/ios # Sync with Capacitor npx cap sync android # For iOS: Use the npm script (handles Podfile fixes automatically) npm run cap:sync:ios # This runs: cap copy ios + fix Podfile + pod install # Run on Android device/emulator npx cap run android # Run on iOS device/simulator npx cap run ios ``` **iOS Setup (Vue 3 Test App)** The iOS setup requires additional steps to configure the plugin correctly: **1. Install Dependencies** ```bash cd test-apps/daily-notification-test npm install ``` **2. Build Vue App** ```bash npm run build ``` **3. Add iOS Platform (if not already added)** ```bash npx cap add ios ``` **4. Fix Podfile Configuration** **Critical**: Capacitor's `npx cap sync ios` regenerates the Podfile with incorrect plugin references (`TimesafariDailyNotificationPlugin` instead of `DailyNotificationPlugin`). **Solution**: Use the npm script `npm run cap:sync:ios` which: 1. Copies assets without running pod install (`npx cap copy ios`) 2. Automatically fixes the Podfile 3. Then runs `pod install` with the corrected Podfile ```bash # Use the npm script (recommended) npm run cap:sync:ios # Or manually fix after copy npx cap copy ios node scripts/fix-capacitor-plugins.js cd ios/App && pod install && cd ../.. ``` The fix script will: - Change `TimesafariDailyNotificationPlugin` → `DailyNotificationPlugin` - Fix the path from `'../../../..'` → `'../../node_modules/@timesafari/daily-notification-plugin/ios'` **5. Install CocoaPods Dependencies** After the Podfile is fixed, install the iOS dependencies: ```bash cd ios/App pod install cd ../.. ``` **Expected Podfile Configuration:** The Podfile should reference the plugin like this: ```ruby def capacitor_pods pod 'Capacitor', :path => '../../node_modules/@capacitor/ios' pod 'CapacitorCordova', :path => '../../node_modules/@capacitor/ios' pod 'DailyNotificationPlugin', :path => '../../node_modules/@timesafari/daily-notification-plugin/ios' end ``` **Important Notes:** - The pod name must be `DailyNotificationPlugin` (not `TimesafariDailyNotificationPlugin`) - The path must point to `../../node_modules/@timesafari/daily-notification-plugin/ios` - The plugin must be installed in `node_modules` via `npm install` (it's installed as a local file dependency) **6. Sync and Build** **Important**: `npx cap sync ios` tries to run `pod install` automatically, but it will fail because the Podfile has incorrect plugin references. Use the npm script instead: ```bash # Option 1: Use the npm script (recommended - handles everything) npm run cap:sync:ios # This script: # 1. Copies web assets (npx cap copy ios) # 2. Fixes the Podfile (node scripts/fix-capacitor-plugins.js) # 3. Installs pods (cd ios/App && pod install) # Option 2: Manual steps (if you need more control) npx cap copy ios # Copy assets without pod install node scripts/fix-capacitor-plugins.js # Fix Podfile cd ios/App && pod install && cd ../.. # Install pods # Open in Xcode npx cap open ios ``` **Why this approach?** - `npx cap sync ios` regenerates the Podfile with wrong references, then tries to run `pod install` which fails - `npx cap copy ios` only copies files, allowing us to fix the Podfile before `pod install` - The npm script automates the entire workflow correctly **Troubleshooting iOS Setup:** **Error: `[!] No podspec found for 'TimesafariDailyNotificationPlugin'`** This means the Podfile has the wrong pod name or path. Solutions: 1. **Run the fix script:** ```bash node scripts/fix-capacitor-plugins.js ``` 2. **Manually fix the Podfile:** - Open `ios/App/Podfile` - Change `TimesafariDailyNotificationPlugin` to `DailyNotificationPlugin` - Change path from `'../../../..'` to `'../../node_modules/@timesafari/daily-notification-plugin/ios'` 3. **Verify plugin is installed:** ```bash ls -la node_modules/@timesafari/daily-notification-plugin/ios/DailyNotificationPlugin.podspec ``` 4. **Reinstall dependencies if needed:** ```bash rm -rf node_modules package-lock.json npm install ``` **Error: `pod install` fails** 1. **Update CocoaPods:** ```bash sudo gem install cocoapods ``` 2. **Clean CocoaPods cache:** ```bash cd ios/App rm -rf Pods Podfile.lock pod install --repo-update ``` 3. **Verify Xcode Command Line Tools:** ```bash xcode-select --install ``` **Test App Features:** - Interactive plugin testing interface - Plugin diagnostics and status checking - Notification scheduling and management - Permission testing and management - Comprehensive logging and debugging **Test App Structure:** ``` test-apps/daily-notification-test/ ├── src/ # Vue 3 source code │ ├── views/ # Test interface views │ ├── components/ # Reusable UI components │ └── stores/ # Pinia state management ├── android/ # Android Capacitor app ├── ios/ # iOS Capacitor app │ └── App/ │ ├── Podfile # CocoaPods dependencies │ └── App.xcworkspace # Xcode workspace ├── docs/ # Test app documentation └── scripts/ # Test app build scripts │ └── fix-capacitor-plugins.js # Auto-fixes Podfile ``` #### Android Test Apps The project includes **two separate Android test applications**: ##### 1. Main Android Test App (`test-apps/android-test-app/app`) A Capacitor-based Android test app with full plugin integration: ```bash # Build main Android test app cd test-apps/android-test-app ./gradlew :app:assembleDebug # Install on device adb install app/build/outputs/apk/debug/app-debug.apk # Run tests ./gradlew :app:test # Run in Android Studio # File → Open → /path/to/daily-notification-plugin/test-apps/android-test-app # Select 'app' module and run ``` **Test App Structure:** ``` test-apps/android-test-app/ ├── app/ │ ├── src/ │ │ ├── main/ │ │ │ ├── AndroidManifest.xml # App manifest with permissions │ │ │ ├── assets/ # Capacitor web assets │ │ │ │ ├── capacitor.config.json # Capacitor configuration │ │ │ │ ├── capacitor.plugins.json # Plugin registry │ │ │ │ └── public/ # Web app files │ │ │ ├── java/ │ │ │ │ └── com/timesafari/dailynotification/ │ │ │ │ └── MainActivity.java # Capacitor BridgeActivity │ │ │ └── res/ # Android resources │ │ ├── androidTest/ # Instrumented tests │ │ └── test/ # Unit tests │ ├── build.gradle # App build configuration │ ├── capacitor.build.gradle # Auto-generated Capacitor config │ └── proguard-rules.pro # Code obfuscation rules ``` **Key Files Explained:** **`MainActivity.java`** - Entry point extending Capacitor's BridgeActivity: ```java public class MainActivity extends BridgeActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); } } ``` **`AndroidManifest.xml`** - App permissions and configuration: - Notification permissions - Background execution permissions - Exact alarm permissions - Capacitor plugin declarations **`assets/public/index.html`** - Main test interface: - Interactive plugin testing buttons - Plugin diagnostics and status checking - Notification scheduling interface - Permission management UI **`capacitor.plugins.json`** - Plugin registry: ```json { "plugins": { "DailyNotification": { "class": "org.timesafari.dailynotification.DailyNotificationPlugin" } } } ``` **Build Process:** 1. **Web Assets**: Capacitor copies `assets/public/` to APK 2. **Java Compilation**: Compiles `MainActivity.java` and dependencies 3. **Resource Processing**: Processes Android resources and assets 4. **APK Generation**: Packages everything into installable APK 5. **Plugin Integration**: Links with plugin from `node_modules/@timesafari/daily-notification-plugin/android` **Editing Guidelines:** - **HTML/JS**: Edit `assets/public/index.html` for UI changes - **Java**: Edit `src/main/java/` for native Android code - **Resources**: Edit `src/main/res/` for icons, strings, layouts - **Configuration**: Edit `AndroidManifest.xml` for permissions - **Build**: Modify `build.gradle` for dependencies and build settings **Features:** - Full Capacitor integration - Plugin testing interface (HTML/JS) - Native Android testing capabilities - Complete app lifecycle testing ##### 2. Vue 3 Test App Android Module (`/test-apps/daily-notification-test/android`) Android module within the Vue 3 test application: ```bash # Build Vue 3 test app Android module cd test-apps/daily-notification-test/android ./gradlew assembleDebug # Install on device adb install app/build/outputs/apk/debug/app-debug.apk # Run tests ./gradlew test ``` **Features:** - Integrated with Vue 3 frontend - Plugin diagnostics and management - Interactive testing interface - Comprehensive logging and debugging **Plugin Integration Approach:** The Vue 3 test app uses a **project reference approach** for plugin integration: 1. **Project Reference Configuration**: ```gradle // capacitor.settings.gradle include ':timesafari-daily-notification-plugin' project(':timesafari-daily-notification-plugin').projectDir = new File('../../../android') // capacitor.build.gradle implementation project(':timesafari-daily-notification-plugin') ``` 2. **Required Dependencies**: ```gradle // app/build.gradle implementation 'androidx.work:work-runtime:2.9.0' implementation 'androidx.lifecycle:lifecycle-service:2.7.0' implementation 'com.google.code.gson:gson:2.10.1' ``` 3. **Plugin Discovery**: ```json // assets/capacitor.plugins.json [ { "id": "DailyNotification", "name": "DailyNotification", "class": "org.timesafari.dailynotification.DailyNotificationPlugin" } ] ``` **Troubleshooting Integration Issues:** - **Duplicate Classes**: Use project reference instead of AAR to avoid conflicts - **Gradle Cache**: Clear completely (`rm -rf ~/.gradle`) when switching approaches - **Path Issues**: Ensure correct project path (`../../../android`) - **Dependencies**: Include required WorkManager and Gson dependencies ### Integration Testing #### 1. Create External Test Capacitor App ```bash # Create new Capacitor app npx @capacitor/create-app@latest TestApp cd TestApp # Install your plugin npm install /path/to/daily-notification-plugin # Add platforms npx cap add android npx cap add ios # Sync with Capacitor npx cap sync android npx cap sync ios ``` #### 2. Test in Android Studio ```bash # Open test app in Android Studio File → Open → TestApp/android # Now you can: # - Run the app # - Test notifications # - Debug full integration # - Test background tasks ``` #### 3. Test on Device ```bash # Run on Android device npx cap run android # Run on iOS device npx cap run ios ``` ### Manual Testing Checklist #### Basic Functionality - [ ] Plugin loads without errors - [ ] DailyNotification.configure() works - [ ] Background fetching works - [ ] Notifications appear - [ ] Settings are persisted #### Integration Testing - [ ] ActiveDid change handling - [ ] Settings synchronization - [ ] Request pattern matching - [ ] Error handling - [ ] Network failure recovery #### Edge Cases - [ ] Network failures - [ ] ActiveDid changes during fetch - [ ] App backgrounding/foregrounding - [ ] Battery optimization settings - [ ] Low storage conditions ## Build Scripts and Automation ### Available Build Scripts The project includes several automated build scripts in the `scripts/` directory: #### Core Build Scripts ```bash # Main build script (handles TypeScript + native) ./scripts/build-native.sh --platform android ./scripts/build-native.sh --platform ios ./scripts/build-native.sh --verbose # Clean build (removes all build artifacts and caches) ./scripts/clean-build.sh ./scripts/clean-build.sh --all # Also cleans caches and reinstalls dependencies ./scripts/clean-build.sh --clean-gradle-cache # Clean Gradle cache ./scripts/clean-build.sh --clean-derived-data # Clean Xcode DerivedData ./scripts/clean-build.sh --reinstall-node # Reinstall node_modules # TimeSafari-specific builds node scripts/build-timesafari.js # Comprehensive testing ./scripts/comprehensive-test-v2.sh # Capacitor build fixes ./scripts/fix-capacitor-build.sh ``` #### Setup and Configuration Scripts ```bash # Gradle setup automation ./scripts/setup-gradle.sh # Native environment setup node scripts/setup-native.js # Environment checking node scripts/check-environment.js ``` #### Testing and Validation Scripts ```bash # Chaos testing for reliability node scripts/chaos-test.js # API changes detection node scripts/check-api-changes.js # Bundle size monitoring node scripts/check-bundle-size.js # Daily notification testing ./scripts/daily-notification-test.sh node scripts/daily-notification-test.py ``` #### Release and Deployment Scripts ```bash # Release notes generation node scripts/update-release-notes.js # Type checksum generation node scripts/generate-types-checksum.js ``` ### Deployment to External Projects #### 1. Publishing to npm Registry ```bash # Build the plugin npm run build # Run tests npm test # Update version npm version patch # or minor, major # Publish to npm npm publish # Verify publication npm view @timesafari/daily-notification-plugin ``` #### 2. Installing in External Capacitor Projects ```bash # Install from npm npm install @timesafari/daily-notification-plugin # Install from local development npm install /path/to/daily-notification-plugin # Install from git repository npm install git+https://gitea.anomalistdesign.com/trent_larson/daily-notification-plugin.git ``` #### 3. Integration in Host Applications ```bash # Add to Capacitor project npx cap add android npx cap add ios # Sync with Capacitor npx cap sync android npx cap sync ios # Build and run npx cap run android npx cap run ios ``` #### 4. Version Management ```bash # Check current version npm list @timesafari/daily-notification-plugin # Update to latest version npm update @timesafari/daily-notification-plugin # Install specific version npm install @timesafari/daily-notification-plugin@1.2.3 ``` ### For Plugin Development #### 1. Edit Plugin Code ```bash # Edit TypeScript interface vim src/definitions.ts # Edit Android native code vim android/src/main/java/com/timesafari/dailynotification/DailyNotificationPlugin.kt # Edit iOS native code vim ios/Plugin/DailyNotificationPlugin.swift ``` #### 2. Build and Test ```bash # Build plugin ./scripts/build-native.sh --platform android # Test in Capacitor app cd /path/to/test-capacitor-app npx cap sync android npx cap run android ``` #### 3. Iterate ```bash # Make changes # Build again # Test again # Repeat until working ``` ### For Production Testing #### 1. Test in TimeSafari PWA ```bash # Install plugin in TimeSafari PWA npm install @timesafari/daily-notification-plugin # Sync with Capacitor npx cap sync android npx cap sync ios # Test on real devices npx cap run android npx cap run ios ``` #### 2. Monitor and Debug ```bash # Check logs adb logcat | grep DailyNotification # Check plugin metrics # Use observability dashboards ``` ## Troubleshooting ### Clean Build (First Step for Many Issues) If you encounter persistent build issues, try a clean build first: ```bash # Clean all build artifacts (recommended first step) ./scripts/clean-build.sh # Clean everything including caches (for stubborn issues) ./scripts/clean-build.sh --all # Then rebuild ./scripts/build-native.sh --platform all ``` **When to use clean-build:** - Build errors that don't make sense - Dependency conflicts - Stale build artifacts - After switching branches - After updating dependencies ### Common Issues #### Gradle Sync Failures ```bash # Problem: Gradle sync fails # Solution: Check Java version java -version # Should be 11+ # Solution: Clear Gradle cache ./gradlew clean rm -rf ~/.gradle/caches ~/.gradle/daemon ``` #### Build Failures ```bash # Problem: Build fails with "Could not read script" # Solution: This is a plugin development project # The build script handles this automatically ./scripts/build-native.sh --platform android # Problem: Build fails with "Could not resolve project :capacitor-cordova-android-plugins" # Solution: Build the plugin module instead of the test app ./gradlew :plugin:assembleRelease # Problem: Build fails with "Cannot locate tasks that match ':android:assembleRelease'" # Solution: Use correct project name - available projects are: # - :app (test app, may have Capacitor issues) # - :plugin (plugin library, recommended) # - :capacitor-android # - :capacitor-cordova-android-plugins ./gradlew :plugin:assembleRelease # Problem: Build fails with "Plugin with id 'kotlin-android' not found" # Solution: The plugin module doesn't need Kotlin plugin for Java/Kotlin code # Check the plugin/build.gradle file ``` #### Capacitor Integration Warnings ```bash # ⚠️ WARNING: capacitor.build.gradle is auto-generated! # Any manual fixes will be lost when running: # - npx cap sync # - npx cap update # - npx cap add android # ⚠️ NOTE: npx cap sync will fail in plugin development projects! # This is expected - plugin projects don't have www/ directory # Error: "Could not find the web assets directory: ./www" # This is normal for plugin development projects # To fix after Capacitor operations: ./scripts/fix-capacitor-build.sh # Or use the build script (applies fix automatically): ./scripts/build-native.sh --platform android ``` #### Capacitor Settings Path Fix (Test App) **Note**: The plugin now uses standard Capacitor structure, so no path fixes are needed for consuming apps. The test app at `test-apps/android-test-app/` references the plugin correctly. #### Android Studio Issues ```bash # Problem: Android Studio can't find SDK # Solution: Configure SDK location File → Project Structure → SDK Location # Problem: Kotlin compilation errors # Solution: Check Kotlin version in build.gradle ``` #### iOS Build Issues ```bash # Problem: "Xcode Command Line Tools not configured" # Error: xcode-select -p fails or xcodebuild not found # Solution: Install Command Line Tools xcode-select --install # Verify installation xcode-select -p xcodebuild -version sqlite3 --version # Problem: "sqlite3 not found" or linker errors with SQLite # Solution: Ensure Command Line Tools are properly installed # The build script checks for this automatically, but if you see linker errors: xcode-select --install # Problem: pkgx SQLite conflicts with iOS builds # Error: Linker errors about libsqlite3.dylib # Solution: The build script automatically handles this by unsetting problematic # environment variables. If issues persist: unset PKGX_DIR DYLD_LIBRARY_PATH LD_LIBRARY_PATH ./scripts/build-native.sh --platform ios # Problem: "pod install" fails # Solution: Ensure Command Line Tools are installed xcode-select --install # Then reinstall CocoaPods dependencies cd ios pod deintegrate pod install ``` #### Capacitor Integration Issues ```bash # Problem: Plugin not found in Capacitor app # Solution: Check plugin installation npm list @timesafari/daily-notification-plugin # Solution: Re-sync Capacitor npx cap sync android ``` #### AAR Duplicate Class Issues ```bash # Problem: Duplicate class errors when integrating plugin AAR # Error: "Duplicate class org.timesafari.dailynotification.BootReceiver found in modules" # Root Cause: Plugin being included both as project reference and as AAR file # Solution 1: Use Project Reference Approach (Recommended) # 1. Clear Gradle cache completely ./gradlew --stop rm -rf ~/.gradle rm -rf app/build rm -rf build # 2. Configure project reference in capacitor.settings.gradle include ':timesafari-daily-notification-plugin' project(':timesafari-daily-notification-plugin').projectDir = new File('../../../android/plugin') # 3. Add dependency in capacitor.build.gradle implementation project(':timesafari-daily-notification-plugin') # 4. Remove AAR dependency from app/build.gradle # Comment out: implementation(name: 'plugin-debug', ext: 'aar') # Solution 2: AAR-Only Approach (Alternative) # 1. Remove project references from capacitor.settings.gradle and capacitor.build.gradle # 2. Ensure only AAR dependency in app/build.gradle # 3. Remove any duplicate classes.jar files from libs/ directory # 4. Clear Gradle cache and rebuild # Verification: Check that plugin is included only once ./gradlew :app:dependencies | grep timesafari ``` ### Debug Commands #### Android Debugging ```bash # View Android logs adb logcat | grep DailyNotification # Check plugin installation adb shell pm list packages | grep timesafari # Test background tasks adb shell am start -n com.capacitorjs.app/.MainActivity ``` #### iOS Debugging ```bash # View iOS logs xcrun simctl spawn booted log stream --predicate 'subsystem contains "DailyNotification"' # Check plugin installation # Use Xcode Organizer or Device Manager ``` ### Performance Issues #### Build Performance ```bash # Enable Gradle daemon echo "org.gradle.daemon=true" >> ~/.gradle/gradle.properties # Increase memory echo "org.gradle.jvmargs=-Xmx4g" >> ~/.gradle/gradle.properties # Enable parallel builds echo "org.gradle.parallel=true" >> ~/.gradle/gradle.properties ``` #### Android Studio Performance ```bash # Increase Android Studio memory # Help → Edit Custom VM Options -Xmx4g -XX:ReservedCodeCacheSize=1g ``` ## Project Structure ### Root Directory ``` daily-notification-plugin/ ├── android/ # Android native code ├── ios/ # iOS native code ├── src/ # TypeScript plugin interface ├── dist/ # Built plugin files ├── scripts/ # Build scripts and automation ├── test-apps/ # Test applications │ └── daily-notification-test/ # Vue 3 test app ├── doc/ # Documentation ├── examples/ # Usage examples ├── tests/ # Test files ├── package.json # Node.js dependencies ├── tsconfig.json # TypeScript configuration ├── rollup.config.js # Bundler configuration └── BUILDING.md # This file ``` ### Android Structure ``` android/ ├── src/main/java/ # Plugin source code ├── build.gradle # Plugin build configuration └── variables.gradle # Gradle variables ``` ### iOS Structure ``` ios/ ├── Plugin/ # Swift plugin code ├── DailyNotificationPlugin.xcodeproj/ # Xcode project ├── DailyNotificationPlugin.xcworkspace/ # Xcode workspace ├── Podfile # CocoaPods dependencies └── Tests/ # iOS unit tests ``` ### Test Apps Structure ``` test-apps/ └── daily-notification-test/ # Vue 3 test application ├── src/ # Vue 3 source code │ ├── views/ # Test interface views │ ├── components/ # Reusable UI components │ ├── stores/ # Pinia state management │ └── router/ # Vue Router configuration ├── android/ # Android Capacitor app │ ├── app/ # Android app module │ ├── dailynotification/ # Plugin module │ └── build.gradle # Android build config ├── docs/ # Test app documentation ├── scripts/ # Test app build scripts ├── package.json # Vue 3 dependencies └── vite.config.ts # Vite build configuration ``` ### Scripts Structure ``` scripts/ ├── build-native.sh # Main build script ├── build-timesafari.js # TimeSafari-specific builds ├── comprehensive-test-v2.sh # Full test suite ├── fix-capacitor-build.sh # Capacitor build fixes ├── setup-gradle.sh # Gradle setup automation ├── setup-native.js # Native environment setup ├── check-environment.js # Environment validation ├── chaos-test.js # Reliability testing ├── check-api-changes.js # API change detection ├── check-bundle-size.js # Bundle size monitoring ├── daily-notification-test.sh # Notification testing ├── daily-notification-test.py # Python test runner ├── update-release-notes.js # Release notes generation └── generate-types-checksum.js # Type checksum generation ``` ## Best Practices ### Code Organization - Keep plugin code modular and testable - Use consistent naming conventions - Document all public APIs - Follow platform-specific coding standards ### Build Optimization - Use incremental builds when possible - Cache build artifacts - Parallelize builds where supported - Monitor build times and optimize ### Testing Strategy - Write unit tests for all plugin logic - Test on real devices, not just simulators - Test edge cases and error conditions - Monitor performance and memory usage ### Documentation - Keep BUILDING.md updated - Document all build requirements - Provide troubleshooting guides - Include examples and best practices ## Support ### Getting Help - Check the [troubleshooting section](#troubleshooting) - Review [GitHub issues](https://gitea.anomalistdesign.com/trent_larson/daily-notification-plugin/issues) - Consult [Capacitor documentation](https://capacitorjs.com/docs) - Ask in [Capacitor community](https://github.com/ionic-team/capacitor/discussions) ### Contributing - Follow the [contributing guidelines](CONTRIBUTING.md) - Test all changes thoroughly - Update documentation as needed - Submit pull requests with clear descriptions --- **Remember**: This is a Capacitor plugin development project. For full functionality testing, use it in a Capacitor host application, not as a standalone Android/iOS app.