native-update 1.4.9 → 3.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (265) hide show
  1. package/Readme.md +35 -9
  2. package/android/manifest-additions.xml +28 -0
  3. package/android/src/main/AndroidManifest.xml +3 -7
  4. package/android/src/main/java/com/aoneahsan/nativeupdate/BackgroundNotificationManager.kt +21 -13
  5. package/android/src/main/java/com/aoneahsan/nativeupdate/BackgroundUpdatePlugin.kt +15 -0
  6. package/android/src/main/java/com/aoneahsan/nativeupdate/BackgroundUpdateWorker.kt +23 -7
  7. package/android/src/main/java/com/aoneahsan/nativeupdate/LiveUpdatePlugin.kt +346 -31
  8. package/android/src/main/java/com/aoneahsan/nativeupdate/NativeUpdatePlugin.kt +32 -34
  9. package/android/src/main/java/com/aoneahsan/nativeupdate/NotificationActionReceiver.kt +10 -1
  10. package/android/src/main/java/com/aoneahsan/nativeupdate/SecurityManager.kt +18 -18
  11. package/cli/AGENTS.md +43 -0
  12. package/cli/CLAUDE.md +65 -0
  13. package/cli/commands/backend-create.js +56 -15
  14. package/cli/commands/bundle-create.js +39 -7
  15. package/cli/commands/monitor.js +72 -51
  16. package/cli/index.js +10 -24
  17. package/cli/package.json +11 -3
  18. package/dist/esm/app-review/app-review-manager.js +0 -1
  19. package/dist/esm/app-review/index.js +0 -1
  20. package/dist/esm/app-review/platform-review-handler.js +0 -1
  21. package/dist/esm/app-review/review-conditions-checker.js +0 -1
  22. package/dist/esm/app-review/review-rate-limiter.js +0 -1
  23. package/dist/esm/app-review/types.js +0 -1
  24. package/dist/esm/app-update/app-update-checker.js +0 -1
  25. package/dist/esm/app-update/app-update-installer.d.ts +1 -0
  26. package/dist/esm/app-update/app-update-installer.js +19 -8
  27. package/dist/esm/app-update/app-update-manager.js +0 -1
  28. package/dist/esm/app-update/app-update-notifier.js +0 -1
  29. package/dist/esm/app-update/index.js +0 -1
  30. package/dist/esm/app-update/platform-app-update.js +12 -3
  31. package/dist/esm/app-update/types.js +0 -1
  32. package/dist/esm/background-update/background-scheduler.js +0 -1
  33. package/dist/esm/background-update/index.js +0 -1
  34. package/dist/esm/background-update/notification-manager.js +0 -1
  35. package/dist/esm/config/support.js +0 -1
  36. package/dist/esm/core/analytics.d.ts +13 -0
  37. package/dist/esm/core/analytics.js +15 -1
  38. package/dist/esm/core/cache-manager.js +0 -1
  39. package/dist/esm/core/config.d.ts +6 -30
  40. package/dist/esm/core/config.js +1 -8
  41. package/dist/esm/core/errors.d.ts +1 -0
  42. package/dist/esm/core/errors.js +1 -1
  43. package/dist/esm/core/event-emitter.d.ts +0 -3
  44. package/dist/esm/core/event-emitter.js +8 -3
  45. package/dist/esm/core/logger.js +0 -1
  46. package/dist/esm/core/performance.js +0 -1
  47. package/dist/esm/core/plugin-manager.js +3 -1
  48. package/dist/esm/core/security.d.ts +22 -3
  49. package/dist/esm/core/security.js +46 -7
  50. package/dist/esm/definitions.d.ts +13 -40
  51. package/dist/esm/definitions.js +0 -1
  52. package/dist/esm/index.d.ts +3 -4
  53. package/dist/esm/index.js +3 -3
  54. package/dist/esm/live-update/bundle-manager.d.ts +8 -0
  55. package/dist/esm/live-update/bundle-manager.js +20 -1
  56. package/dist/esm/live-update/certificate-pinning.js +0 -1
  57. package/dist/esm/live-update/delta-processor.d.ts +1 -1
  58. package/dist/esm/live-update/delta-processor.js +3 -1
  59. package/dist/esm/live-update/download-manager.d.ts +36 -5
  60. package/dist/esm/live-update/download-manager.js +70 -24
  61. package/dist/esm/live-update/rollout-checker.d.ts +1 -1
  62. package/dist/esm/live-update/rollout-checker.js +5 -6
  63. package/dist/esm/live-update/update-manager.d.ts +12 -1
  64. package/dist/esm/live-update/update-manager.js +38 -11
  65. package/dist/esm/live-update/version-manager.d.ts +9 -12
  66. package/dist/esm/live-update/version-manager.js +40 -68
  67. package/dist/esm/plugin.js +82 -89
  68. package/dist/esm/security/crypto.js +11 -7
  69. package/dist/esm/security/validator.js +0 -1
  70. package/dist/esm/types/rollout.d.ts +85 -0
  71. package/dist/esm/types/rollout.js +25 -0
  72. package/dist/esm/web.d.ts +26 -1
  73. package/dist/esm/web.js +214 -75
  74. package/dist/plugin.cjs.js +1 -2
  75. package/dist/plugin.esm.js +1 -2
  76. package/dist/plugin.js +2 -3
  77. package/docs/AGENTS.md +38 -0
  78. package/docs/CHANGELOG.md +275 -0
  79. package/docs/CLAUDE.md +101 -0
  80. package/docs/MANUAL-TASKS.md +17 -0
  81. package/docs/MARKETING_WEBSITE_TRACKER.md +18 -2
  82. package/docs/MIGRATION.md +170 -0
  83. package/docs/PACKAGES.md +167 -0
  84. package/docs/PERFORMANCE.md +110 -0
  85. package/docs/PROJECT_COMPLETION_TRACKER.md +4 -35
  86. package/docs/README.md +12 -2
  87. package/docs/REMAINING_FEATURES.md +123 -76
  88. package/docs/ROADMAP.md +200 -120
  89. package/docs/SECURITY-IF-REPO-PUBLIC.md +232 -0
  90. package/docs/TESTING_REQUIREMENTS.md +1 -112
  91. package/docs/ai-knowledge-base/00-project-profile.md +38 -0
  92. package/docs/ai-knowledge-base/01-features.md +46 -0
  93. package/docs/ai-knowledge-base/02-routes.md +72 -0
  94. package/docs/ai-knowledge-base/03-tech-stack.md +57 -0
  95. package/docs/ai-knowledge-base/README.md +23 -0
  96. package/docs/analytics-tracking.md +37 -0
  97. package/docs/capacitor-official-plugins.md +46 -0
  98. package/docs/capawesome-plugins.md +29 -0
  99. package/docs/deployment/HOSTINGER_DEPLOY.md +370 -0
  100. package/docs/deployment/PRODUCTION-DEPLOY-CHECKLIST.md +184 -0
  101. package/docs/docs-site/plan.md +201 -0
  102. package/docs/docs-site/scope.md +127 -0
  103. package/docs/docs-site/tracker.json +235 -0
  104. package/docs/error-handling-tracking.md +37 -0
  105. package/docs/features/laravel-nova-backend/ASSESSMENT-SUMMARY.md +96 -0
  106. package/docs/features/laravel-nova-backend/IMPLEMENTATION-PLAN.md +504 -0
  107. package/docs/features/laravel-nova-backend/progress-tracker.json +184 -0
  108. package/docs/guides/testing-guide.md +15 -41
  109. package/docs/package-audit.md +41 -0
  110. package/docs/play-store/ASO-METADATA.md +5 -0
  111. package/docs/play-store/DATA-SAFETY.md +5 -0
  112. package/docs/play-store/DECLARATIONS.md +5 -0
  113. package/docs/play-store/README.md +27 -0
  114. package/docs/play-store/RELEASE-NOTES.md +99 -0
  115. package/docs/play-store/RELEASE-STEPS.md +6 -0
  116. package/docs/play-store/STORE-LISTING.md +7 -0
  117. package/docs/play-store/SUBMISSION-CHECKLIST.md +5 -0
  118. package/docs/production-readiness.md +1 -1
  119. package/docs/project-audit/2026-05-16/00-FINALIZATION-PLAN.md +123 -0
  120. package/docs/project-audit/2026-05-16/01-BATCH-PLAN.md +227 -0
  121. package/docs/project-audit/2026-05-16/02-AUDIT-FINDINGS.md +144 -0
  122. package/docs/project-audit/2026-05-16/sessions/batch-01.md +42 -0
  123. package/docs/project-audit/2026-05-16/sessions/batch-02.md +74 -0
  124. package/docs/project-audit/2026-05-16/sessions/batch-03.md +71 -0
  125. package/docs/project-audit/2026-05-16/sessions/batch-04.md +88 -0
  126. package/docs/project-audit/2026-05-16/sessions/batch-05.md +63 -0
  127. package/docs/project-audit/2026-05-16/sessions/batch-06.md +103 -0
  128. package/docs/project-audit/2026-05-16/sessions/batch-07.md +61 -0
  129. package/docs/project-audit/2026-05-16/sessions/batch-08.md +101 -0
  130. package/docs/project-audit/2026-05-16/sessions/batch-09.md +105 -0
  131. package/docs/project-audit/2026-05-16/sessions/batch-10.md +102 -0
  132. package/docs/project-audit/AUDIT-HISTORY.md +74 -0
  133. package/docs/project-audit/BATCH-PLAN.md +168 -0
  134. package/docs/project-audit/MARKETING-WEBSITE-FINDINGS-2026-05-11.md +73 -0
  135. package/docs/project-audit/PRODUCTION-READINESS-AUDIT-2026-05-08.md +275 -0
  136. package/docs/project-finalization/00-tracker.json +60 -0
  137. package/docs/project-knowledge-base/01-system-overview.md +227 -0
  138. package/docs/project-knowledge-base/02-routes-pages-forms-users.md +352 -0
  139. package/docs/project-knowledge-base/03-tech-stack-modules-services.md +379 -0
  140. package/docs/project-knowledge-base/04-data-models-integrations.md +244 -0
  141. package/docs/project-knowledge-base/05-docs-corpus-inventory.md +256 -0
  142. package/docs/project-knowledge-base/06-operations-testing-legal-content.md +208 -0
  143. package/docs/project-knowledge-base/README.md +103 -0
  144. package/docs/project-profiles/native-update-capacitor-update-platform-project-profile-last-updated-2026-05-19.md +81 -0
  145. package/docs/rules-tracker.md +102 -0
  146. package/docs/security/PRE-LAUNCH-PENTEST-CHECKLIST.md +116 -0
  147. package/docs/seo-aeo-rules.json +3043 -0
  148. package/docs/social-media-marketing/README.md +81 -0
  149. package/docs/social-media-marketing/posts-batch-01.md +613 -0
  150. package/docs/social-media-marketing/posts-batch-02.md +528 -0
  151. package/docs/social-media-marketing/whatsapp-messages-batch-01.md +458 -0
  152. package/docs/social-media-marketing/whatsapp-status-batch-01.md +355 -0
  153. package/docs/tracking/finalization-2026-05-16-tracker.json +346 -0
  154. package/docs/tracking/full-audit-tracker.json +121 -0
  155. package/docs/tracking/production-readiness-audit-tracker.json +429 -0
  156. package/docs/tracking/seo-checklist-tracker.json +333 -0
  157. package/ios/Plugin/BackgroundUpdate/BackgroundUpdatePlugin.swift +66 -9
  158. package/ios/Plugin/LiveUpdate/LiveUpdatePlugin.swift +306 -52
  159. package/ios/Plugin/NativeUpdatePlugin.swift +22 -9
  160. package/ios/Plugin/Security/SecurityManager.swift +13 -14
  161. package/package.json +37 -38
  162. package/cli/node_modules/.yarn-integrity +0 -16
  163. package/cli/node_modules/commander/LICENSE +0 -22
  164. package/cli/node_modules/commander/Readme.md +0 -1148
  165. package/cli/node_modules/commander/esm.mjs +0 -16
  166. package/cli/node_modules/commander/index.js +0 -26
  167. package/cli/node_modules/commander/lib/argument.js +0 -145
  168. package/cli/node_modules/commander/lib/command.js +0 -2179
  169. package/cli/node_modules/commander/lib/error.js +0 -43
  170. package/cli/node_modules/commander/lib/help.js +0 -462
  171. package/cli/node_modules/commander/lib/option.js +0 -329
  172. package/cli/node_modules/commander/lib/suggestSimilar.js +0 -100
  173. package/cli/node_modules/commander/package-support.json +0 -16
  174. package/cli/node_modules/commander/package.json +0 -80
  175. package/cli/node_modules/commander/typings/esm.d.mts +0 -3
  176. package/cli/node_modules/commander/typings/index.d.ts +0 -884
  177. package/cli/yarn.lock +0 -8
  178. package/dist/esm/__tests__/bundle-manager.test.d.ts +0 -1
  179. package/dist/esm/__tests__/bundle-manager.test.js +0 -151
  180. package/dist/esm/__tests__/bundle-manager.test.js.map +0 -1
  181. package/dist/esm/__tests__/config.test.d.ts +0 -1
  182. package/dist/esm/__tests__/config.test.js +0 -70
  183. package/dist/esm/__tests__/config.test.js.map +0 -1
  184. package/dist/esm/__tests__/delta-processor.test.d.ts +0 -1
  185. package/dist/esm/__tests__/delta-processor.test.js +0 -77
  186. package/dist/esm/__tests__/delta-processor.test.js.map +0 -1
  187. package/dist/esm/__tests__/firestore-schema.test.d.ts +0 -1
  188. package/dist/esm/__tests__/firestore-schema.test.js +0 -74
  189. package/dist/esm/__tests__/firestore-schema.test.js.map +0 -1
  190. package/dist/esm/__tests__/integration.test.d.ts +0 -1
  191. package/dist/esm/__tests__/integration.test.js +0 -78
  192. package/dist/esm/__tests__/integration.test.js.map +0 -1
  193. package/dist/esm/__tests__/manifest-reader.test.d.ts +0 -1
  194. package/dist/esm/__tests__/manifest-reader.test.js +0 -271
  195. package/dist/esm/__tests__/manifest-reader.test.js.map +0 -1
  196. package/dist/esm/__tests__/rollout-checker.test.d.ts +0 -1
  197. package/dist/esm/__tests__/rollout-checker.test.js +0 -210
  198. package/dist/esm/__tests__/rollout-checker.test.js.map +0 -1
  199. package/dist/esm/__tests__/security.test.d.ts +0 -1
  200. package/dist/esm/__tests__/security.test.js +0 -54
  201. package/dist/esm/__tests__/security.test.js.map +0 -1
  202. package/dist/esm/__tests__/version-manager.test.d.ts +0 -1
  203. package/dist/esm/__tests__/version-manager.test.js +0 -45
  204. package/dist/esm/__tests__/version-manager.test.js.map +0 -1
  205. package/dist/esm/app-review/app-review-manager.js.map +0 -1
  206. package/dist/esm/app-review/index.js.map +0 -1
  207. package/dist/esm/app-review/platform-review-handler.js.map +0 -1
  208. package/dist/esm/app-review/review-conditions-checker.js.map +0 -1
  209. package/dist/esm/app-review/review-rate-limiter.js.map +0 -1
  210. package/dist/esm/app-review/types.js.map +0 -1
  211. package/dist/esm/app-update/app-update-checker.js.map +0 -1
  212. package/dist/esm/app-update/app-update-installer.js.map +0 -1
  213. package/dist/esm/app-update/app-update-manager.js.map +0 -1
  214. package/dist/esm/app-update/app-update-notifier.js.map +0 -1
  215. package/dist/esm/app-update/index.js.map +0 -1
  216. package/dist/esm/app-update/platform-app-update.js.map +0 -1
  217. package/dist/esm/app-update/types.js.map +0 -1
  218. package/dist/esm/background-update/background-scheduler.js.map +0 -1
  219. package/dist/esm/background-update/index.js.map +0 -1
  220. package/dist/esm/background-update/notification-manager.js.map +0 -1
  221. package/dist/esm/config/support.js.map +0 -1
  222. package/dist/esm/core/analytics.js.map +0 -1
  223. package/dist/esm/core/cache-manager.js.map +0 -1
  224. package/dist/esm/core/config.js.map +0 -1
  225. package/dist/esm/core/errors.js.map +0 -1
  226. package/dist/esm/core/event-emitter.js.map +0 -1
  227. package/dist/esm/core/logger.js.map +0 -1
  228. package/dist/esm/core/performance.js.map +0 -1
  229. package/dist/esm/core/plugin-manager.js.map +0 -1
  230. package/dist/esm/core/security.js.map +0 -1
  231. package/dist/esm/definitions.js.map +0 -1
  232. package/dist/esm/firestore/firestore-client.d.ts +0 -109
  233. package/dist/esm/firestore/firestore-client.js +0 -264
  234. package/dist/esm/firestore/firestore-client.js.map +0 -1
  235. package/dist/esm/firestore/index.d.ts +0 -11
  236. package/dist/esm/firestore/index.js +0 -11
  237. package/dist/esm/firestore/index.js.map +0 -1
  238. package/dist/esm/firestore/manifest-reader.d.ts +0 -87
  239. package/dist/esm/firestore/manifest-reader.js +0 -294
  240. package/dist/esm/firestore/manifest-reader.js.map +0 -1
  241. package/dist/esm/firestore/schema.d.ts +0 -507
  242. package/dist/esm/firestore/schema.js +0 -73
  243. package/dist/esm/firestore/schema.js.map +0 -1
  244. package/dist/esm/index.js.map +0 -1
  245. package/dist/esm/live-update/bundle-manager.js.map +0 -1
  246. package/dist/esm/live-update/certificate-pinning.js.map +0 -1
  247. package/dist/esm/live-update/delta-processor.js.map +0 -1
  248. package/dist/esm/live-update/download-manager.js.map +0 -1
  249. package/dist/esm/live-update/rollout-checker.js.map +0 -1
  250. package/dist/esm/live-update/update-manager.js.map +0 -1
  251. package/dist/esm/live-update/version-manager.js.map +0 -1
  252. package/dist/esm/plugin.js.map +0 -1
  253. package/dist/esm/security/crypto.js.map +0 -1
  254. package/dist/esm/security/validator.js.map +0 -1
  255. package/dist/esm/web.js.map +0 -1
  256. package/dist/plugin.cjs.js.map +0 -1
  257. package/dist/plugin.esm.js.map +0 -1
  258. package/dist/plugin.js.map +0 -1
  259. package/docs/FIREBASE_INTEGRATION_TRACKER.md +0 -321
  260. package/docs/FIREBASE_QUERIES_AND_INDEXES_AUDIT.md +0 -221
  261. package/docs/examples/firebase-backend-example.md +0 -27
  262. package/docs/guides/no-cost-backend-implementation-plan.md +0 -77
  263. package/docs/guides/no-cost-firestore-google-drive-backend.md +0 -60
  264. package/docs/play-console-rejection-rules.json +0 -428
  265. /package/docs/{MARKETING_WEBSITE_PLAN.md → archive/MARKETING_WEBSITE_PLAN.md} +0 -0
