agy-superpowers 5.0.8 → 5.0.9

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 (204) hide show
  1. package/package.json +1 -1
  2. package/template/agent/rules/superpowers.md +54 -0
  3. package/template/agent/skills/frontend-developer/SKILL.md +39 -0
  4. package/template/agent/skills/frontend-developer/references/react-nextjs.md +343 -0
  5. package/template/agent/skills/frontend-developer/references/react-rules/_sections.md +46 -0
  6. package/template/agent/skills/frontend-developer/references/react-rules/_template.md +28 -0
  7. package/template/agent/skills/frontend-developer/references/react-rules/advanced-event-handler-refs.md +55 -0
  8. package/template/agent/skills/frontend-developer/references/react-rules/advanced-init-once.md +42 -0
  9. package/template/agent/skills/frontend-developer/references/react-rules/advanced-use-latest.md +39 -0
  10. package/template/agent/skills/frontend-developer/references/react-rules/async-api-routes.md +38 -0
  11. package/template/agent/skills/frontend-developer/references/react-rules/async-defer-await.md +80 -0
  12. package/template/agent/skills/frontend-developer/references/react-rules/async-dependencies.md +51 -0
  13. package/template/agent/skills/frontend-developer/references/react-rules/async-parallel.md +28 -0
  14. package/template/agent/skills/frontend-developer/references/react-rules/async-suspense-boundaries.md +99 -0
  15. package/template/agent/skills/frontend-developer/references/react-rules/bundle-barrel-imports.md +59 -0
  16. package/template/agent/skills/frontend-developer/references/react-rules/bundle-conditional.md +31 -0
  17. package/template/agent/skills/frontend-developer/references/react-rules/bundle-defer-third-party.md +49 -0
  18. package/template/agent/skills/frontend-developer/references/react-rules/bundle-dynamic-imports.md +35 -0
  19. package/template/agent/skills/frontend-developer/references/react-rules/bundle-preload.md +50 -0
  20. package/template/agent/skills/frontend-developer/references/react-rules/client-event-listeners.md +74 -0
  21. package/template/agent/skills/frontend-developer/references/react-rules/client-localstorage-schema.md +71 -0
  22. package/template/agent/skills/frontend-developer/references/react-rules/client-passive-event-listeners.md +48 -0
  23. package/template/agent/skills/frontend-developer/references/react-rules/client-swr-dedup.md +56 -0
  24. package/template/agent/skills/frontend-developer/references/react-rules/js-batch-dom-css.md +107 -0
  25. package/template/agent/skills/frontend-developer/references/react-rules/js-cache-function-results.md +80 -0
  26. package/template/agent/skills/frontend-developer/references/react-rules/js-cache-property-access.md +28 -0
  27. package/template/agent/skills/frontend-developer/references/react-rules/js-cache-storage.md +70 -0
  28. package/template/agent/skills/frontend-developer/references/react-rules/js-combine-iterations.md +32 -0
  29. package/template/agent/skills/frontend-developer/references/react-rules/js-early-exit.md +50 -0
  30. package/template/agent/skills/frontend-developer/references/react-rules/js-flatmap-filter.md +60 -0
  31. package/template/agent/skills/frontend-developer/references/react-rules/js-hoist-regexp.md +45 -0
  32. package/template/agent/skills/frontend-developer/references/react-rules/js-index-maps.md +37 -0
  33. package/template/agent/skills/frontend-developer/references/react-rules/js-length-check-first.md +49 -0
  34. package/template/agent/skills/frontend-developer/references/react-rules/js-min-max-loop.md +82 -0
  35. package/template/agent/skills/frontend-developer/references/react-rules/js-set-map-lookups.md +24 -0
  36. package/template/agent/skills/frontend-developer/references/react-rules/js-tosorted-immutable.md +57 -0
  37. package/template/agent/skills/frontend-developer/references/react-rules/rendering-activity.md +26 -0
  38. package/template/agent/skills/frontend-developer/references/react-rules/rendering-animate-svg-wrapper.md +47 -0
  39. package/template/agent/skills/frontend-developer/references/react-rules/rendering-conditional-render.md +40 -0
  40. package/template/agent/skills/frontend-developer/references/react-rules/rendering-content-visibility.md +38 -0
  41. package/template/agent/skills/frontend-developer/references/react-rules/rendering-hoist-jsx.md +46 -0
  42. package/template/agent/skills/frontend-developer/references/react-rules/rendering-hydration-no-flicker.md +82 -0
  43. package/template/agent/skills/frontend-developer/references/react-rules/rendering-hydration-suppress-warning.md +30 -0
  44. package/template/agent/skills/frontend-developer/references/react-rules/rendering-resource-hints.md +85 -0
  45. package/template/agent/skills/frontend-developer/references/react-rules/rendering-script-defer-async.md +68 -0
  46. package/template/agent/skills/frontend-developer/references/react-rules/rendering-svg-precision.md +28 -0
  47. package/template/agent/skills/frontend-developer/references/react-rules/rendering-usetransition-loading.md +75 -0
  48. package/template/agent/skills/frontend-developer/references/react-rules/rerender-defer-reads.md +39 -0
  49. package/template/agent/skills/frontend-developer/references/react-rules/rerender-dependencies.md +45 -0
  50. package/template/agent/skills/frontend-developer/references/react-rules/rerender-derived-state-no-effect.md +40 -0
  51. package/template/agent/skills/frontend-developer/references/react-rules/rerender-derived-state.md +29 -0
  52. package/template/agent/skills/frontend-developer/references/react-rules/rerender-functional-setstate.md +74 -0
  53. package/template/agent/skills/frontend-developer/references/react-rules/rerender-lazy-state-init.md +58 -0
  54. package/template/agent/skills/frontend-developer/references/react-rules/rerender-memo-with-default-value.md +38 -0
  55. package/template/agent/skills/frontend-developer/references/react-rules/rerender-memo.md +44 -0
  56. package/template/agent/skills/frontend-developer/references/react-rules/rerender-move-effect-to-event.md +45 -0
  57. package/template/agent/skills/frontend-developer/references/react-rules/rerender-no-inline-components.md +82 -0
  58. package/template/agent/skills/frontend-developer/references/react-rules/rerender-simple-expression-in-memo.md +35 -0
  59. package/template/agent/skills/frontend-developer/references/react-rules/rerender-split-combined-hooks.md +64 -0
  60. package/template/agent/skills/frontend-developer/references/react-rules/rerender-transitions.md +40 -0
  61. package/template/agent/skills/frontend-developer/references/react-rules/rerender-use-deferred-value.md +59 -0
  62. package/template/agent/skills/frontend-developer/references/react-rules/rerender-use-ref-transient-values.md +73 -0
  63. package/template/agent/skills/frontend-developer/references/react-rules/server-after-nonblocking.md +73 -0
  64. package/template/agent/skills/frontend-developer/references/react-rules/server-auth-actions.md +96 -0
  65. package/template/agent/skills/frontend-developer/references/react-rules/server-cache-lru.md +41 -0
  66. package/template/agent/skills/frontend-developer/references/react-rules/server-cache-react.md +76 -0
  67. package/template/agent/skills/frontend-developer/references/react-rules/server-dedup-props.md +65 -0
  68. package/template/agent/skills/frontend-developer/references/react-rules/server-hoist-static-io.md +142 -0
  69. package/template/agent/skills/frontend-developer/references/react-rules/server-parallel-fetching.md +83 -0
  70. package/template/agent/skills/frontend-developer/references/react-rules/server-serialization.md +38 -0
  71. package/template/agent/skills/frontend-developer/references/svelte-sveltekit.md +220 -0
  72. package/template/agent/skills/frontend-developer/references/vanilla.md +275 -0
  73. package/template/agent/skills/frontend-developer/references/vue-nuxt.md +289 -0
  74. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/_index.md +154 -0
  75. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/animation-class-based-technique.md +254 -0
  76. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/animation-state-driven-technique.md +291 -0
  77. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-async.md +97 -0
  78. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-data-flow.md +307 -0
  79. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-fallthrough-attrs.md +174 -0
  80. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-keep-alive.md +137 -0
  81. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-slots.md +216 -0
  82. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-suspense.md +228 -0
  83. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-teleport.md +108 -0
  84. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-transition-group.md +128 -0
  85. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/component-transition.md +125 -0
  86. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/composables.md +290 -0
  87. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/directives.md +162 -0
  88. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/perf-avoid-component-abstraction-in-lists.md +159 -0
  89. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/perf-v-once-v-memo-directives.md +182 -0
  90. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/perf-virtualize-large-lists.md +187 -0
  91. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/plugins.md +166 -0
  92. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/reactivity.md +344 -0
  93. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/render-functions.md +201 -0
  94. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/sfc.md +310 -0
  95. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/state-management.md +135 -0
  96. package/template/agent/skills/frontend-developer/references/vue-rules/best-practices/updated-hook-performance.md +187 -0
  97. package/template/agent/skills/frontend-developer/references/vue-rules/router/_index.md +23 -0
  98. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-beforeenter-no-param-trigger.md +167 -0
  99. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-beforerouteenter-no-this.md +176 -0
  100. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-guard-async-await-pattern.md +227 -0
  101. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-navigation-guard-infinite-loop.md +187 -0
  102. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-navigation-guard-next-deprecated.md +150 -0
  103. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-param-change-no-lifecycle.md +181 -0
  104. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-simple-routing-cleanup.md +209 -0
  105. package/template/agent/skills/frontend-developer/references/vue-rules/router/router-use-vue-router-for-production.md +183 -0
  106. package/template/agent/skills/frontend-developer/references/vue-rules/testing/_index.md +29 -0
  107. package/template/agent/skills/frontend-developer/references/vue-rules/testing/async-component-testing.md +163 -0
  108. package/template/agent/skills/frontend-developer/references/vue-rules/testing/teleport-testing-complexity.md +158 -0
  109. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-async-await-flushpromises.md +175 -0
  110. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-browser-vs-node-runners.md +208 -0
  111. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-component-blackbox-approach.md +144 -0
  112. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-composables-helper-wrapper.md +238 -0
  113. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-e2e-playwright-recommended.md +242 -0
  114. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-no-snapshot-only.md +197 -0
  115. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-pinia-store-setup.md +228 -0
  116. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-suspense-async-components.md +229 -0
  117. package/template/agent/skills/frontend-developer/references/vue-rules/testing/testing-vitest-recommended-for-vue.md +204 -0
  118. package/template/agent/skills/mobile-developer/SKILL.md +52 -0
  119. package/template/agent/skills/mobile-developer/references/android-native.md +396 -0
  120. package/template/agent/skills/mobile-developer/references/android-rules/android-accessibility.md +36 -0
  121. package/template/agent/skills/mobile-developer/references/android-rules/android-architecture.md +52 -0
  122. package/template/agent/skills/mobile-developer/references/android-rules/android-coroutines.md +139 -0
  123. package/template/agent/skills/mobile-developer/references/android-rules/android-data-layer.md +51 -0
  124. package/template/agent/skills/mobile-developer/references/android-rules/android-emulator-skill.md +108 -0
  125. package/template/agent/skills/mobile-developer/references/android-rules/android-gradle-logic.md +126 -0
  126. package/template/agent/skills/mobile-developer/references/android-rules/android-retrofit.md +142 -0
  127. package/template/agent/skills/mobile-developer/references/android-rules/android-testing.md +102 -0
  128. package/template/agent/skills/mobile-developer/references/android-rules/android-viewmodel.md +43 -0
  129. package/template/agent/skills/mobile-developer/references/android-rules/coil-compose.md +74 -0
  130. package/template/agent/skills/mobile-developer/references/android-rules/compose-navigation.md +422 -0
  131. package/template/agent/skills/mobile-developer/references/android-rules/compose-performance-audit.md +199 -0
  132. package/template/agent/skills/mobile-developer/references/android-rules/compose-ui.md +49 -0
  133. package/template/agent/skills/mobile-developer/references/android-rules/gradle-build-performance.md +346 -0
  134. package/template/agent/skills/mobile-developer/references/android-rules/kotlin-concurrency-expert.md +169 -0
  135. package/template/agent/skills/mobile-developer/references/android-rules/rxjava-to-coroutines-migration.md +101 -0
  136. package/template/agent/skills/mobile-developer/references/android-rules/xml-to-compose-migration.md +338 -0
  137. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-best-practices.md +52 -0
  138. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-checks-migration.md +134 -0
  139. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-cli-app-best-practices.md +123 -0
  140. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-doc-validation.md +45 -0
  141. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-matcher-best-practices.md +106 -0
  142. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-modern-features.md +241 -0
  143. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-package-maintenance.md +75 -0
  144. package/template/agent/skills/mobile-developer/references/flutter-rules/dart-test-fundamentals.md +124 -0
  145. package/template/agent/skills/mobile-developer/references/flutter.md +291 -0
  146. package/template/agent/skills/mobile-developer/references/ios-native.md +358 -0
  147. package/template/agent/skills/mobile-developer/references/ios-rules/accessibility-patterns.md +215 -0
  148. package/template/agent/skills/mobile-developer/references/ios-rules/animation-advanced.md +403 -0
  149. package/template/agent/skills/mobile-developer/references/ios-rules/animation-basics.md +284 -0
  150. package/template/agent/skills/mobile-developer/references/ios-rules/animation-transitions.md +326 -0
  151. package/template/agent/skills/mobile-developer/references/ios-rules/charts-accessibility.md +135 -0
  152. package/template/agent/skills/mobile-developer/references/ios-rules/charts.md +602 -0
  153. package/template/agent/skills/mobile-developer/references/ios-rules/image-optimization.md +203 -0
  154. package/template/agent/skills/mobile-developer/references/ios-rules/latest-apis.md +464 -0
  155. package/template/agent/skills/mobile-developer/references/ios-rules/layout-best-practices.md +266 -0
  156. package/template/agent/skills/mobile-developer/references/ios-rules/liquid-glass.md +416 -0
  157. package/template/agent/skills/mobile-developer/references/ios-rules/list-patterns.md +394 -0
  158. package/template/agent/skills/mobile-developer/references/ios-rules/macos-scenes.md +318 -0
  159. package/template/agent/skills/mobile-developer/references/ios-rules/macos-views.md +357 -0
  160. package/template/agent/skills/mobile-developer/references/ios-rules/macos-window-styling.md +303 -0
  161. package/template/agent/skills/mobile-developer/references/ios-rules/performance-patterns.md +403 -0
  162. package/template/agent/skills/mobile-developer/references/ios-rules/scroll-patterns.md +293 -0
  163. package/template/agent/skills/mobile-developer/references/ios-rules/sheet-navigation-patterns.md +363 -0
  164. package/template/agent/skills/mobile-developer/references/ios-rules/state-management.md +417 -0
  165. package/template/agent/skills/mobile-developer/references/ios-rules/view-structure.md +389 -0
  166. package/template/agent/skills/mobile-developer/references/react-native-rules/_sections.md +86 -0
  167. package/template/agent/skills/mobile-developer/references/react-native-rules/_template.md +28 -0
  168. package/template/agent/skills/mobile-developer/references/react-native-rules/animation-derived-value.md +53 -0
  169. package/template/agent/skills/mobile-developer/references/react-native-rules/animation-gesture-detector-press.md +95 -0
  170. package/template/agent/skills/mobile-developer/references/react-native-rules/animation-gpu-properties.md +65 -0
  171. package/template/agent/skills/mobile-developer/references/react-native-rules/design-system-compound-components.md +66 -0
  172. package/template/agent/skills/mobile-developer/references/react-native-rules/fonts-config-plugin.md +71 -0
  173. package/template/agent/skills/mobile-developer/references/react-native-rules/imports-design-system-folder.md +68 -0
  174. package/template/agent/skills/mobile-developer/references/react-native-rules/js-hoist-intl.md +61 -0
  175. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-callbacks.md +44 -0
  176. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-function-references.md +132 -0
  177. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-images.md +53 -0
  178. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-inline-objects.md +97 -0
  179. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-item-expensive.md +94 -0
  180. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-item-memo.md +82 -0
  181. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-item-types.md +104 -0
  182. package/template/agent/skills/mobile-developer/references/react-native-rules/list-performance-virtualize.md +67 -0
  183. package/template/agent/skills/mobile-developer/references/react-native-rules/monorepo-native-deps-in-app.md +46 -0
  184. package/template/agent/skills/mobile-developer/references/react-native-rules/monorepo-single-dependency-versions.md +63 -0
  185. package/template/agent/skills/mobile-developer/references/react-native-rules/navigation-native-navigators.md +188 -0
  186. package/template/agent/skills/mobile-developer/references/react-native-rules/react-compiler-destructure-functions.md +50 -0
  187. package/template/agent/skills/mobile-developer/references/react-native-rules/react-compiler-reanimated-shared-values.md +48 -0
  188. package/template/agent/skills/mobile-developer/references/react-native-rules/react-state-dispatcher.md +91 -0
  189. package/template/agent/skills/mobile-developer/references/react-native-rules/react-state-fallback.md +56 -0
  190. package/template/agent/skills/mobile-developer/references/react-native-rules/react-state-minimize.md +65 -0
  191. package/template/agent/skills/mobile-developer/references/react-native-rules/rendering-no-falsy-and.md +74 -0
  192. package/template/agent/skills/mobile-developer/references/react-native-rules/rendering-text-in-text-component.md +36 -0
  193. package/template/agent/skills/mobile-developer/references/react-native-rules/scroll-position-no-state.md +82 -0
  194. package/template/agent/skills/mobile-developer/references/react-native-rules/state-ground-truth.md +80 -0
  195. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-expo-image.md +66 -0
  196. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-image-gallery.md +104 -0
  197. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-measure-views.md +78 -0
  198. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-menus.md +174 -0
  199. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-native-modals.md +77 -0
  200. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-pressable.md +61 -0
  201. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-safe-area-scroll.md +65 -0
  202. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-scrollview-content-inset.md +45 -0
  203. package/template/agent/skills/mobile-developer/references/react-native-rules/ui-styling.md +87 -0
  204. package/template/agent/skills/mobile-developer/references/react-native.md +345 -0
