android-ai-skills 1.3.0 → 1.4.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.
- package/CHANGELOG.md +7 -0
- package/README.md +250 -0
- package/android-auth-identity/SKILL.md +36 -0
- package/android-auth-identity/references/biometric_auth.md +36 -0
- package/android-auth-identity/references/credential_manager.md +32 -0
- package/android-auth-identity/references/google_sign_in.md +39 -0
- package/android-auth-identity/references/session_security.md +33 -0
- package/android-auth-identity/references/token_management.md +33 -0
- package/android-ci-cd/SKILL.md +36 -0
- package/android-ci-cd/references/build_optimization.md +39 -0
- package/android-ci-cd/references/fastlane.md +34 -0
- package/android-ci-cd/references/github_actions.md +35 -0
- package/android-ci-cd/references/play_store_deployment.md +36 -0
- package/android-ci-cd/references/signing_ci.md +39 -0
- package/android-dependency-injection/SKILL.md +36 -0
- package/android-dependency-injection/references/common_mistakes.md +37 -0
- package/android-dependency-injection/references/hilt_setup.md +32 -0
- package/android-dependency-injection/references/multi_module_di.md +31 -0
- package/android-dependency-injection/references/scoping.md +34 -0
- package/android-dependency-injection/references/testing_di.md +36 -0
- package/android-local-storage/SKILL.md +36 -0
- package/android-local-storage/references/cache_strategies.md +33 -0
- package/android-local-storage/references/datastore.md +35 -0
- package/android-local-storage/references/encryption.md +35 -0
- package/android-local-storage/references/offline_first.md +39 -0
- package/android-local-storage/references/room_patterns.md +34 -0
- package/android-maps-location/SKILL.md +35 -0
- package/android-maps-location/references/fused_location.md +40 -0
- package/android-maps-location/references/geofencing.md +36 -0
- package/android-maps-location/references/google_maps.md +39 -0
- package/android-maps-location/references/location_permissions.md +34 -0
- package/android-media/SKILL.md +36 -0
- package/android-media/references/audio_focus.md +34 -0
- package/android-media/references/camerax.md +40 -0
- package/android-media/references/image_loading.md +37 -0
- package/android-media/references/media3_playback.md +40 -0
- package/android-media/references/picture_in_picture.md +34 -0
- package/android-ml-ondevice/SKILL.md +35 -0
- package/android-ml-ondevice/references/gemini_nano.md +36 -0
- package/android-ml-ondevice/references/ml_kit.md +34 -0
- package/android-ml-ondevice/references/model_management.md +41 -0
- package/android-ml-ondevice/references/tensorflow_lite.md +42 -0
- package/android-networking/SKILL.md +36 -0
- package/android-networking/references/caching.md +31 -0
- package/android-networking/references/error_handling.md +32 -0
- package/android-networking/references/ktor_multiplatform.md +33 -0
- package/android-networking/references/okhttp_interceptors.md +34 -0
- package/android-networking/references/retrofit_setup.md +33 -0
- package/bin/android-ai-skills.js +30 -0
- package/firebase-best-practices/SKILL.md +37 -0
- package/firebase-best-practices/references/analytics.md +36 -0
- package/firebase-best-practices/references/cloud_messaging.md +34 -0
- package/firebase-best-practices/references/crashlytics.md +35 -0
- package/firebase-best-practices/references/firebase_auth.md +34 -0
- package/firebase-best-practices/references/firestore.md +36 -0
- package/firebase-best-practices/references/remote_config.md +34 -0
- package/package.json +11 -1
- package/play-billing-best-practices/SKILL.md +36 -0
- package/play-billing-best-practices/references/billing_client_lifecycle.md +28 -0
- package/play-billing-best-practices/references/one_time_purchases.md +29 -0
- package/play-billing-best-practices/references/server_verification.md +34 -0
- package/play-billing-best-practices/references/subscriptions.md +29 -0
- package/play-billing-best-practices/references/testing_billing.md +34 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,10 @@
|
|
|
1
|
+
# [1.4.0](https://github.com/noloman/Android-AI-skills/compare/v1.3.0...v1.4.0) (2026-02-12)
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
### Features
|
|
5
|
+
|
|
6
|
+
* add 10 more cross-cutting skills (billing, Firebase, DI, networking, storage, auth, media, CI/CD, maps, ML) ([bb2990e](https://github.com/noloman/Android-AI-skills/commit/bb2990ebd9929d0c725c99c9cfcc94c88593b702))
|
|
7
|
+
|
|
1
8
|
# [1.3.0](https://github.com/noloman/Android-AI-skills/compare/v1.2.0...v1.3.0) (2026-02-12)
|
|
2
9
|
|
|
3
10
|
|
package/README.md
CHANGED
|
@@ -55,6 +55,16 @@ These AI skills:
|
|
|
55
55
|
- Standardize **build infrastructure** (version catalogs, convention plugins, modularization)
|
|
56
56
|
- Govern **background work** (WorkManager, foreground services, notifications)
|
|
57
57
|
- Guide **navigation** (type-safe routes, deep links, App Links)
|
|
58
|
+
- Enforce **Play Billing** (subscriptions, server verification, purchase lifecycle)
|
|
59
|
+
- Integrate **Firebase** (Auth, Firestore, Crashlytics, FCM, Remote Config)
|
|
60
|
+
- Standardize **dependency injection** (Hilt scoping, multi-module DI, testing)
|
|
61
|
+
- Govern **networking** (Retrofit, OkHttp, Ktor, caching, error handling)
|
|
62
|
+
- Manage **local storage** (Room, DataStore, offline-first, encryption)
|
|
63
|
+
- Secure **authentication** (Credential Manager, biometrics, token management)
|
|
64
|
+
- Handle **media** (Media3, CameraX, image loading, audio focus)
|
|
65
|
+
- Automate **CI/CD** (GitHub Actions, Fastlane, signing, Play Store deployment)
|
|
66
|
+
- Guide **maps & location** (FusedLocationProvider, geofencing, permissions)
|
|
67
|
+
- Enable **on-device ML** (ML Kit, TFLite, Gemini Nano, model management)
|
|
58
68
|
- Scale from indie to enterprise
|
|
59
69
|
- Adapt automatically (Enterprise Mode auto-detection)
|
|
60
70
|
|
|
@@ -124,6 +134,56 @@ flowchart LR
|
|
|
124
134
|
C --- U
|
|
125
135
|
D --- U
|
|
126
136
|
E --- U
|
|
137
|
+
|
|
138
|
+
V[play-billing-best-practices]
|
|
139
|
+
C --- V
|
|
140
|
+
D --- V
|
|
141
|
+
E --- V
|
|
142
|
+
|
|
143
|
+
W[firebase-best-practices]
|
|
144
|
+
C --- W
|
|
145
|
+
D --- W
|
|
146
|
+
E --- W
|
|
147
|
+
|
|
148
|
+
X[android-dependency-injection]
|
|
149
|
+
C --- X
|
|
150
|
+
D --- X
|
|
151
|
+
E --- X
|
|
152
|
+
|
|
153
|
+
Y[android-networking]
|
|
154
|
+
C --- Y
|
|
155
|
+
D --- Y
|
|
156
|
+
E --- Y
|
|
157
|
+
|
|
158
|
+
Z[android-local-storage]
|
|
159
|
+
C --- Z
|
|
160
|
+
D --- Z
|
|
161
|
+
E --- Z
|
|
162
|
+
|
|
163
|
+
AA[android-auth-identity]
|
|
164
|
+
C --- AA
|
|
165
|
+
D --- AA
|
|
166
|
+
E --- AA
|
|
167
|
+
|
|
168
|
+
AB[android-media]
|
|
169
|
+
C --- AB
|
|
170
|
+
D --- AB
|
|
171
|
+
E --- AB
|
|
172
|
+
|
|
173
|
+
AC[android-ci-cd]
|
|
174
|
+
C --- AC
|
|
175
|
+
D --- AC
|
|
176
|
+
E --- AC
|
|
177
|
+
|
|
178
|
+
AD[android-maps-location]
|
|
179
|
+
C --- AD
|
|
180
|
+
D --- AD
|
|
181
|
+
E --- AD
|
|
182
|
+
|
|
183
|
+
AE[android-ml-ondevice]
|
|
184
|
+
C --- AE
|
|
185
|
+
D --- AE
|
|
186
|
+
E --- AE
|
|
127
187
|
```
|
|
128
188
|
|
|
129
189
|
---
|
|
@@ -304,6 +364,146 @@ Cross-cutting skill — type-safe routes, deep links, App Links, navigation patt
|
|
|
304
364
|
|
|
305
365
|
---
|
|
306
366
|
|
|
367
|
+
### 13. play-billing-best-practices
|
|
368
|
+
|
|
369
|
+
Cross-cutting skill — in-app purchases, subscriptions, server verification, testing.
|
|
370
|
+
|
|
371
|
+
**Enforces:**
|
|
372
|
+
- Server-side purchase verification — never trust client
|
|
373
|
+
- Acknowledge all purchases within 3 days
|
|
374
|
+
- Consume consumable purchases after delivery
|
|
375
|
+
- Handle all BillingResponseCode values
|
|
376
|
+
- Test with license testers on real devices
|
|
377
|
+
- Handle pending purchases for slow payment methods
|
|
378
|
+
|
|
379
|
+
---
|
|
380
|
+
|
|
381
|
+
### 14. firebase-best-practices
|
|
382
|
+
|
|
383
|
+
Cross-cutting skill — Auth, Firestore, Crashlytics, Remote Config, FCM, Analytics.
|
|
384
|
+
|
|
385
|
+
**Enforces:**
|
|
386
|
+
- Firebase BoM for consistent versions
|
|
387
|
+
- Firestore security rules before production
|
|
388
|
+
- No PII in Crashlytics logs
|
|
389
|
+
- Respect user consent before Analytics collection
|
|
390
|
+
- Handle FCM token rotation
|
|
391
|
+
- Rate-limit Remote Config fetches
|
|
392
|
+
|
|
393
|
+
---
|
|
394
|
+
|
|
395
|
+
### 15. android-dependency-injection
|
|
396
|
+
|
|
397
|
+
Cross-cutting skill — Hilt/Dagger setup, scoping, multi-module DI, testing.
|
|
398
|
+
|
|
399
|
+
**Enforces:**
|
|
400
|
+
- Hilt as default DI framework
|
|
401
|
+
- Correct scoping (@Singleton, @ViewModelScoped)
|
|
402
|
+
- Never inject Activity context into singletons
|
|
403
|
+
- Constructor injection over field injection
|
|
404
|
+
- @Binds for interface-to-implementation mapping
|
|
405
|
+
- Focused modules per feature boundary
|
|
406
|
+
|
|
407
|
+
---
|
|
408
|
+
|
|
409
|
+
### 16. android-networking
|
|
410
|
+
|
|
411
|
+
Cross-cutting skill — Retrofit, OkHttp, Ktor, caching, error handling, resilience.
|
|
412
|
+
|
|
413
|
+
**Enforces:**
|
|
414
|
+
- Suspend functions for all API calls
|
|
415
|
+
- Explicit error handling for all HTTP codes
|
|
416
|
+
- OkHttp interceptors for cross-cutting concerns
|
|
417
|
+
- No request/response body logging in production
|
|
418
|
+
- Token refresh in Authenticator
|
|
419
|
+
- kotlinx.serialization or Moshi (not Gson)
|
|
420
|
+
|
|
421
|
+
---
|
|
422
|
+
|
|
423
|
+
### 17. android-local-storage
|
|
424
|
+
|
|
425
|
+
Cross-cutting skill — Room, DataStore, offline-first architecture, caching, encryption.
|
|
426
|
+
|
|
427
|
+
**Enforces:**
|
|
428
|
+
- Room for relational data, DataStore for key-value
|
|
429
|
+
- Export Room schemas and test all migrations
|
|
430
|
+
- No database operations on main thread
|
|
431
|
+
- Database as single source of truth
|
|
432
|
+
- No sensitive data in unencrypted storage
|
|
433
|
+
- Transactions for multi-table writes
|
|
434
|
+
|
|
435
|
+
---
|
|
436
|
+
|
|
437
|
+
### 18. android-auth-identity
|
|
438
|
+
|
|
439
|
+
Cross-cutting skill — Credential Manager, biometrics, token management, session security.
|
|
440
|
+
|
|
441
|
+
**Enforces:**
|
|
442
|
+
- Credential Manager API for sign-in flows
|
|
443
|
+
- Tokens in EncryptedSharedPreferences or Keystore
|
|
444
|
+
- Transparent token refresh
|
|
445
|
+
- BiometricPrompt (not FingerprintManager)
|
|
446
|
+
- BIOMETRIC_STRONG for sensitive operations
|
|
447
|
+
- Clear all credentials on logout
|
|
448
|
+
|
|
449
|
+
---
|
|
450
|
+
|
|
451
|
+
### 19. android-media
|
|
452
|
+
|
|
453
|
+
Cross-cutting skill — Media3/ExoPlayer, CameraX, image loading, audio focus, PiP.
|
|
454
|
+
|
|
455
|
+
**Enforces:**
|
|
456
|
+
- Media3 for playback (not legacy ExoPlayer)
|
|
457
|
+
- CameraX for camera (not Camera2 directly)
|
|
458
|
+
- Coil or Glide for image loading
|
|
459
|
+
- Audio focus management before playback
|
|
460
|
+
- MediaSession for background playback
|
|
461
|
+
- Lifecycle-aware resource release
|
|
462
|
+
|
|
463
|
+
---
|
|
464
|
+
|
|
465
|
+
### 20. android-ci-cd
|
|
466
|
+
|
|
467
|
+
Cross-cutting skill — GitHub Actions, Fastlane, signing, Play Store deployment, build optimization.
|
|
468
|
+
|
|
469
|
+
**Enforces:**
|
|
470
|
+
- Never store signing keys in repository
|
|
471
|
+
- Unit tests on every PR
|
|
472
|
+
- Release AAB built in CI
|
|
473
|
+
- Pin CI action versions to SHA hashes
|
|
474
|
+
- Gradle build cache and configuration cache
|
|
475
|
+
- Separate CI stages (lint → test → build → deploy)
|
|
476
|
+
|
|
477
|
+
---
|
|
478
|
+
|
|
479
|
+
### 21. android-maps-location
|
|
480
|
+
|
|
481
|
+
Cross-cutting skill — Google Maps SDK, FusedLocationProvider, geofencing, permissions.
|
|
482
|
+
|
|
483
|
+
**Enforces:**
|
|
484
|
+
- FusedLocationProviderClient (not LocationManager)
|
|
485
|
+
- Request only needed location accuracy
|
|
486
|
+
- Remove location updates when not needed
|
|
487
|
+
- Protect API keys with app restrictions
|
|
488
|
+
- Foreground service for background location
|
|
489
|
+
- Handle approximate vs precise location (API 31+)
|
|
490
|
+
|
|
491
|
+
---
|
|
492
|
+
|
|
493
|
+
### 22. android-ml-ondevice
|
|
494
|
+
|
|
495
|
+
Cross-cutting skill — ML Kit, TensorFlow Lite, Gemini Nano, model management.
|
|
496
|
+
|
|
497
|
+
**Enforces:**
|
|
498
|
+
- ML Kit for common vision/NLP tasks
|
|
499
|
+
- Run inference off main thread
|
|
500
|
+
- Play Services-based models to reduce APK size
|
|
501
|
+
- Validate model input/output shapes
|
|
502
|
+
- Graceful fallback when models unavailable
|
|
503
|
+
- Quantize models for size and performance
|
|
504
|
+
|
|
505
|
+
---
|
|
506
|
+
|
|
307
507
|
## Enterprise Mode (Auto-Detection)
|
|
308
508
|
|
|
309
509
|
Enterprise Mode activates automatically if the repository contains:
|
|
@@ -429,6 +629,16 @@ CLAUDE.md # Claude Code
|
|
|
429
629
|
.cursor/rules/android-build-infra.mdc
|
|
430
630
|
.cursor/rules/android-background-work.mdc
|
|
431
631
|
.cursor/rules/android-navigation-best-practices.mdc
|
|
632
|
+
.cursor/rules/play-billing-best-practices.mdc
|
|
633
|
+
.cursor/rules/firebase-best-practices.mdc
|
|
634
|
+
.cursor/rules/android-dependency-injection.mdc
|
|
635
|
+
.cursor/rules/android-networking.mdc
|
|
636
|
+
.cursor/rules/android-local-storage.mdc
|
|
637
|
+
.cursor/rules/android-auth-identity.mdc
|
|
638
|
+
.cursor/rules/android-media.mdc
|
|
639
|
+
.cursor/rules/android-ci-cd.mdc
|
|
640
|
+
.cursor/rules/android-maps-location.mdc
|
|
641
|
+
.cursor/rules/android-ml-ondevice.mdc
|
|
432
642
|
.windsurfrules # Windsurf
|
|
433
643
|
.clinerules/compose-best-practices.md # Cline (per skill)
|
|
434
644
|
.clinerules/kmp-architecture-best-practices.md
|
|
@@ -442,6 +652,16 @@ CLAUDE.md # Claude Code
|
|
|
442
652
|
.clinerules/android-build-infra.md
|
|
443
653
|
.clinerules/android-background-work.md
|
|
444
654
|
.clinerules/android-navigation-best-practices.md
|
|
655
|
+
.clinerules/play-billing-best-practices.md
|
|
656
|
+
.clinerules/firebase-best-practices.md
|
|
657
|
+
.clinerules/android-dependency-injection.md
|
|
658
|
+
.clinerules/android-networking.md
|
|
659
|
+
.clinerules/android-local-storage.md
|
|
660
|
+
.clinerules/android-auth-identity.md
|
|
661
|
+
.clinerules/android-media.md
|
|
662
|
+
.clinerules/android-ci-cd.md
|
|
663
|
+
.clinerules/android-maps-location.md
|
|
664
|
+
.clinerules/android-ml-ondevice.md
|
|
445
665
|
.aiassistant/rules/compose-best-practices.md # JetBrains AI (per skill)
|
|
446
666
|
.aiassistant/rules/kmp-architecture-best-practices.md
|
|
447
667
|
.aiassistant/rules/compose-multiplatform-best-practices.md
|
|
@@ -454,6 +674,16 @@ CLAUDE.md # Claude Code
|
|
|
454
674
|
.aiassistant/rules/android-build-infra.md
|
|
455
675
|
.aiassistant/rules/android-background-work.md
|
|
456
676
|
.aiassistant/rules/android-navigation-best-practices.md
|
|
677
|
+
.aiassistant/rules/play-billing-best-practices.md
|
|
678
|
+
.aiassistant/rules/firebase-best-practices.md
|
|
679
|
+
.aiassistant/rules/android-dependency-injection.md
|
|
680
|
+
.aiassistant/rules/android-networking.md
|
|
681
|
+
.aiassistant/rules/android-local-storage.md
|
|
682
|
+
.aiassistant/rules/android-auth-identity.md
|
|
683
|
+
.aiassistant/rules/android-media.md
|
|
684
|
+
.aiassistant/rules/android-ci-cd.md
|
|
685
|
+
.aiassistant/rules/android-maps-location.md
|
|
686
|
+
.aiassistant/rules/android-ml-ondevice.md
|
|
457
687
|
.amazonq/rules/compose-best-practices.md # Amazon Q (per skill)
|
|
458
688
|
.amazonq/rules/kmp-architecture-best-practices.md
|
|
459
689
|
.amazonq/rules/compose-multiplatform-best-practices.md
|
|
@@ -466,6 +696,16 @@ CLAUDE.md # Claude Code
|
|
|
466
696
|
.amazonq/rules/android-build-infra.md
|
|
467
697
|
.amazonq/rules/android-background-work.md
|
|
468
698
|
.amazonq/rules/android-navigation-best-practices.md
|
|
699
|
+
.amazonq/rules/play-billing-best-practices.md
|
|
700
|
+
.amazonq/rules/firebase-best-practices.md
|
|
701
|
+
.amazonq/rules/android-dependency-injection.md
|
|
702
|
+
.amazonq/rules/android-networking.md
|
|
703
|
+
.amazonq/rules/android-local-storage.md
|
|
704
|
+
.amazonq/rules/android-auth-identity.md
|
|
705
|
+
.amazonq/rules/android-media.md
|
|
706
|
+
.amazonq/rules/android-ci-cd.md
|
|
707
|
+
.amazonq/rules/android-maps-location.md
|
|
708
|
+
.amazonq/rules/android-ml-ondevice.md
|
|
469
709
|
CONVENTIONS.md # Aider
|
|
470
710
|
.aider.conf.yml
|
|
471
711
|
```
|
|
@@ -547,6 +787,16 @@ android-accessibility-best-practices/
|
|
|
547
787
|
android-build-infra/
|
|
548
788
|
android-background-work/
|
|
549
789
|
android-navigation-best-practices/
|
|
790
|
+
play-billing-best-practices/
|
|
791
|
+
firebase-best-practices/
|
|
792
|
+
android-dependency-injection/
|
|
793
|
+
android-networking/
|
|
794
|
+
android-local-storage/
|
|
795
|
+
android-auth-identity/
|
|
796
|
+
android-media/
|
|
797
|
+
android-ci-cd/
|
|
798
|
+
android-maps-location/
|
|
799
|
+
android-ml-ondevice/
|
|
550
800
|
README.md
|
|
551
801
|
```
|
|
552
802
|
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
|
|
2
|
+
---
|
|
3
|
+
name: android-auth-identity
|
|
4
|
+
description: Authentication & identity — Credential Manager, biometrics, token management, session security.
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Android Authentication & Identity
|
|
8
|
+
|
|
9
|
+
Cross-cutting skill — always activates alongside the project-type-specific skill.
|
|
10
|
+
|
|
11
|
+
## Hard Rules
|
|
12
|
+
- Use Credential Manager API for sign-in flows — replaces legacy Smart Lock and FIDO2 APIs.
|
|
13
|
+
- Store tokens in EncryptedSharedPreferences or Android Keystore — never in plain SharedPreferences.
|
|
14
|
+
- Implement token refresh transparently — user should not see expired-token errors.
|
|
15
|
+
- Use BiometricPrompt from androidx.biometric — not deprecated FingerprintManager.
|
|
16
|
+
- Require BIOMETRIC_STRONG for sensitive operations (payments, account changes).
|
|
17
|
+
- Never store raw passwords on device — use credential management APIs.
|
|
18
|
+
- Validate all tokens server-side — client-side validation alone is insufficient.
|
|
19
|
+
- Handle account linking carefully — merge conflicts can lose user data.
|
|
20
|
+
- Clear all credentials on logout — tokens, cookies, cached user data.
|
|
21
|
+
- Support passkeys (WebAuthn) as the primary passwordless credential.
|
|
22
|
+
|
|
23
|
+
## Core Patterns
|
|
24
|
+
- Single AuthRepository abstraction over Credential Manager + token storage.
|
|
25
|
+
- Refresh tokens in OkHttp Authenticator — seamless for all API calls.
|
|
26
|
+
- Biometric-bound keys for sensitive operations (CryptoObject in BiometricPrompt).
|
|
27
|
+
- Use ID tokens (JWT) for user identity, access tokens for API authorization.
|
|
28
|
+
- Implement session timeout — re-authenticate after inactivity period.
|
|
29
|
+
- Wrap auth state in StateFlow for reactive UI updates.
|
|
30
|
+
|
|
31
|
+
## References
|
|
32
|
+
- references/credential_manager.md
|
|
33
|
+
- references/biometric_auth.md
|
|
34
|
+
- references/token_management.md
|
|
35
|
+
- references/google_sign_in.md
|
|
36
|
+
- references/session_security.md
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
# Biometric Authentication
|
|
2
|
+
|
|
3
|
+
## BiometricPrompt
|
|
4
|
+
- Use androidx.biometric.BiometricPrompt — not deprecated FingerprintManager.
|
|
5
|
+
- Create with BiometricPrompt(activity/fragment, executor, callback).
|
|
6
|
+
- Configure with BiometricPrompt.PromptInfo.Builder().
|
|
7
|
+
- setTitle(), setSubtitle(), setDescription() for user-facing text.
|
|
8
|
+
- setNegativeButtonText() for cancel action (required unless using device credential).
|
|
9
|
+
|
|
10
|
+
## Authenticator Types
|
|
11
|
+
- BIOMETRIC_STRONG: fingerprint, face (Class 3) — required for crypto operations.
|
|
12
|
+
- BIOMETRIC_WEAK: less secure biometrics (Class 2) — no crypto support.
|
|
13
|
+
- DEVICE_CREDENTIAL: PIN, pattern, password fallback.
|
|
14
|
+
- setAllowedAuthenticators(BIOMETRIC_STRONG or DEVICE_CREDENTIAL) for flexible auth.
|
|
15
|
+
- Check availability: BiometricManager.canAuthenticate(authenticators).
|
|
16
|
+
|
|
17
|
+
## Crypto Integration
|
|
18
|
+
- CryptoObject: wraps Cipher, Signature, or Mac bound to biometric auth.
|
|
19
|
+
- Key generated with setUserAuthenticationRequired(true) in KeyGenParameterSpec.
|
|
20
|
+
- After successful auth, use CryptoObject to perform crypto operation.
|
|
21
|
+
- Use for: decrypting tokens, signing transactions, accessing secure data.
|
|
22
|
+
- Key invalidated if biometric enrollment changes (setInvalidatedByBiometricEnrollment).
|
|
23
|
+
|
|
24
|
+
## Authentication Flow
|
|
25
|
+
1. Check BiometricManager.canAuthenticate() — handle BIOMETRIC_ERROR_*.
|
|
26
|
+
2. Build PromptInfo with title and allowed authenticators.
|
|
27
|
+
3. Create CryptoObject if needed (for sensitive operations).
|
|
28
|
+
4. Call authenticate(promptInfo) or authenticate(promptInfo, cryptoObject).
|
|
29
|
+
5. Handle callback: onAuthenticationSucceeded, onAuthenticationError, onAuthenticationFailed.
|
|
30
|
+
|
|
31
|
+
## Best Practices
|
|
32
|
+
- Use BIOMETRIC_STRONG for payments and sensitive data access.
|
|
33
|
+
- Allow DEVICE_CREDENTIAL as fallback for convenience features.
|
|
34
|
+
- Never use biometrics as the sole authentication — combine with server-side auth.
|
|
35
|
+
- Handle all error codes: ERROR_LOCKOUT (too many attempts), ERROR_NO_BIOMETRICS, etc.
|
|
36
|
+
- Test on devices with and without biometric hardware.
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# Credential Manager
|
|
2
|
+
|
|
3
|
+
## Overview
|
|
4
|
+
- Credential Manager is the unified API for sign-in (replaces Smart Lock, FIDO2 APIs).
|
|
5
|
+
- Supports: passkeys (WebAuthn), passwords, federated sign-in (Google, etc.).
|
|
6
|
+
- Single API: getCredential() presents all available credentials.
|
|
7
|
+
- Available on API 28+ via Google Play Services, API 34+ natively.
|
|
8
|
+
|
|
9
|
+
## Passkeys (WebAuthn)
|
|
10
|
+
- Passkeys are FIDO2 credentials — phishing-resistant, no password needed.
|
|
11
|
+
- Create: createCredential(CreatePublicKeyCredentialRequest(requestJson)).
|
|
12
|
+
- Authenticate: getCredential(GetCredentialRequest(listOf(GetPublicKeyCredentialOption(requestJson)))).
|
|
13
|
+
- requestJson comes from your server (WebAuthn challenge).
|
|
14
|
+
- Passkeys sync across devices via Google Password Manager.
|
|
15
|
+
|
|
16
|
+
## Password Credentials
|
|
17
|
+
- GetPasswordOption() in GetCredentialRequest to offer saved passwords.
|
|
18
|
+
- CreatePasswordRequest(id, password) to save new passwords.
|
|
19
|
+
- Credential Manager auto-fills saved passwords.
|
|
20
|
+
- Encourage passkey adoption — offer passkey creation after password sign-in.
|
|
21
|
+
|
|
22
|
+
## Federated Sign-In
|
|
23
|
+
- Google Sign-In: GetGoogleIdOption with serverClientId.
|
|
24
|
+
- Returns GoogleIdTokenCredential — send ID token to your server.
|
|
25
|
+
- Configure in Google Cloud Console: OAuth 2.0 client ID.
|
|
26
|
+
- Filter by authorized accounts or allow any Google account.
|
|
27
|
+
|
|
28
|
+
## Implementation Pattern
|
|
29
|
+
- Call getCredential() on sign-in screen — shows bottom sheet with all options.
|
|
30
|
+
- Handle GetCredentialResponse — check credential type and extract data.
|
|
31
|
+
- Handle exceptions: NoCredentialException (no saved credentials), GetCredentialCancellationException (user dismissed).
|
|
32
|
+
- Call clearCredentialState() on logout — clears Credential Manager state.
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
# Google Sign-In
|
|
2
|
+
|
|
3
|
+
## Credential Manager Approach (Modern)
|
|
4
|
+
- Use GetGoogleIdOption in Credential Manager — replaces legacy GoogleSignInClient.
|
|
5
|
+
- Set serverClientId to your OAuth 2.0 Web client ID (from Google Cloud Console).
|
|
6
|
+
- Set filterByAuthorizedAccounts(true) for returning users, false for new sign-up.
|
|
7
|
+
- Returns GoogleIdTokenCredential with ID token and basic profile info.
|
|
8
|
+
|
|
9
|
+
## OAuth Configuration
|
|
10
|
+
- Create OAuth 2.0 client IDs in Google Cloud Console.
|
|
11
|
+
- Web client ID: used as serverClientId in Android app.
|
|
12
|
+
- Android client ID: configured with package name + SHA-1 fingerprint.
|
|
13
|
+
- Add both debug and release SHA-1 fingerprints.
|
|
14
|
+
- Update fingerprints when signing keys rotate.
|
|
15
|
+
|
|
16
|
+
## Sign-In Flow
|
|
17
|
+
1. Create GetGoogleIdOption with serverClientId.
|
|
18
|
+
2. Build GetCredentialRequest with the option.
|
|
19
|
+
3. Call credentialManager.getCredential(context, request).
|
|
20
|
+
4. Extract GoogleIdTokenCredential from response.
|
|
21
|
+
5. Send ID token to your server for verification.
|
|
22
|
+
6. Server verifies token and creates/updates user account.
|
|
23
|
+
|
|
24
|
+
## Server Verification
|
|
25
|
+
- Verify ID token using Google's tokeninfo endpoint or client library.
|
|
26
|
+
- Check: aud matches your client ID, iss is accounts.google.com, exp is not past.
|
|
27
|
+
- Extract: sub (unique Google user ID), email, name, picture.
|
|
28
|
+
- Use sub as the stable identifier — email can change.
|
|
29
|
+
|
|
30
|
+
## One Tap Sign-In
|
|
31
|
+
- Credential Manager shows One Tap UI automatically.
|
|
32
|
+
- Returns user selection without full-screen flow.
|
|
33
|
+
- Falls back to full sign-in if One Tap is dismissed.
|
|
34
|
+
- Rate-limited: Google may suppress One Tap if dismissed repeatedly.
|
|
35
|
+
|
|
36
|
+
## Sign-Out
|
|
37
|
+
- Call credentialManager.clearCredentialState(ClearCredentialStateRequest()).
|
|
38
|
+
- Also sign out from your backend (revoke tokens).
|
|
39
|
+
- Clear local user data and cached credentials.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Session Security
|
|
2
|
+
|
|
3
|
+
## Session Management
|
|
4
|
+
- Define session lifetime based on app sensitivity (banking: 15 min, social: 30 days).
|
|
5
|
+
- Track last-active timestamp — expire session after inactivity period.
|
|
6
|
+
- Store session state in EncryptedSharedPreferences.
|
|
7
|
+
- Clear session on logout: tokens, cached data, navigation state.
|
|
8
|
+
|
|
9
|
+
## Re-Authentication
|
|
10
|
+
- Require re-auth for sensitive operations: password change, payment, account deletion.
|
|
11
|
+
- Use BiometricPrompt for seamless re-auth (if biometrics enrolled).
|
|
12
|
+
- Fall back to full credential entry if biometrics fail.
|
|
13
|
+
- Server should enforce re-auth — don't rely solely on client-side checks.
|
|
14
|
+
|
|
15
|
+
## Device Binding
|
|
16
|
+
- Use Android Keystore to generate device-bound keys.
|
|
17
|
+
- Include device attestation in auth flow for high-security apps.
|
|
18
|
+
- Detect device change: invalidate sessions when device fingerprint changes.
|
|
19
|
+
- Use Play Integrity API for device integrity verification.
|
|
20
|
+
|
|
21
|
+
## Secure Logout
|
|
22
|
+
- Clear all tokens (access, refresh, ID) from secure storage.
|
|
23
|
+
- Clear Credential Manager state: clearCredentialState().
|
|
24
|
+
- Revoke tokens server-side — prevent reuse.
|
|
25
|
+
- Clear WebView cookies if using web-based auth.
|
|
26
|
+
- Navigate to login screen and clear back stack.
|
|
27
|
+
|
|
28
|
+
## Attack Mitigation
|
|
29
|
+
- Token fixation: always issue new tokens on successful auth.
|
|
30
|
+
- Session hijacking: bind sessions to device/IP when feasible.
|
|
31
|
+
- Brute force: implement account lockout after N failed attempts (server-side).
|
|
32
|
+
- Replay attacks: use nonces in authentication challenges.
|
|
33
|
+
- Man-in-the-middle: enforce certificate pinning for auth endpoints.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Token Management
|
|
2
|
+
|
|
3
|
+
## Token Types
|
|
4
|
+
- Access token: short-lived (15-60 minutes), authorizes API requests.
|
|
5
|
+
- Refresh token: long-lived (days-months), used to obtain new access tokens.
|
|
6
|
+
- ID token (JWT): contains user identity claims, used for user info.
|
|
7
|
+
- Never use refresh tokens for API authorization — only for token renewal.
|
|
8
|
+
|
|
9
|
+
## Storage
|
|
10
|
+
- Store tokens in EncryptedSharedPreferences — not plain SharedPreferences.
|
|
11
|
+
- Never store tokens in: Room database, DataStore, files, or logs.
|
|
12
|
+
- Clear all tokens on logout.
|
|
13
|
+
- Handle storage errors gracefully — force re-authentication if token storage fails.
|
|
14
|
+
|
|
15
|
+
## Refresh Flow
|
|
16
|
+
- Implement in OkHttp Authenticator for transparent refresh.
|
|
17
|
+
- On 401: use refresh token to get new access token → retry original request.
|
|
18
|
+
- Synchronize refresh: multiple concurrent 401s should trigger only one refresh.
|
|
19
|
+
- If refresh fails (refresh token expired): clear tokens, navigate to login.
|
|
20
|
+
- Use mutex or synchronized block to prevent concurrent refresh requests.
|
|
21
|
+
|
|
22
|
+
## JWT Validation
|
|
23
|
+
- Validate ID tokens on your server — not just on the client.
|
|
24
|
+
- Check: issuer (iss), audience (aud), expiration (exp), signature.
|
|
25
|
+
- Client-side: only check expiration for UX purposes (show login screen).
|
|
26
|
+
- Never trust client-side JWT validation as the sole security measure.
|
|
27
|
+
|
|
28
|
+
## Security
|
|
29
|
+
- Rotate refresh tokens on each use (refresh token rotation).
|
|
30
|
+
- Detect token theft: if a used refresh token is reused, revoke all tokens.
|
|
31
|
+
- Set reasonable token lifetimes: access (15 min), refresh (7-30 days).
|
|
32
|
+
- Bind tokens to device if possible (device attestation).
|
|
33
|
+
- Handle token revocation from server (user changed password, admin action).
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
|
|
2
|
+
---
|
|
3
|
+
name: android-ci-cd
|
|
4
|
+
description: Android CI/CD — GitHub Actions, Fastlane, signing, Play Store deployment, build optimization.
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Android CI/CD
|
|
8
|
+
|
|
9
|
+
Cross-cutting skill — always activates alongside the project-type-specific skill.
|
|
10
|
+
|
|
11
|
+
## Hard Rules
|
|
12
|
+
- Never store signing keys or passwords in the repository — use CI secrets.
|
|
13
|
+
- Run unit tests on every pull request — block merge on failure.
|
|
14
|
+
- Build release AAB in CI — not on developer machines.
|
|
15
|
+
- Upload mapping.txt and native symbols with every release build.
|
|
16
|
+
- Use Gradle build cache and configuration cache in CI.
|
|
17
|
+
- Pin all CI action versions to SHA hashes — not tags (supply chain security).
|
|
18
|
+
- Separate CI stages: lint → unit test → build → instrumented test → deploy.
|
|
19
|
+
- Never skip CI checks for hotfixes — no --no-verify equivalent.
|
|
20
|
+
- Cache Gradle dependencies and build outputs between runs.
|
|
21
|
+
- Use Gradle Managed Devices or Firebase Test Lab for instrumented tests in CI.
|
|
22
|
+
|
|
23
|
+
## Core Patterns
|
|
24
|
+
- GitHub Actions with matrix strategy for testing on multiple API levels.
|
|
25
|
+
- Fastlane for automated screenshots, metadata management, and deployment.
|
|
26
|
+
- Decode signing keystore from base64 CI secret at build time.
|
|
27
|
+
- Use semantic-release or Gradle Play Publisher for automated releases.
|
|
28
|
+
- Run lint checks (detekt, ktlint, Android Lint) as CI gates.
|
|
29
|
+
- Separate pipelines: PR validation (fast) vs release (thorough).
|
|
30
|
+
|
|
31
|
+
## References
|
|
32
|
+
- references/github_actions.md
|
|
33
|
+
- references/fastlane.md
|
|
34
|
+
- references/signing_ci.md
|
|
35
|
+
- references/play_store_deployment.md
|
|
36
|
+
- references/build_optimization.md
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
# Build Optimization for CI
|
|
2
|
+
|
|
3
|
+
## Gradle Caching
|
|
4
|
+
- Enable build cache: org.gradle.caching=true in gradle.properties.
|
|
5
|
+
- Enable configuration cache: org.gradle.configuration-cache=true.
|
|
6
|
+
- Cache Gradle wrapper, dependencies, and build outputs in CI.
|
|
7
|
+
- GitHub Actions: use gradle/actions/setup-gradle for automatic caching.
|
|
8
|
+
- Cache key should include: gradle-wrapper.properties, libs.versions.toml, build files.
|
|
9
|
+
|
|
10
|
+
## Parallel Execution
|
|
11
|
+
- Enable parallel builds: org.gradle.parallel=true.
|
|
12
|
+
- Set workers: org.gradle.workers.max=4 (match CI runner cores).
|
|
13
|
+
- Modularized projects benefit most — independent modules build concurrently.
|
|
14
|
+
- CI runners typically have 2-4 cores — adjust workers accordingly.
|
|
15
|
+
|
|
16
|
+
## Daemon & Memory
|
|
17
|
+
- Disable Gradle daemon in CI: org.gradle.daemon=false (CI runners are ephemeral).
|
|
18
|
+
- Or keep daemon with warm-start for multi-step workflows.
|
|
19
|
+
- Set JVM heap: org.gradle.jvmargs=-Xmx4g -XX:+UseParallelGC.
|
|
20
|
+
- Match to CI runner memory — OOM kills are silent and confusing.
|
|
21
|
+
- Use metaspace limit: -XX:MaxMetaspaceSize=512m.
|
|
22
|
+
|
|
23
|
+
## Incremental Builds
|
|
24
|
+
- Avoid clean builds in CI — leverage incremental compilation.
|
|
25
|
+
- Only clean when: Gradle version changes, build scripts change significantly.
|
|
26
|
+
- KSP/KAPT: incremental processing reduces annotation processing time.
|
|
27
|
+
- Use --no-rebuild to skip up-to-date tasks.
|
|
28
|
+
|
|
29
|
+
## Build Scans
|
|
30
|
+
- Enable Gradle build scans for CI debugging: --scan flag.
|
|
31
|
+
- Build scans show: task execution times, dependency resolution, cache hit rates.
|
|
32
|
+
- Identify slow tasks and optimize them.
|
|
33
|
+
- Use Develocity (Gradle Enterprise) for team-wide build analytics.
|
|
34
|
+
|
|
35
|
+
## CI-Specific Tips
|
|
36
|
+
- Use --stacktrace for debugging but --quiet for production CI (less log noise).
|
|
37
|
+
- Upload build reports (lint, test, scan) as CI artifacts.
|
|
38
|
+
- Set timeout on build steps — prevent hung builds from consuming runner time.
|
|
39
|
+
- Use self-hosted runners for faster builds with persistent caches.
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
# Fastlane for Android
|
|
2
|
+
|
|
3
|
+
## Setup
|
|
4
|
+
- Install: gem install fastlane or add to Gemfile.
|
|
5
|
+
- Initialize: fastlane init in project root.
|
|
6
|
+
- Configure in fastlane/Fastfile with lanes.
|
|
7
|
+
- Use .env files for environment-specific config (never commit secrets).
|
|
8
|
+
|
|
9
|
+
## Common Lanes
|
|
10
|
+
- lane :test — run unit tests: gradle(task: "testDebugUnitTest").
|
|
11
|
+
- lane :build — build release: gradle(task: "bundleRelease").
|
|
12
|
+
- lane :deploy — upload to Play Store: upload_to_play_store.
|
|
13
|
+
- lane :screenshots — automated screenshots: capture_android_screenshots.
|
|
14
|
+
- Chain lanes: before_all, after_all, error blocks.
|
|
15
|
+
|
|
16
|
+
## Play Store Upload
|
|
17
|
+
- upload_to_play_store: uploads AAB to specified track.
|
|
18
|
+
- Tracks: internal, alpha, beta, production.
|
|
19
|
+
- Set rollout_percentage for staged rollout: rollout_percentage: "10".
|
|
20
|
+
- Include mapping.txt: mapping_paths: ["app/build/outputs/mapping/release/mapping.txt"].
|
|
21
|
+
- Manage metadata: supply action for descriptions, screenshots, changelogs.
|
|
22
|
+
|
|
23
|
+
## Screenshots
|
|
24
|
+
- Use screengrab for automated screenshot capture.
|
|
25
|
+
- Configure devices and locales in Screengrabfile.
|
|
26
|
+
- Requires instrumented test that navigates through screens.
|
|
27
|
+
- Upload screenshots to Play Store with supply.
|
|
28
|
+
|
|
29
|
+
## Best Practices
|
|
30
|
+
- Version lock fastlane in Gemfile — avoid CI surprises.
|
|
31
|
+
- Use fastlane match or manual key management for signing.
|
|
32
|
+
- Store Play Store JSON key in CI secrets — not in repo.
|
|
33
|
+
- Use --verbose flag for debugging CI failures.
|
|
34
|
+
- Run fastlane locally before pushing to CI.
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# GitHub Actions for Android
|
|
2
|
+
|
|
3
|
+
## Basic Workflow
|
|
4
|
+
- Trigger on: push to main, pull_request.
|
|
5
|
+
- Runner: ubuntu-latest (Linux — fastest for Android builds).
|
|
6
|
+
- Set up JDK: actions/setup-java with distribution: 'temurin' and java-version: '17'.
|
|
7
|
+
- Cache Gradle: actions/cache with ~/.gradle/caches and ~/.gradle/wrapper.
|
|
8
|
+
- Or use gradle/actions/setup-gradle for automatic caching.
|
|
9
|
+
|
|
10
|
+
## Build Steps
|
|
11
|
+
- Make gradlew executable: chmod +x gradlew.
|
|
12
|
+
- Lint: ./gradlew lint detekt ktlintCheck.
|
|
13
|
+
- Unit tests: ./gradlew testDebugUnitTest.
|
|
14
|
+
- Build: ./gradlew assembleRelease or bundleRelease.
|
|
15
|
+
- Upload artifacts: actions/upload-artifact for APK/AAB.
|
|
16
|
+
|
|
17
|
+
## Matrix Testing
|
|
18
|
+
- Use strategy.matrix for multiple API levels or configurations.
|
|
19
|
+
- Matrix dimensions: api-level [29, 33, 34], target [default, google_apis].
|
|
20
|
+
- Use reactivecircus/android-emulator-runner for instrumented tests.
|
|
21
|
+
- Cache AVD snapshots: force-avd-creation: false + avd-cache key.
|
|
22
|
+
|
|
23
|
+
## Instrumented Tests
|
|
24
|
+
- Use reactivecircus/android-emulator-runner action.
|
|
25
|
+
- Or use Firebase Test Lab via gcloud CLI.
|
|
26
|
+
- Set emulator-options: -no-snapshot-save -no-window -gpu swiftshader_indirect.
|
|
27
|
+
- Run with script: ./gradlew connectedCheck.
|
|
28
|
+
- Upload test reports as artifacts on failure.
|
|
29
|
+
|
|
30
|
+
## Security
|
|
31
|
+
- Pin action versions to SHA hashes: actions/checkout@<sha> (not @v4).
|
|
32
|
+
- Store secrets in GitHub Settings > Secrets: KEYSTORE_BASE64, KEY_PASSWORD, etc.
|
|
33
|
+
- Never echo secrets in workflow logs.
|
|
34
|
+
- Use OIDC for trusted publishing (npm, PyPI) — no long-lived tokens.
|
|
35
|
+
- Review third-party actions before adoption.
|