package/Readme.md CHANGED
@@ -7,12 +7,24 @@
7
7
  > - ✅ **yarn Workspace Monorepo** - Seamless development with workspace:* references
8
8
  > - ✅ **3 Complete Examples** - React+Capacitor frontend, Node.js+Express and Firebase backends in `example-apps/`
9
9
  > - ✅ **Native Implementations Complete** - iOS (Swift) and Android (Kotlin) fully implemented
10
- > - ✅ **Comprehensive Test Suite** - Unit and integration tests with Vitest
11
10
  > - ✅ **Development Tools Included** - Bundle creator, signer, and CLI tools
12
11
  > - ✅ **Security Features Implemented** - HTTPS enforcement, signatures, checksums
13
12
  >
14
13
  > **🚀 Try the example apps in `example-apps/` to see all features in action!**
15
14
 
15
+ ## Current State
16
+
17
+ - Package version: `3.1.0`
18
+ - Verified on: `2026-05-18`
19
+ - Tests: `134/134` backend PHPUnit via `php artisan test`
20
+ - Build: `yarn build` succeeds (root plugin Rollup + website Vite + Docusaurus docs site)
21
+ - Root package manager is standardized on Yarn, and the root scripts no longer shell out to npm or pnpm
22
+ - Backend: Laravel 13 + Nova 5 — the only backend after v3.0.0 (Firestore removed); identity via Laravel Socialite + Sanctum personal access tokens; RBAC via `spatie/laravel-permission` (roles `super-admin`, `admin`, `user`)
23
+ - Root portfolio info file:
24
+ - `NATIVE-UPDATE_portfolio-info_2026-06-26.md`
25
+ - Current dated project profile:
26
+ - `docs/project-profiles/native-update-capacitor-update-platform-project-profile-last-updated-2026-05-19.md`
27
+
16
28
  ## 📚 Documentation