@@ -0,0 +1,51 @@
1
+ ---
2
+ name: android-data-layer
3
+ description: Guidance on implementing the Data Layer using Repository pattern, Room (Local), and Retrofit (Remote) with offline-first synchronization.
4
+ ---
5
+
6
+ # Android Data Layer & Offline-First
7
+
8
+ ## Instructions
9
+
10
+ The Data Layer coordinates data from multiple sources.
11
+
12
+ ### 1. Repository Pattern
13
+ * **Role**: Single Source of Truth (SSOT).
14
+ * **Logic**: The repository decides whether to return cached data or fetch fresh data.
15
+ * **Implementation**:
16
+ ```kotlin
17
+ class NewsRepository @Inject constructor(
18
+ private val newsDao: NewsDao,
19
+ private val newsApi: NewsApi
20
+ ) {
21
+ // Expose data from Local DB as the source of truth
22
+ val newsStream: Flow<List<News>> = newsDao.getAllNews()
23
+
24
+ // Sync operation
25
+ suspend fun refreshNews() {
26
+ val remoteNews = newsApi.fetchLatest()
27
+ newsDao.insertAll(remoteNews)
28
+ }
29
+ }
30
+ ```
31
+
32
+ ### 2. Local Persistence (Room)
33
+ * **Usage**: Primary cache and offline storage.
34
+ * **Entities**: Define `@Entity` data classes.
35
+ * **DAOs**: Return `Flow<T>` for observable data.
36
+
37
+ ### 3. Remote Data (Retrofit)
38
+ * **Usage**: Fetching data from backend.
39
+ * **Response**: Use `suspend` functions in interfaces.
40
+ * **Error Handling**: Wrap network calls in `try-catch` blocks or a `Result` wrapper to handle exceptions (NoInternet, 404, etc.) gracefully.
41
+
42
+ ### 4. Synchronization
43
+ * **Read**: "Stale-While-Revalidate". Show local data immediately, trigger a background refresh.
44
+ * **Write**: "Outbox Pattern" (Advanced). Save local change immediately, mark as "unsynced", use `WorkManager` to push changes to server.
45
+
46
+ ### 5. Dependency Injection
47
+ * Bind Repository interfaces to implementations in a Hilt Module.
48
+ ```kotlin
49
+ @Binds
50
+ abstract fun bindNewsRepository(impl: OfflineFirstNewsRepository): NewsRepository
51
+ ```
@@ -0,0 +1,108 @@
1
+ ---
2
+ name: android-emulator-skill
3
+ version: 1.0.0
4
+ description: Production-ready scripts for Android app testing, building, and automation. Provides semantic UI navigation, build automation, log monitoring, and emulator lifecycle management. Optimized for AI agents with minimal token output.
5
+ ---
6
+
7
+ # Android Emulator Skill
8
+
9
+ Build, test, and automate Android applications using accessibility-driven navigation and structured data instead of pixel coordinates.
10
+
11
+ ## Quick Start
12
+
13
+ ```bash
14
+ # 1. Check environment
15
+ bash scripts/emu_health_check.sh
16
+
17
+ # 2. Launch app
18
+ python scripts/app_launcher.py --launch com.example.app
19
+
20
+ # 3. Map screen to see elements
21
+ python scripts/screen_mapper.py
22
+
23
+ # 4. Tap button
24
+ python scripts/navigator.py --find-text "Login" --tap
25
+
26
+ # 5. Enter text
27
+ python scripts/navigator.py --find-type EditText --enter-text "user@example.com"
28
+ ```
29
+
30
+ All scripts support `--help` for detailed options and `--json` for machine-readable output.
31
+
32
+ ## Production Scripts
33
+
34
+ ### Build & Development
35
+
36
+ 1. **build_and_test.py** - Build Android projects, run tests, parse results
37
+ - Wrapper around Gradle
38
+ - Support for assemble, install, and connectedCheck
39
+ - Parse build errors and test results
40
+ - Options: `--task`, `--clean`, `--json`
41
+
42
+ 2. **log_monitor.py** - Real-time log monitoring with intelligent filtering
43
+ - Wrapper around `adb logcat`
44
+ - Filter by tag, priority, or PID
45
+ - Deduplicate repeated messages
46
+ - Options: `--package`, `--tag`, `--priority`, `--duration`, `--json`
47
+
48
+ ### Navigation & Interaction
49
+
50
+ 3. **screen_mapper.py** - Analyze current screen and list interactive elements
51
+ - Dump UI hierarchy using `uiautomator`
52
+ - Parse XML to identify buttons, text fields, etc.
53
+ - Options: `--verbose`, `--json`
54
+
55
+ 4. **navigator.py** - Find and interact with elements semantically
56
+ - Find by text (fuzzy matching), resource-id, or class name
57
+ - Interactive tapping and text entry
58
+ - Options: `--find-text`, `--find-id`, `--tap`, `--enter-text`, `--json`
59
+
60
+ 5. **gesture.py** - Perform swipes, scrolls, and other gestures
61
+ - Swipe up/down/left/right
62
+ - Scroll lists
63
+ - Options: `--swipe`, `--scroll`, `--duration`, `--json`
64
+
65
+ 6. **keyboard.py** - Key events and hardware buttons
66
+ - Input key events (Home, Back, Enter, Tab)
67
+ - Type text via ADB
68
+ - Options: `--key`, `--text`, `--json`
69
+
70
+ 7. **app_launcher.py** - App lifecycle management
71
+ - Launch apps (`adb shell am start`)
72
+ - Terminate apps (`adb shell am force-stop`)
73
+ - Install/Uninstall APKs
74
+ - List installed packages
75
+ - Options: `--launch`, `--terminate`, `--install`, `--uninstall`, `--list`, `--json`
76
+
77
+ ### Emulator Lifecycle Management
78
+
79
+ 8. **emulator_manage.py** - Manage Android Virtual Devices (AVDs)
80
+ - List available AVDs
81
+ - Boot emulators
82
+ - Shutdown emulators
83
+ - Options: `--list`, `--boot`, `--shutdown`, `--json`
84
+
85
+ 9. **emu_health_check.sh** - Verify environment is properly configured
86
+ - Check ADB, Emulator, Java, Gradle, ANDROID_HOME
87
+ - List connected devices
88
+
89
+ ## Common Patterns
90
+
91
+ **Auto-Device Detection**: Scripts target the single connected device/emulator if only one is present, or require `-s <serial>` if multiple are connected.
92
+
93
+ **Output Formats**: Default is concise human-readable output. Use `--json` for machine-readable output.
94
+
95
+ ## Requirements
96
+
97
+ - Android SDK Platform-Tools (adb, fastboot)
98
+ - Android Emulator
99
+ - Java / OpenJDK
100
+ - Python 3
101
+
102
+ ## Key Design Principles
103
+
104
+ **Semantic Navigation**: Find elements by text, resource-id, or content-description.
105
+
106
+ **Token Efficiency**: Concise default output with optional verbose and JSON modes.
107
+
108
+ **Zero Configuration**: Works with standard Android SDK installation.
@@ -0,0 +1,126 @@
1
+ ---
2
+ name: android-gradle-logic
3
+ description: Expert guidance on setting up scalable Gradle build logic using Convention Plugins and Version Catalogs.
4
+ ---
5
+
6
+ # Android Gradle Build Logic & Convention Plugins
7
+
8
+ This skill helps you configure a scalable, maintainable build system for Android apps using **Gradle Convention Plugins** and **Version Catalogs**, following the "Now in Android" (NiA) architecture.
9
+
10
+ ## Goal
11
+ Stop copy-pasting code between `build.gradle.kts` files. Centralize build logic (Compose setup, Kotlin options, Hilt, etc.) in reusable plugins.
12
+
13
+ ## Project Structure
14
+
15
+ Ensure your project has a `build-logic` directory included in `settings.gradle.kts` as a composite build.
16
+
17
+ ```text
18
+ root/
19
+ ├── build-logic/
20
+ │ ├── convention/
21
+ │ │ ├── src/main/kotlin/
22
+ │ │ │ └── AndroidApplicationConventionPlugin.kt
23
+ │ │ └── build.gradle.kts
24
+ │ ├── build.gradle.kts
25
+ │ └── settings.gradle.kts
26
+ ├── gradle/
27
+ │ └── libs.versions.toml
28
+ ├── app/
29
+ │ └── build.gradle.kts
30
+ └── settings.gradle.kts
31
+ ```
32
+
33
+ ## Step 1: Configure `settings.gradle.kts`
34
+
35
+ Include the `build-logic` as a plugin management source.
36
+
37
+ ```kotlin
38
+ // settings.gradle.kts
39
+ pluginManagement {
40
+ includeBuild("build-logic")
41
+ repositories {
42
+ google()
43
+ mavenCentral()
44
+ gradlePluginPortal()
45
+ }
46
+ }
47
+ dependencyResolutionManagement {
48
+ repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS)
49
+ repositories {
50
+ google()
51
+ mavenCentral()
52
+ }
53
+ }
54
+ ```
55
+
56
+ ## Step 2: Define Dependencies in `libs.versions.toml`
57
+
58
+ Use the Version Catalog for both libraries *and* plugins.
59
+
60
+ ```toml
61
+ [versions]
62
+ androidGradlePlugin = "8.2.0"
63
+ kotlin = "1.9.20"
64
+
65
+ [libraries]
66
+ # ...
67
+
68
+ [plugins]
69
+ android-application = { id = "com.android.application", version.ref = "androidGradlePlugin" }
70
+ android-library = { id = "com.android.library", version.ref = "androidGradlePlugin" }
71
+ kotlin-android = { id = "org.jetbrains.kotlin.android", version.ref = "kotlin" }
72
+ # Define your own plugins here
73
+ nowinandroid-android-application = { id = "nowinandroid.android.application", version = "unspecified" }
74
+ ```
75
+
76
+ ## Step 3: Create a Convention Plugin
77
+
78
+ Inside `build-logic/convention/src/main/kotlin/AndroidApplicationConventionPlugin.kt`:
79
+
80
+ ```kotlin
81
+ import com.android.build.api.dsl.ApplicationExtension
82
+ import org.gradle.api.Plugin
83
+ import org.gradle.api.Project
84
+ import org.gradle.kotlin.dsl.configure
85
+
86
+ class AndroidApplicationConventionPlugin : Plugin<Project> {
87
+ override fun apply(target: Project) {
88
+ with(target) {
89
+ with(pluginManager) {
90
+ apply("com.android.application")
91
+ apply("org.jetbrains.kotlin.android")
92
+ }
93
+
94
+ extensions.configure<ApplicationExtension> {
95
+ defaultConfig.targetSdk = 34
96
+ // Configure common options here
97
+ }
98
+ }
99
+ }
100
+ }
101
+ ```
102
+
103
+ Don't forget to register it in `build-logic/convention/build.gradle.kts`:
104
+
105
+ ```kotlin
106
+ gradlePlugin {
107
+ plugins {
108
+ register("androidApplication") {
109
+ id = "nowinandroid.android.application"
110
+ implementationClass = "AndroidApplicationConventionPlugin"
111
+ }
112
+ }
113
+ }
114
+ ```
115
+
116
+ ## Usage
117
+
118
+ Apply your custom plugin in your modules (e.g., `app/build.gradle.kts`):
119
+
120
+ ```kotlin
121
+ plugins {
122
+ alias(libs.plugins.nowinandroid.android.application)
123
+ }
124
+ ```
125
+
126
+ This drastically cleans up module-level build files.
@@ -0,0 +1,142 @@
1
+ ---
2
+ name: android-retrofit
3
+ description: Expert guidance on setting up and using Retrofit for type-safe HTTP networking in Android. Covers service definitions, coroutines, OkHttp configuration, and Hilt integration.
4
+ ---
5
+
6
+ # Android Networking with Retrofit
7
+
8
+ ## Instructions
9
+
10
+ When implementing network layers using **Retrofit**, follow these modern Android best practices (2025).
11
+
12
+ ### 1. URL Manipulation
13
+ Retrofit allows dynamic URL updates through replacement blocks and query parameters.
14
+
15
+ * **Dynamic Paths**: Use `{name}` in the relative URL and `@Path("name")` in parameters.
16
+ * **Query Parameters**: Use `@Query("key")` for individual parameters.
17
+ * **Complex Queries**: Use `@QueryMap Map<String, String>` for dynamic sets of parameters.
18
+
19
+ ```kotlin
20
+ interface SearchService {
21
+ @GET("group/{id}/users")
22
+ suspend fun groupList(
23
+ @Path("id") groupId: Int,
24
+ @Query("sort") sort: String?,
25
+ @QueryMap options: Map<String, String> = emptyMap()
26
+ ): List<User>
27
+ }
28
+ ```
29
+
30
+ ### 2. Request Body & Form Data
31
+ You can send objects as JSON bodies or use form-encoded/multipart formats.
32
+
33
+ * **@Body**: Serializes an object using the configured converter (JSON).
34
+ * **@FormUrlEncoded**: Sends data as `application/x-www-form-urlencoded`. Use `@Field`.
35
+ * **@Multipart**: Sends data as `multipart/form-data`. Use `@Part`.
36
+
37
+ ```kotlin
38
+ interface UserService {
39
+ @POST("users/new")
40
+ suspend fun createUser(@Body user: User): User
41
+
42
+ @FormUrlEncoded
43
+ @POST("user/edit")
44
+ suspend fun updateUser(
45
+ @Field("first_name") first: String,
46
+ @Field("last_name") last: String
47
+ ): User
48
+
49
+ @Multipart
50
+ @PUT("user/photo")
51
+ suspend fun uploadPhoto(
52
+ @Part("description") description: RequestBody,
53
+ @Part photo: MultipartBody.Part
54
+ ): User
55
+ }
56
+ ```
57
+
58
+ ### 3. Header Manipulation
59
+ Headers can be set statically for a method or dynamically via parameters.
60
+
61
+ * **Static Headers**: Use `@Headers`.
62
+ * **Dynamic Headers**: Use `@Header`.
63
+ * **Header Maps**: Use `@HeaderMap`.
64
+ * **Global Headers**: Use an OkHttp **Interceptor**.
65
+
66
+ ```kotlin
67
+ interface WidgetService {
68
+ @Headers("Cache-Control: max-age=640000")
69
+ @GET("widget/list")
70
+ suspend fun widgetList(): List<Widget>
71
+
72
+ @GET("user")
73
+ suspend fun getUser(@Header("Authorization") token: String): User
74
+ }
75
+ ```
76
+
77
+ ### 4. Kotlin Support & Response Handling
78
+ When using `suspend` functions, you have two choices for return types:
79
+
80
+ 1. **Direct Body (`User`)**: Returns the deserialized body. Throws `HttpException` for non-2xx responses.
81
+ 2. **`Response<User>`**: Provides access to the status code, headers, and error body. Does NOT throw on non-2xx results.
82
+
83
+ ```kotlin
84
+ @GET("users")
85
+ suspend fun getUsers(): List<User> // Throws on error
86
+
87
+ @GET("users")
88
+ suspend fun getUsersResponse(): Response<List<User>> // Manual check
89
+ ```
90
+
91
+ ### 5. Hilt & Serialization Configuration
92
+ Provide your Retrofit instances as singletons in a Hilt module.
93
+
94
+ ```kotlin
95
+ @Module
96
+ @InstallIn(SingletonComponent::class)
97
+ object NetworkModule {
98
+
99
+ @Provides
100
+ @Singleton
101
+ fun provideJson(): Json = Json {
102
+ ignoreUnknownKeys = true
103
+ coerceInputValues = true
104
+ }
105
+
106
+ @Provides
107
+ @Singleton
108
+ fun provideOkHttpClient(): OkHttpClient = OkHttpClient.Builder()
109
+ .addInterceptor(HttpLoggingInterceptor().apply { level = HttpLoggingInterceptor.Level.BODY })
110
+ .connectTimeout(30, TimeUnit.SECONDS)
111
+ .build()
112
+
113
+ @Provides
114
+ @Singleton
115
+ fun provideRetrofit(okHttpClient: OkHttpClient, json: Json): Retrofit = Retrofit.Builder()
116
+ .baseUrl("https://api.github.com/")
117
+ .client(okHttpClient)
118
+ .addConverterFactory(json.asConverterFactory("application/json".toMediaType()))
119
+ .build()
120
+ }
121
+ ```
122
+
123
+ ### 6. Error Handling in Repositories
124
+ Always handle network exceptions in the Repository layer to keep the UI state clean.
125
+
126
+ ```kotlin
127
+ class GitHubRepository @Inject constructor(private val service: GitHubService) {
128
+ suspend fun getRepos(username: String): Result<List<Repo>> = runCatching {
129
+ // Direct body call throws HttpException on 4xx/5xx
130
+ service.listRepos(username)
131
+ }.onFailure { exception ->
132
+ // Handle specific exceptions like UnknownHostException or SocketTimeoutException
133
+ }
134
+ }
135
+ ```
136
+
137
+ ### 7. Checklist
138
+ - [ ] Use `suspend` functions for all network calls.
139
+ - [ ] Prefer `Response<T>` if you need to handle specific status codes (e.g., 401 Unauthorized).
140
+ - [ ] Use `@Path` and `@Query` instead of manual string concatenation for URLs.
141
+ - [ ] Configure `OkHttpClient` with logging (for debug) and sensible timeouts.
142
+ - [ ] Map API DTOs to Domain models to decouple layers.
@@ -0,0 +1,102 @@
1
+ ---
2
+ name: android-testing
3
+ description: Comprehensive testing strategy involving Unit, Integration, Hilt, and Screenshot tests.
4
+ ---
5
+
6
+ # Android Testing Strategies
7
+
8
+ This skill provides expert guidance on testing modern Android applications, inspired by "Now in Android". It covers **Unit Tests**, **Hilt Integration Tests**, and **Screenshot Testing**.
9
+
10
+ ## Testing Pyramid
11
+
12
+ 1. **Unit Tests**: Fast, isolate logic (ViewModels, Repositories).
13
+ 2. **Integration Tests**: Test interactions (Room DAOs, Retrofit vs MockWebServer).
14
+ 3. **UI/Screenshot Tests**: Verify UI correctness (Compose).
15
+
16
+ ## Dependencies (`libs.versions.toml`)
17
+
18
+ Ensure you have the right testing dependencies.
19
+
20
+ ```toml
21
+ [libraries]
22
+ junit4 = { module = "junit:junit", version = "4.13.2" }
23
+ kotlinx-coroutines-test = { group = "org.jetbrains.kotlinx", name = "kotlinx-coroutines-test", version.ref = "kotlinxCoroutines" }
24
+ androidx-test-ext-junit = { group = "androidx.test.ext", name = "junit", version = "1.1.5" }
25
+ espresso-core = { group = "androidx.test.espresso", name = "espresso-core", version = "3.5.1" }
26
+ compose-ui-test = { group = "androidx.compose.ui", name = "ui-test-junit4" }
27
+ hilt-android-testing = { group = "com.google.dagger", name = "hilt-android-testing", version.ref = "hilt" }
28
+ roborazzi = { group = "io.github.takahirom.roborazzi", name = "roborazzi", version.ref = "roborazzi" }
29
+ ```
30
+
31
+ ## Screenshot Testing with Roborazzi
32
+
33
+ Screenshot tests ensure your UI doesn't regress visually. NiA uses **Roborazzi** because it runs on the JVM (fast) without needing an emulator.
34
+
35
+ ### Setup
36
+
37
+ 1. Add the plugin to `libs.versions.toml`:
38
+ ```toml
39
+ [plugins]
40
+ roborazzi = { id = "io.github.takahirom.roborazzi", version.ref = "roborazzi" }
41
+ ```
42
+ 2. Apply it in your module's `build.gradle.kts`:
43
+ ```kotlin
44
+ plugins {
45
+ alias(libs.plugins.roborazzi)
46
+ }
47
+ ```
48
+
49
+ ### Writing a Screenshot Test
50
+
51
+ ```kotlin
52
+ @RunWith(AndroidJUnit4::class)
53
+ @GraphicsMode(GraphicsMode.Mode.NATIVE)
54
+ @Config(sdk = [33], qualifiers = RobolectricDeviceQualifiers.Pixel5)
55
+ class MyScreenScreenshotTest {
56
+
57
+ @get:Rule
58
+ val composeTestRule = createAndroidComposeRule<ComponentActivity>()
59
+
60
+ @Test
61
+ fun captureMyScreen() {
62
+ composeTestRule.setContent {
63
+ MyTheme {
64
+ MyScreen()
65
+ }
66
+ }
67
+
68
+ composeTestRule.onRoot()
69
+ .captureRoboImage()
70
+ }
71
+ }
72
+ ```
73
+
74
+ ## Hilt Testing
75
+
76
+ Use `HiltAndroidRule` to inject dependencies in tests.
77
+
78
+ ```kotlin
79
+ @HiltAndroidTest
80
+ class MyDaoTest {
81
+
82
+ @get:Rule
83
+ var hiltRule = HiltAndroidRule(this)
84
+
85
+ @Inject
86
+ lateinit var database: MyDatabase
87
+ private lateinit var dao: MyDao
88
+
89
+ @Before
90
+ fun init() {
91
+ hiltRule.inject()
92
+ dao = database.myDao()
93
+ }
94
+
95
+ // ... tests
96
+ }
97
+ ```
98
+
99
+ ## Running Tests
100
+
101
+ * **Unit**: `./gradlew test`
102
+ * **Screenshots**: `./gradlew recordRoborazziDebug` (to record) / `./gradlew verifyRoborazziDebug` (to verify)
@@ -0,0 +1,43 @@
1
+ ---
2
+ name: android-viewmodel
3
+ description: Best practices for implementing Android ViewModels, specifically focused on StateFlow for UI state and SharedFlow for one-off events.
4
+ ---
5
+
6
+ # Android ViewModel & State Management
7
+
8
+ ## Instructions
9
+
10
+ Use `ViewModel` to hold state and business logic. It must outlive configuration changes.
11
+
12
+ ### 1. UI State (StateFlow)
13
+ * **What**: Represents the persistent state of the UI (e.g., `Loading`, `Success(data)`, `Error`).
14
+ * **Type**: `StateFlow<UiState>`.
15
+ * **Initialization**: Must have an initial value.
16
+ * **Exposure**: Expose as a read-only `StateFlow` backing a private `MutableStateFlow`.
17
+ ```kotlin
18
+ private val _uiState = MutableStateFlow<UiState>(UiState.Loading)
19
+ val uiState: StateFlow<UiState> = _uiState.asStateFlow()
20
+ ```
21
+ * **Updates**: Update state using `.update { oldState -> ... }` for thread safety.
22
+
23
+ ### 2. One-Off Events (SharedFlow)
24
+ * **What**: Transient events like "Show Toast", "Navigate to Screen", "Show Snackbar".
25
+ * **Type**: `SharedFlow<UiEvent>`.
26
+ * **Configuration**: Must use `replay = 0` to prevent events from re-triggering on screen rotation.
27
+ ```kotlin
28
+ private val _uiEvent = MutableSharedFlow<UiEvent>(replay = 0)
29
+ val uiEvent: SharedFlow<UiEvent> = _uiEvent.asSharedFlow()
30
+ ```
31
+ * **Sending**: Use `.emit(event)` (suspend) or `.tryEmit(event)`.
32
+
33
+ ### 3. Collecting in UI
34
+ * **Compose**: Use `collectAsStateWithLifecycle()` for `StateFlow`.
35
+ ```kotlin
36
+ val state by viewModel.uiState.collectAsStateWithLifecycle()
37
+ ```
38
+ For `SharedFlow`, use `LaunchedEffect` with `LocalLifecycleOwner`.
39
+ * **Views (XML)**: Use `repeatOnLifecycle(Lifecycle.State.STARTED)` within a coroutine.
40
+
41
+ ### 4. Scope
42
+ * Use `viewModelScope` for all coroutines started by the ViewModel.
43
+ * Ideally, specific operations should be delegated to UseCases or Repositories.
@@ -0,0 +1,74 @@
1
+ ---
2
+ name: coil-compose
3
+ description: Expert guidance on using Coil for image loading in Jetpack Compose. Use this when asked about loading images from URLs, handling image states, or optimizing image performance in Compose.
4
+ ---
5
+
6
+ # Coil for Jetpack Compose
7
+
8
+ ## Instructions
9
+
10
+ When implementing image loading in Jetpack Compose, use **Coil** (Coroutines Image Loader). It is the recommended library for Compose due to its efficiency and seamless integration.
11
+
12
+ ### 1. Primary Composable: `AsyncImage`
13
+ Use `AsyncImage` for most use cases. It handles size resolution automatically and supports standard `Image` parameters.
14
+
15
+ ```kotlin
16
+ AsyncImage(
17
+ model = ImageRequest.Builder(LocalContext.current)
18
+ .data("https://example.com/image.jpg")
19
+ .crossfade(true)
20
+ .build(),
21
+ placeholder = painterResource(R.drawable.placeholder),
22
+ error = painterResource(R.drawable.error),
23
+ contentDescription = stringResource(R.string.description),
24
+ contentScale = ContentScale.Crop,
25
+ modifier = Modifier.clip(CircleShape)
26
+ )
27
+ ```
28
+
29
+ ### 2. Low-Level Control: `rememberAsyncImagePainter`
30
+ Use `rememberAsyncImagePainter` only when you need a `Painter` instead of a composable (e.g., for `Canvas` or `Icon`) or when you need to observe the loading state manually.
31
+
32
+ > [!WARNING]
33
+ > `rememberAsyncImagePainter` does not detect the size your image is loaded at on screen and always loads the image with its original dimensions by default. Use `AsyncImage` unless a `Painter` is strictly required.
34
+
35
+ ```kotlin
36
+ val painter = rememberAsyncImagePainter(
37
+ model = ImageRequest.Builder(LocalContext.current)
38
+ .data("https://example.com/image.jpg")
39
+ .size(Size.ORIGINAL) // Explicitly define size if needed
40
+ .build()
41
+ )
42
+ ```
43
+
44
+ ### 3. Slot API: `SubcomposeAsyncImage`
45
+ Use `SubcomposeAsyncImage` when you need a custom slot API for different states (Loading, Success, Error).
46
+
47
+ > [!CAUTION]
48
+ > Subcomposition is slower than regular composition. Avoid using `SubcomposeAsyncImage` in performance-critical areas like `LazyColumn` or `LazyRow`.
49
+
50
+ ```kotlin
51
+ SubcomposeAsyncImage(
52
+ model = "https://example.com/image.jpg",
53
+ contentDescription = null,
54
+ loading = {
55
+ CircularProgressIndicator()
56
+ },
57
+ error = {
58
+ Icon(Icons.Default.Error, contentDescription = null)
59
+ }
60
+ )
61
+ ```
62
+
63
+ ### 4. Performance & Best Practices
64
+ * **Singleton ImageLoader**: Use a single `ImageLoader` instance for the entire app to share the disk/memory cache.
65
+ * **Main-Safe**: Coil executes image requests on a background thread automatically.
66
+ * **Crossfade**: Always enable `crossfade(true)` in `ImageRequest` for a smoother transition from placeholder to success.
67
+ * **Sizing**: Ensure `contentScale` is set appropriately to avoid loading larger images than necessary.
68
+
69
+ ### 5. Checklist for implementation
70
+ - [ ] Prefer `AsyncImage` over other variants.
71
+ - [ ] Always provide a meaningful `contentDescription` or set it to `null` for decorative images.
72
+ - [ ] Use `crossfade(true)` for better UX.
73
+ - [ ] Avoid `SubcomposeAsyncImage` in lists.
74
+ - [ ] Configure `ImageRequest` for specific needs like transformations (e.g., `CircleCropTransformation`).