17
29
 
18
30
  - **[AI Integration Guide](https://nativeupdate.aoneahsan.com/docs/AI-INTEGRATION-GUIDE)** - Quick reference for AI development agents (Claude, Cursor, Copilot)
@@ -61,7 +73,7 @@
61
73
 
62
74
  ---
63
75
 
64
- A **foundation package** for building a comprehensive update management plugin for Capacitor that combines Live/OTA updates, native app store updates, and in-app review capabilities. This package provides the architecture, interfaces, and documentation but requires additional implementation work.
76
+ A production-oriented Capacitor update platform that combines Live/OTA updates, native app store update flows, in-app reviews, release tooling, dashboard support, example backends, and operational documentation in one ecosystem.
65
77
 
66
78
  ## 🌐 Dashboard & Management Platform
67
79
 
@@ -356,15 +368,19 @@ This repository uses **yarn workspace** for seamless development. All examples r
356
368
  - ✅ Rate limiting and compression
357
369
  - ✅ Signature verification
358
370
 
359
- #### 2. Firebase Functions Backend
371
+ #### 2. Laravel + Nova SaaS Backend
360
372
 
361
- **[Firebase Backend Example](https://nativeupdate.aoneahsan.com/docs/examples/firebase-backend-example)**
373
+ The canonical backend ships in this monorepo under [`backend/`](./backend) — a
374
+ Laravel 13 + Nova 5 application that powers the hosted Native Update SaaS at
375
+ `api.nativeupdate.aoneahsan.com`. You can use it as a managed service or
376
+ self-host it on any PHP 8.2+ host. Setup is documented in
377
+ [`docs/deployment/PRODUCTION-DEPLOY-CHECKLIST.md`](./docs/deployment/PRODUCTION-DEPLOY-CHECKLIST.md).
362
378
 
363
- - ✅ Serverless architecture with Firebase
364
- - ✅ Cloud Functions for bundle management
365
- - ✅ Firestore for bundle metadata
366
- - ✅ Firebase Storage for bundle hosting
367
- - ✅ Auto-scaling infrastructure
379
+ - ✅ Google OAuth (Socialite) + Sanctum bearer tokens + spatie/laravel-permission RBAC
380
+ - ✅ MySQL / PostgreSQL bundle metadata + signed download URLs
381
+ - ✅ Per-app API keys + signing keys generated through Nova
382
+ - ✅ Per-bundle rollout percentages + per-device rollout buckets
383
+ - ✅ Google Drive integration so bundle ZIPs stay in your own Drive
368
384
 
369
385
  **🚀 Get started:** Each example app has its own README with setup instructions.
370
386
 
@@ -530,3 +546,13 @@ MIT License - see [LICENSE](./LICENSE) for details.
530
546
  - LinkedIn: [linkedin.com/in/aoneahsan](https://linkedin.com/in/aoneahsan)
531
547
  - Email: aoneahsan@gmail.com
532
548
  - Phone: +923046619706
549
+
550
+ <!-- project-links:start -->
551
+ ## Links
552
+
553
+ - Live: https://nativeupdate.aoneahsan.com
554
+ - Play Store: https://play.google.com/store/apps/details?id=com.aoneahsan.nativeupdate
555
+ - NPM: https://www.npmjs.com/package/native-update
556
+
557
+ _URL source of truth: `01-code/projects/project-live-urls.json` (auto-generated — do not hand-edit between these markers)._
558
+ <!-- project-links:end -->
@@ -0,0 +1,28 @@
1
+ <!--
2
+ IMPORTANT: These elements MUST be added to your app's AndroidManifest.xml inside the <application> tag
3
+ when using background update features of the native-update plugin.
4
+
5
+ Without these additions:
6
+ 1. Background updates will crash with ServiceNotFoundException
7
+ 2. Update notification buttons won't work (they'll appear but won't respond to taps)
8
+ 3. Downloads won't continue when app is in background
9
+
10
+ Location: android/app/src/main/AndroidManifest.xml (in your app, not in the plugin)
11
+ -->
12
+
13
+ <!-- WorkManager service for background updates -->
14
+ <service
15
+ android:name="androidx.work.impl.foreground.SystemForegroundService"
16
+ android:foregroundServiceType="dataSync"
17
+ tools:node="merge" />
18
+
19
+ <!-- Broadcast receiver for notification actions -->
20
+ <receiver
21
+ android:name="com.aoneahsan.nativeupdate.NotificationActionReceiver"
22
+ android:exported="false">
23
+ <intent-filter>
24
+ <action android:name="com.aoneahsan.nativeupdate.UPDATE_NOW" />
25
+ <action android:name="com.aoneahsan.nativeupdate.UPDATE_LATER" />
26
+ <action android:name="com.aoneahsan.nativeupdate.DISMISS" />
27
+ </intent-filter>
28
+ </receiver>
@@ -1,17 +1,13 @@
1
1
  <manifest xmlns:android="http://schemas.android.com/apk/res/android">
2
-
2
+
3
3
  <!-- Required permissions -->
4
4
  <uses-permission android:name="android.permission.INTERNET" />
5
5
  <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
6
-
7
- <!-- Optional permissions (requested at runtime) -->
8
- <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"
9
- android:maxSdkVersion="28" />
10
-
6
+
11
7
  <!-- Background update permissions -->
12
8
  <uses-permission android:name="android.permission.WAKE_LOCK" />
13
9
  <uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
14
10
  <uses-permission android:name="android.permission.POST_NOTIFICATIONS" />
15
11
  <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
16
-
12
+
17
13
  </manifest>
@@ -22,9 +22,12 @@ class BackgroundNotificationManager(
22
22
  private const val CHANNEL_ID = "capacitor_native_update"
23
23
  private const val CHANNEL_NAME = "App Updates"
24
24
  private const val NOTIFICATION_ID = 1001
25
- private const val ACTION_UPDATE_NOW = "com.aoneahsan.nativeupdate.UPDATE_NOW"
26
- private const val ACTION_UPDATE_LATER = "com.aoneahsan.nativeupdate.UPDATE_LATER"
27
- private const val ACTION_DISMISS = "com.aoneahsan.nativeupdate.DISMISS"
25
+ // Action strings MUST match NotificationActionReceiver's
26
+ // companion-object constants. They were `UPDATE_NOW` here and
27
+ // `INSTALL_NOW` there, so every action button silently no-op'd.
28
+ private const val ACTION_UPDATE_NOW = NotificationActionReceiver.ACTION_INSTALL_NOW
29
+ private const val ACTION_UPDATE_LATER = NotificationActionReceiver.ACTION_INSTALL_LATER
30
+ private const val ACTION_DISMISS = NotificationActionReceiver.ACTION_DISMISS
28
31
 
29
32
  /**
30
33
  * Static method to cancel notification from BroadcastReceiver
@@ -259,8 +262,11 @@ class BackgroundNotificationManager(
259
262
  ) {
260
263
  val actionLabels = preferences.actionLabels ?: ActionLabels.default()
261
264
 
262
- // Update Now action
263
- val updateNowIntent = Intent(ACTION_UPDATE_NOW).apply {
265
+ // Explicit intents (component set) — Android 8+ blocks implicit
266
+ // broadcasts to non-exported manifest receivers, which silently
267
+ // dropped these notifications before this fix.
268
+ val updateNowIntent = Intent(context, NotificationActionReceiver::class.java).apply {
269
+ action = ACTION_UPDATE_NOW
264
270
  putExtra("update_type", if (appUpdate?.updateAvailable == true) "app_update" else "live_update")
265
271
  }
266
272
  val updateNowPendingIntent = PendingIntent.getBroadcast(
@@ -269,30 +275,32 @@ class BackgroundNotificationManager(
269
275
  updateNowIntent,
270
276
  PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
271
277
  )
272
-
278
+
273
279
  builder.addAction(
274
280
  android.R.drawable.ic_menu_upload,
275
281
  actionLabels.updateNow ?: "Update Now",
276
282
  updateNowPendingIntent
277
283
  )
278
-
279
- // Update Later action
280
- val updateLaterIntent = Intent(ACTION_UPDATE_LATER)
284
+
285
+ val updateLaterIntent = Intent(context, NotificationActionReceiver::class.java).apply {
286
+ action = ACTION_UPDATE_LATER
287
+ }
281
288
  val updateLaterPendingIntent = PendingIntent.getBroadcast(
282
289
  context,
283
290
  2,
284
291
  updateLaterIntent,
285
292
  PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
286
293
  )
287
-
294
+
288
295
  builder.addAction(
289
296
  android.R.drawable.ic_menu_recent_history,
290
297
  actionLabels.updateLater ?: "Later",
291
298
  updateLaterPendingIntent
292
299
  )
293
-
294
- // Dismiss action
295
- val dismissIntent = Intent(ACTION_DISMISS)
300
+
301
+ val dismissIntent = Intent(context, NotificationActionReceiver::class.java).apply {
302
+ action = ACTION_DISMISS
303
+ }
296
304
  val dismissPendingIntent = PendingIntent.getBroadcast(
297
305
  context,
298
306
  3,
@@ -81,6 +81,15 @@ class BackgroundUpdatePlugin : Plugin() {
81
81
  val workRequest = OneTimeWorkRequestBuilder<BackgroundUpdateWorker>()
82
82
  .setInputData(createWorkData())
83
83
  .addTag(WORK_TAG)
84
+ // Exponential backoff starting at 30s. WorkManager's default
85
+ // is 10s which hits a failing server too fast and burns
86
+ // battery on mobile. 30s base, doubled each retry, caps
87
+ // automatically at WorkManager's internal max (~5 hours).
88
+ .setBackoffCriteria(
89
+ BackoffPolicy.EXPONENTIAL,
90
+ 30,
91
+ TimeUnit.SECONDS
92
+ )
84
93
  .build()
85
94
 
86
95
  WorkManager.getInstance(context)
@@ -141,6 +150,12 @@ class BackgroundUpdatePlugin : Plugin() {
141
150
  .setConstraints(constraints)
142
151
  .setInputData(createWorkData())
143
152
  .addTag(WORK_TAG)
153
+ // See triggerBackgroundCheck — same 30s exponential base.
154
+ .setBackoffCriteria(
155
+ BackoffPolicy.EXPONENTIAL,
156
+ 30,
157
+ TimeUnit.SECONDS
158
+ )
144
159
  .build()
145
160
 
146
161
  WorkManager.getInstance(context)
@@ -17,31 +17,47 @@ class BackgroundUpdateWorker(
17
17
  companion object {
18
18
  private const val TAG = "BackgroundUpdateWorker"
19
19
  private const val NOTIFICATION_ID = 1001
20
+ // Cap the number of automatic retries for a transient failure
21
+ // (network error, backend 5xx, etc). WorkManager does not cap
22
+ // retries natively for our periodic request — without this guard
23
+ // a persistently-failing server would burn battery indefinitely.
24
+ // The schedule (with exponential backoff starting at 30s) takes
25
+ // roughly 30+60+120+240+480 = ~15 minutes across 5 retries, after
26
+ // which we give up until the next periodic run.
27
+ private const val MAX_RETRY_ATTEMPTS = 5
20
28
  }
21
-
29
+
22
30
  override suspend fun doWork(): Result {
23
31
  return withContext(Dispatchers.IO) {
24
32
  try {
33
+ if (runAttemptCount >= MAX_RETRY_ATTEMPTS) {
34
+ android.util.Log.w(
35
+ TAG,
36
+ "Giving up after $runAttemptCount retries; will try again on next periodic run"
37
+ )
38
+ return@withContext Result.failure()
39
+ }
40
+
25
41
  val configJson = inputData.getString("config")
26
42
  val config = parseConfig(configJson)
27
-
43
+
28
44
  if (config == null || !config.enabled) {
29
45
  return@withContext Result.failure()
30
46
  }
31
-
47
+
32
48
  val result = performBackgroundCheck(config)
33
-
49
+
34
50
  // Update plugin status
35
51
  updatePluginStatus(result)
36
-
52
+
37
53
  // Send notification if updates found
38
54
  if (result.updatesFound) {
39
55
  sendNotification(result)
40
56
  }
41
-
57
+
42
58
  // Notify listeners
43
59
  notifyListeners(result)
44
-
60
+
45
61
  if (result.success) Result.success() else Result.retry()
46
62
  } catch (e: Exception) {
47
63
  android.util.Log.e(TAG, "Background update failed", e)