@ngxtm/devkit 3.3.0 → 3.4.1

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 (345) hide show
  1. package/cli/index.js +59 -13
  2. package/cli/rules.js +248 -0
  3. package/package.json +2 -1
  4. package/rules/README.md +141 -0
  5. package/rules/dart/best-practices/SKILL.md +23 -0
  6. package/rules/dart/language/SKILL.md +52 -0
  7. package/rules/dart/tooling/SKILL.md +43 -0
  8. package/rules/dotnet/aspnet-core/SKILL.md +92 -0
  9. package/rules/dotnet/aspnet-core/references/REFERENCE.md +335 -0
  10. package/rules/dotnet/best-practices/SKILL.md +101 -0
  11. package/rules/dotnet/best-practices/references/REFERENCE.md +256 -0
  12. package/rules/dotnet/blazor/SKILL.md +146 -0
  13. package/rules/dotnet/blazor/references/REFERENCE.md +392 -0
  14. package/rules/dotnet/language/SKILL.md +82 -0
  15. package/rules/dotnet/language/references/REFERENCE.md +222 -0
  16. package/rules/dotnet/patterns.rule.md +388 -0
  17. package/rules/dotnet/razor-pages/SKILL.md +124 -0
  18. package/rules/dotnet/razor-pages/references/REFERENCE.md +321 -0
  19. package/rules/dotnet/security/SKILL.md +89 -0
  20. package/rules/dotnet/security/references/REFERENCE.md +295 -0
  21. package/rules/dotnet/tooling/SKILL.md +92 -0
  22. package/rules/dotnet/tooling/references/REFERENCE.md +300 -0
  23. package/rules/flutter/auto-route-navigation/SKILL.md +43 -0
  24. package/rules/flutter/auto-route-navigation/references/REFERENCE.md +19 -0
  25. package/rules/flutter/auto-route-navigation/references/router-config.md +62 -0
  26. package/rules/flutter/bloc-state-management/SKILL.md +64 -0
  27. package/rules/flutter/bloc-state-management/references/REFERENCE.md +20 -0
  28. package/rules/flutter/bloc-state-management/references/auth-bloc-example.md +52 -0
  29. package/rules/flutter/bloc-state-management/references/equatable-usage.md +56 -0
  30. package/rules/flutter/bloc-state-management/references/property-based-state.md +68 -0
  31. package/rules/flutter/bloc.rule.md +76 -0
  32. package/rules/flutter/cicd/SKILL.md +48 -0
  33. package/rules/flutter/cicd/references/advanced-workflow.md +66 -0
  34. package/rules/flutter/cicd/references/fastlane.md +139 -0
  35. package/rules/flutter/cicd/references/github-actions.md +59 -0
  36. package/rules/flutter/dependency-injection/SKILL.md +42 -0
  37. package/rules/flutter/dependency-injection/references/REFERENCE.md +15 -0
  38. package/rules/flutter/dependency-injection/references/modules.md +37 -0
  39. package/rules/flutter/error-handling/SKILL.md +32 -0
  40. package/rules/flutter/error-handling/references/REFERENCE.md +19 -0
  41. package/rules/flutter/error-handling/references/error-mapping.md +31 -0
  42. package/rules/flutter/feature-based-clean-architecture/SKILL.md +46 -0
  43. package/rules/flutter/feature-based-clean-architecture/references/REFERENCE.md +14 -0
  44. package/rules/flutter/feature-based-clean-architecture/references/folder-structure.md +36 -0
  45. package/rules/flutter/getx-navigation/SKILL.md +70 -0
  46. package/rules/flutter/getx-navigation/references/app-pages.md +40 -0
  47. package/rules/flutter/getx-navigation/references/middleware-example.md +29 -0
  48. package/rules/flutter/getx-state-management/SKILL.md +76 -0
  49. package/rules/flutter/getx-state-management/references/binding-example.md +32 -0
  50. package/rules/flutter/getx-state-management/references/reactive-vs-simple.md +39 -0
  51. package/rules/flutter/go-router-navigation/SKILL.md +57 -0
  52. package/rules/flutter/idiomatic-flutter/SKILL.md +20 -0
  53. package/rules/flutter/layer-based-clean-architecture/SKILL.md +50 -0
  54. package/rules/flutter/layer-based-clean-architecture/references/REFERENCE.md +60 -0
  55. package/rules/flutter/layer-based-clean-architecture/references/repository-mapping.md +50 -0
  56. package/rules/flutter/localization/SKILL.md +50 -0
  57. package/rules/flutter/localization/references/REFERENCE.md +48 -0
  58. package/rules/flutter/localization/references/sheet-loader.md +33 -0
  59. package/rules/flutter/navigator-v1-navigation/SKILL.md +71 -0
  60. package/rules/flutter/navigator-v1-navigation/references/on-generate-route.md +48 -0
  61. package/rules/flutter/performance/SKILL.md +24 -0
  62. package/rules/flutter/retrofit-networking/SKILL.md +51 -0
  63. package/rules/flutter/retrofit-networking/references/REFERENCE.md +19 -0
  64. package/rules/flutter/retrofit-networking/references/token-refresh.md +40 -0
  65. package/rules/flutter/riverpod-state-management/SKILL.md +53 -0
  66. package/rules/flutter/riverpod-state-management/references/architecture.md +124 -0
  67. package/rules/flutter/riverpod-state-management/references/best-practices.md +89 -0
  68. package/rules/flutter/riverpod-state-management/references/testing.md +73 -0
  69. package/rules/flutter/riverpod.rule.md +78 -0
  70. package/rules/flutter/security/SKILL.md +33 -0
  71. package/rules/flutter/security/references/REFERENCE.md +15 -0
  72. package/rules/flutter/security/references/network-security.md +28 -0
  73. package/rules/flutter/testing/SKILL.md +44 -0
  74. package/rules/flutter/testing/references/REFERENCE.md +21 -0
  75. package/rules/flutter/testing/references/bloc-testing.md +38 -0
  76. package/rules/flutter/testing/references/integration-testing.md +128 -0
  77. package/rules/flutter/testing/references/robot-pattern.md +82 -0
  78. package/rules/flutter/testing/references/unit-testing.md +130 -0
  79. package/rules/flutter/testing/references/widget-testing.md +120 -0
  80. package/rules/flutter/widgets/SKILL.md +37 -0
  81. package/rules/golang/chi-router/SKILL.md +219 -0
  82. package/rules/golang/chi-router/references/REFERENCE.md +13 -0
  83. package/rules/golang/chi-router/references/routing-patterns.md +205 -0
  84. package/rules/golang/cobra-cli/SKILL.md +227 -0
  85. package/rules/golang/cobra-cli/references/REFERENCE.md +13 -0
  86. package/rules/golang/cobra-cli/references/command-patterns.md +224 -0
  87. package/rules/golang/core/SKILL.md +210 -0
  88. package/rules/golang/core/references/REFERENCE.md +14 -0
  89. package/rules/golang/core/references/concurrency-patterns.md +114 -0
  90. package/rules/golang/core/references/error-handling.md +87 -0
  91. package/rules/golang/echo-framework/SKILL.md +215 -0
  92. package/rules/golang/echo-framework/references/REFERENCE.md +14 -0
  93. package/rules/golang/echo-framework/references/middleware-patterns.md +141 -0
  94. package/rules/golang/echo-framework/references/routing-patterns.md +140 -0
  95. package/rules/golang/ent-orm/SKILL.md +239 -0
  96. package/rules/golang/ent-orm/references/REFERENCE.md +13 -0
  97. package/rules/golang/ent-orm/references/schema-patterns.md +255 -0
  98. package/rules/golang/fiber-framework/SKILL.md +196 -0
  99. package/rules/golang/fiber-framework/references/REFERENCE.md +13 -0
  100. package/rules/golang/fiber-framework/references/routing-patterns.md +191 -0
  101. package/rules/golang/gin-framework/SKILL.md +205 -0
  102. package/rules/golang/gin-framework/references/REFERENCE.md +14 -0
  103. package/rules/golang/gin-framework/references/middleware-patterns.md +119 -0
  104. package/rules/golang/gorm-orm/SKILL.md +196 -0
  105. package/rules/golang/gorm-orm/references/REFERENCE.md +14 -0
  106. package/rules/golang/gorm-orm/references/model-definitions.md +167 -0
  107. package/rules/golang/gorm-orm/references/query-patterns.md +161 -0
  108. package/rules/golang/grpc/SKILL.md +231 -0
  109. package/rules/golang/grpc/references/REFERENCE.md +13 -0
  110. package/rules/golang/grpc/references/service-patterns.md +276 -0
  111. package/rules/golang/testify/SKILL.md +239 -0
  112. package/rules/golang/testify/references/REFERENCE.md +13 -0
  113. package/rules/golang/testify/references/assert-patterns.md +170 -0
  114. package/rules/golang/validator/SKILL.md +234 -0
  115. package/rules/golang/validator/references/REFERENCE.md +13 -0
  116. package/rules/golang/validator/references/validation-tags.md +211 -0
  117. package/rules/golang/viper-config/SKILL.md +244 -0
  118. package/rules/golang/viper-config/references/REFERENCE.md +13 -0
  119. package/rules/golang/viper-config/references/config-loading.md +181 -0
  120. package/rules/golang/wire-di/SKILL.md +243 -0
  121. package/rules/golang/wire-di/references/REFERENCE.md +13 -0
  122. package/rules/golang/wire-di/references/provider-patterns.md +193 -0
  123. package/rules/golang/zap-logging/SKILL.md +203 -0
  124. package/rules/golang/zap-logging/references/REFERENCE.md +13 -0
  125. package/rules/golang/zap-logging/references/logger-config.md +165 -0
  126. package/rules/java/build-gradle/SKILL.md +92 -0
  127. package/rules/java/build-gradle/references/REFERENCE.md +14 -0
  128. package/rules/java/build-gradle/references/kotlin-dsl.md +118 -0
  129. package/rules/java/build-gradle/references/task-configuration.md +132 -0
  130. package/rules/java/build-maven/SKILL.md +86 -0
  131. package/rules/java/build-maven/references/REFERENCE.md +14 -0
  132. package/rules/java/build-maven/references/dependency-management.md +111 -0
  133. package/rules/java/build-maven/references/lifecycle-phases.md +114 -0
  134. package/rules/java/graalvm-native/SKILL.md +105 -0
  135. package/rules/java/graalvm-native/references/REFERENCE.md +12 -0
  136. package/rules/java/java-collections-streams/SKILL.md +148 -0
  137. package/rules/java/java-collections-streams/references/REFERENCE.md +15 -0
  138. package/rules/java/java-collections-streams/references/collectors-patterns.md +178 -0
  139. package/rules/java/java-collections-streams/references/stream-pipelines.md +165 -0
  140. package/rules/java/java-concurrency/SKILL.md +187 -0
  141. package/rules/java/java-concurrency/references/REFERENCE.md +17 -0
  142. package/rules/java/java-concurrency/references/completable-future.md +165 -0
  143. package/rules/java/java-concurrency/references/executor-patterns.md +176 -0
  144. package/rules/java/java-concurrency/references/virtual-threads.md +190 -0
  145. package/rules/java/java-core-language/SKILL.md +121 -0
  146. package/rules/java/java-core-language/references/REFERENCE.md +15 -0
  147. package/rules/java/java-core-language/references/jvm-memory-model.md +160 -0
  148. package/rules/java/java-core-language/references/modern-java-features.md +168 -0
  149. package/rules/java/java-project-structure/SKILL.md +195 -0
  150. package/rules/java/java-project-structure/references/REFERENCE.md +15 -0
  151. package/rules/java/java-project-structure/references/maven-project-layout.md +199 -0
  152. package/rules/java/java-project-structure/references/module-system.md +159 -0
  153. package/rules/java/micronaut-core/SKILL.md +99 -0
  154. package/rules/java/micronaut-core/references/REFERENCE.md +12 -0
  155. package/rules/java/micronaut-reactive/SKILL.md +68 -0
  156. package/rules/java/micronaut-reactive/references/REFERENCE.md +12 -0
  157. package/rules/java/quarkus-core/SKILL.md +85 -0
  158. package/rules/java/quarkus-core/references/REFERENCE.md +12 -0
  159. package/rules/java/quarkus-reactive/SKILL.md +67 -0
  160. package/rules/java/quarkus-reactive/references/REFERENCE.md +12 -0
  161. package/rules/java/spring-batch/SKILL.md +102 -0
  162. package/rules/java/spring-batch/references/REFERENCE.md +12 -0
  163. package/rules/java/spring-boot-architecture/SKILL.md +206 -0
  164. package/rules/java/spring-boot-architecture/references/REFERENCE.md +15 -0
  165. package/rules/java/spring-boot-architecture/references/auto-configuration.md +158 -0
  166. package/rules/java/spring-boot-architecture/references/configuration-properties.md +202 -0
  167. package/rules/java/spring-boot-web/SKILL.md +217 -0
  168. package/rules/java/spring-boot-web/references/REFERENCE.md +17 -0
  169. package/rules/java/spring-cloud/SKILL.md +109 -0
  170. package/rules/java/spring-cloud/references/REFERENCE.md +13 -0
  171. package/rules/java/spring-data-jpa/SKILL.md +241 -0
  172. package/rules/java/spring-data-jpa/references/REFERENCE.md +16 -0
  173. package/rules/java/spring-security/SKILL.md +161 -0
  174. package/rules/java/spring-security/references/REFERENCE.md +16 -0
  175. package/rules/java/spring-security/references/jwt-auth-flow.md +213 -0
  176. package/rules/java/testing-junit-mockito/SKILL.md +135 -0
  177. package/rules/java/testing-junit-mockito/references/REFERENCE.md +15 -0
  178. package/rules/java/testing-junit-mockito/references/junit5-patterns.md +159 -0
  179. package/rules/java/testing-junit-mockito/references/mockito-patterns.md +148 -0
  180. package/rules/java/testing-junit-mockito/references/spring-boot-testing.md +152 -0
  181. package/rules/javascript/best-practices/SKILL.md +64 -0
  182. package/rules/javascript/best-practices/references/REFERENCE.md +91 -0
  183. package/rules/javascript/language/SKILL.md +71 -0
  184. package/rules/javascript/language/references/REFERENCE.md +106 -0
  185. package/rules/javascript/tooling/SKILL.md +60 -0
  186. package/rules/javascript/tooling/references/REFERENCE.md +107 -0
  187. package/rules/metadata.json +54 -0
  188. package/rules/nestjs/api-standards/SKILL.md +47 -0
  189. package/rules/nestjs/api-standards/references/pagination-wrapper.md +87 -0
  190. package/rules/nestjs/architecture/SKILL.md +68 -0
  191. package/rules/nestjs/architecture/references/dynamic-module.md +53 -0
  192. package/rules/nestjs/caching/SKILL.md +51 -0
  193. package/rules/nestjs/caching/references/REFERENCE.md +13 -0
  194. package/rules/nestjs/caching/references/cache-patterns.md +183 -0
  195. package/rules/nestjs/configuration/SKILL.md +41 -0
  196. package/rules/nestjs/configuration/references/REFERENCE.md +13 -0
  197. package/rules/nestjs/configuration/references/config-patterns.md +184 -0
  198. package/rules/nestjs/controllers-services/SKILL.md +63 -0
  199. package/rules/nestjs/controllers-services/references/REFERENCE.md +14 -0
  200. package/rules/nestjs/controllers-services/references/controller-patterns.md +119 -0
  201. package/rules/nestjs/controllers-services/references/service-patterns.md +129 -0
  202. package/rules/nestjs/database/SKILL.md +102 -0
  203. package/rules/nestjs/database/references/REFERENCE.md +14 -0
  204. package/rules/nestjs/database/references/typeorm-patterns.md +156 -0
  205. package/rules/nestjs/deployment/SKILL.md +36 -0
  206. package/rules/nestjs/deployment/references/REFERENCE.md +13 -0
  207. package/rules/nestjs/deployment/references/deployment-patterns.md +140 -0
  208. package/rules/nestjs/documentation/SKILL.md +64 -0
  209. package/rules/nestjs/documentation/references/REFERENCE.md +13 -0
  210. package/rules/nestjs/documentation/references/swagger-patterns.md +139 -0
  211. package/rules/nestjs/error-handling/SKILL.md +55 -0
  212. package/rules/nestjs/error-handling/references/REFERENCE.md +13 -0
  213. package/rules/nestjs/error-handling/references/exception-filters.md +152 -0
  214. package/rules/nestjs/file-uploads/SKILL.md +35 -0
  215. package/rules/nestjs/file-uploads/references/REFERENCE.md +13 -0
  216. package/rules/nestjs/file-uploads/references/upload-patterns.md +125 -0
  217. package/rules/nestjs/observability/SKILL.md +39 -0
  218. package/rules/nestjs/observability/references/REFERENCE.md +13 -0
  219. package/rules/nestjs/observability/references/logging-metrics.md +175 -0
  220. package/rules/nestjs/performance/SKILL.md +60 -0
  221. package/rules/nestjs/performance/references/REFERENCE.md +13 -0
  222. package/rules/nestjs/performance/references/performance-patterns.md +107 -0
  223. package/rules/nestjs/real-time/SKILL.md +45 -0
  224. package/rules/nestjs/real-time/references/REFERENCE.md +13 -0
  225. package/rules/nestjs/real-time/references/websocket-patterns.md +121 -0
  226. package/rules/nestjs/scheduling/SKILL.md +39 -0
  227. package/rules/nestjs/scheduling/references/REFERENCE.md +13 -0
  228. package/rules/nestjs/scheduling/references/scheduling-patterns.md +137 -0
  229. package/rules/nestjs/search/SKILL.md +41 -0
  230. package/rules/nestjs/search/references/REFERENCE.md +13 -0
  231. package/rules/nestjs/search/references/search-patterns.md +137 -0
  232. package/rules/nestjs/security/SKILL.md +87 -0
  233. package/rules/nestjs/security/references/REFERENCE.md +14 -0
  234. package/rules/nestjs/security/references/authentication.md +151 -0
  235. package/rules/nestjs/testing/SKILL.md +40 -0
  236. package/rules/nestjs/testing/references/REFERENCE.md +14 -0
  237. package/rules/nestjs/testing/references/unit-testing.md +179 -0
  238. package/rules/nestjs/transport/SKILL.md +45 -0
  239. package/rules/nestjs/transport/references/REFERENCE.md +13 -0
  240. package/rules/nestjs/transport/references/microservices-patterns.md +170 -0
  241. package/rules/nextjs/app-router/SKILL.md +46 -0
  242. package/rules/nextjs/app-router/references/REFERENCE.md +14 -0
  243. package/rules/nextjs/app-router/references/routing-patterns.md +182 -0
  244. package/rules/nextjs/architecture/SKILL.md +44 -0
  245. package/rules/nextjs/architecture/references/fsd-structure.md +77 -0
  246. package/rules/nextjs/authentication/SKILL.md +29 -0
  247. package/rules/nextjs/authentication/references/auth-implementation.md +73 -0
  248. package/rules/nextjs/caching/SKILL.md +66 -0
  249. package/rules/nextjs/caching/references/REFERENCE.md +13 -0
  250. package/rules/nextjs/caching/references/cache-strategies.md +168 -0
  251. package/rules/nextjs/data-access-layer/SKILL.md +33 -0
  252. package/rules/nextjs/data-access-layer/references/patterns.md +66 -0
  253. package/rules/nextjs/data-fetching/SKILL.md +59 -0
  254. package/rules/nextjs/data-fetching/references/REFERENCE.md +13 -0
  255. package/rules/nextjs/data-fetching/references/fetch-patterns.md +160 -0
  256. package/rules/nextjs/internationalization/SKILL.md +105 -0
  257. package/rules/nextjs/internationalization/references/REFERENCE.md +13 -0
  258. package/rules/nextjs/internationalization/references/i18n-patterns.md +180 -0
  259. package/rules/nextjs/optimization/SKILL.md +64 -0
  260. package/rules/nextjs/optimization/references/REFERENCE.md +13 -0
  261. package/rules/nextjs/optimization/references/optimization-patterns.md +190 -0
  262. package/rules/nextjs/rendering/SKILL.md +91 -0
  263. package/rules/nextjs/rendering/references/REFERENCE.md +13 -0
  264. package/rules/nextjs/rendering/references/rendering-modes.md +163 -0
  265. package/rules/nextjs/server-actions/SKILL.md +46 -0
  266. package/rules/nextjs/server-actions/references/REFERENCE.md +13 -0
  267. package/rules/nextjs/server-actions/references/action-patterns.md +188 -0
  268. package/rules/nextjs/server-components/SKILL.md +52 -0
  269. package/rules/nextjs/server-components/references/REFERENCE.md +13 -0
  270. package/rules/nextjs/server-components/references/component-patterns.md +175 -0
  271. package/rules/nextjs/state-management/SKILL.md +73 -0
  272. package/rules/nextjs/state-management/references/REFERENCE.md +13 -0
  273. package/rules/nextjs/state-management/references/state-patterns.md +218 -0
  274. package/rules/nextjs/styling/SKILL.md +31 -0
  275. package/rules/nextjs/styling/references/implementation.md +56 -0
  276. package/rules/react/component-patterns/SKILL.md +66 -0
  277. package/rules/react/component-patterns/references/REFERENCE.md +126 -0
  278. package/rules/react/hooks/SKILL.md +60 -0
  279. package/rules/react/hooks/references/REFERENCE.md +132 -0
  280. package/rules/react/hooks.rule.md +79 -0
  281. package/rules/react/performance/SKILL.md +69 -0
  282. package/rules/react/performance/references/REFERENCE.md +143 -0
  283. package/rules/react/security/SKILL.md +46 -0
  284. package/rules/react/security/references/REFERENCE.md +170 -0
  285. package/rules/react/state-management/SKILL.md +56 -0
  286. package/rules/react/state-management/references/REFERENCE.md +137 -0
  287. package/rules/react/testing/SKILL.md +45 -0
  288. package/rules/react/testing/references/REFERENCE.md +149 -0
  289. package/rules/react/tooling/SKILL.md +39 -0
  290. package/rules/react/typescript/SKILL.md +53 -0
  291. package/rules/rust/actix-web/SKILL.md +160 -0
  292. package/rules/rust/actix-web/references/REFERENCE.md +13 -0
  293. package/rules/rust/actix-web/references/handler-patterns.md +198 -0
  294. package/rules/rust/async-graphql/SKILL.md +228 -0
  295. package/rules/rust/async-graphql/references/REFERENCE.md +13 -0
  296. package/rules/rust/async-graphql/references/schema-patterns.md +215 -0
  297. package/rules/rust/axum/SKILL.md +161 -0
  298. package/rules/rust/axum/references/REFERENCE.md +14 -0
  299. package/rules/rust/axum/references/handler-patterns.md +97 -0
  300. package/rules/rust/bevy/SKILL.md +206 -0
  301. package/rules/rust/bevy/references/REFERENCE.md +13 -0
  302. package/rules/rust/bevy/references/ecs-patterns.md +226 -0
  303. package/rules/rust/clap/SKILL.md +217 -0
  304. package/rules/rust/clap/references/REFERENCE.md +13 -0
  305. package/rules/rust/clap/references/derive-patterns.md +205 -0
  306. package/rules/rust/core/SKILL.md +154 -0
  307. package/rules/rust/core/references/REFERENCE.md +14 -0
  308. package/rules/rust/core/references/error-handling.md +92 -0
  309. package/rules/rust/diesel-orm/SKILL.md +176 -0
  310. package/rules/rust/diesel-orm/references/REFERENCE.md +13 -0
  311. package/rules/rust/diesel-orm/references/schema-patterns.md +206 -0
  312. package/rules/rust/rocket/SKILL.md +182 -0
  313. package/rules/rust/rocket/references/REFERENCE.md +13 -0
  314. package/rules/rust/rocket/references/handler-patterns.md +209 -0
  315. package/rules/rust/sea-orm/SKILL.md +230 -0
  316. package/rules/rust/sea-orm/references/REFERENCE.md +13 -0
  317. package/rules/rust/sea-orm/references/entity-patterns.md +221 -0
  318. package/rules/rust/serde-serialization/SKILL.md +150 -0
  319. package/rules/rust/serde-serialization/references/REFERENCE.md +13 -0
  320. package/rules/rust/serde-serialization/references/serialization-patterns.md +199 -0
  321. package/rules/rust/sqlx-database/SKILL.md +140 -0
  322. package/rules/rust/sqlx-database/references/REFERENCE.md +13 -0
  323. package/rules/rust/sqlx-database/references/query-patterns.md +210 -0
  324. package/rules/rust/tauri/SKILL.md +180 -0
  325. package/rules/rust/tauri/references/REFERENCE.md +13 -0
  326. package/rules/rust/tauri/references/command-patterns.md +209 -0
  327. package/rules/rust/tokio-runtime/SKILL.md +167 -0
  328. package/rules/rust/tokio-runtime/references/REFERENCE.md +14 -0
  329. package/rules/rust/tokio-runtime/references/async-patterns.md +137 -0
  330. package/rules/rust/tokio-runtime/references/synchronization.md +152 -0
  331. package/rules/rust/tonic/SKILL.md +231 -0
  332. package/rules/rust/tonic/references/REFERENCE.md +13 -0
  333. package/rules/rust/tonic/references/service-patterns.md +213 -0
  334. package/rules/rust/tracing/SKILL.md +214 -0
  335. package/rules/rust/tracing/references/REFERENCE.md +13 -0
  336. package/rules/rust/tracing/references/instrumentation.md +187 -0
  337. package/rules/typescript/best-practices/SKILL.md +108 -0
  338. package/rules/typescript/best-practices/references/REFERENCE.md +68 -0
  339. package/rules/typescript/language/SKILL.md +72 -0
  340. package/rules/typescript/language/references/REFERENCE.md +67 -0
  341. package/rules/typescript/patterns.rule.md +85 -0
  342. package/rules/typescript/security/SKILL.md +59 -0
  343. package/rules/typescript/security/references/REFERENCE.md +113 -0
  344. package/rules/typescript/tooling/SKILL.md +52 -0
  345. package/rules/typescript/tooling/references/REFERENCE.md +110 -0
@@ -0,0 +1,48 @@
1
+ # Localization Reference
2
+
3
+ ## Easy Localization Setup
4
+
5
+ Basic implementation in `main.dart`.
6
+
7
+ ```dart
8
+ Future<void> main() async {
9
+ WidgetsFlutterBinding.ensureInitialized();
10
+ await EasyLocalization.ensureInitialized();
11
+
12
+ runApp(
13
+ EasyLocalization(
14
+ supportedLocales: const [Locale('en'), Locale('vi')],
15
+ path: 'assets/translations', // <-- Path to translations
16
+ fallbackLocale: const Locale('en'),
17
+ child: const MyApp(),
18
+ ),
19
+ );
20
+ }
21
+ ```
22
+
23
+ ## JSON Translation Format
24
+
25
+ Default format for project assets.
26
+
27
+ ```json
28
+ // en.json
29
+ {
30
+ "app_title": "My App",
31
+ "welcome": "Welcome, {}!",
32
+ "items_count": {
33
+ "zero": "No items",
34
+ "one": "{} item",
35
+ "other": "{} items"
36
+ }
37
+ }
38
+ ```
39
+
40
+ ## Google Sheets Integration
41
+
42
+ Use `sheet_loader_localization` to fetch and generate localizations from Google Sheets.
43
+
44
+ 1. Add to `pubspec.yaml` under `dev_dependencies`.
45
+ 2. Configure sheets URL/ID in `pubspec.yaml` or separate config.
46
+ 3. Run `flutter pub run sheet_loader_localization:main`.
47
+
48
+ See [Sheet Loader Example](sheet-loader.md).
@@ -0,0 +1,33 @@
1
+ # Google Sheets Localization Loader
2
+
3
+ Automating translation updates from Google Sheets using `sheet_loader_localization`.
4
+
5
+ ## Configuration (`pubspec.yaml`)
6
+
7
+ ```yaml
8
+ dev_dependencies:
9
+ sheet_loader_localization: ^0.1.0
10
+
11
+ sheet_loader_localization:
12
+ # Google Sheet ID (find in the URL of your sheet)
13
+ doc_id: 'your_google_sheet_id_here'
14
+ sheet_id: '0' # Usually 0 for first sheet
15
+ output_path: 'assets/translations'
16
+ output_format: 'json' # Can be csv or json
17
+ ```
18
+
19
+ ## Typical Sheet Format ([example sheet](https://docs.google.com/spreadsheets/d/1v2Y3e0Uvn0JTwHvsduNT70u7Fy9TG43DIcZYJxPu1ZA/edit?gid=1013756643#gid=1013756643))
20
+
21
+ | key | en | vi |
22
+ | :------------- | :------------ | :--------- |
23
+ | welcome | Welcome! | Chào mừng! |
24
+ | login.button | Login | Đăng nhập |
25
+ | errors.network | Network Error | Lỗi mạng |
26
+
27
+ ## CLI Command
28
+
29
+ Run this command to synchronize your local asset files with the Google Sheet:
30
+
31
+ ```bash
32
+ flutter pub run sheet_loader_localization:main
33
+ ```
@@ -0,0 +1,71 @@
1
+ ---
2
+ name: Flutter Navigator v1 (Imperative)
3
+ description: Standard Flutter navigation using Navigator 1.0 (push/pop).
4
+ metadata:
5
+ labels: [navigation, navigator, flutter-core]
6
+ triggers:
7
+ files: ['**/app.dart']
8
+ keywords: [Navigator, push, pop, MaterialPageRoute, onGenerateRoute]
9
+ ---
10
+
11
+ # Navigator v1 Navigation
12
+
13
+ ## **Priority: P0 (CRITICAL)**
14
+
15
+ Standard imperative navigation system built into Flutter using `Navigator` and `MaterialPageRoute`.
16
+
17
+ ## Implementation Guidelines
18
+
19
+ - **Standard Push**: Use `Navigator.of(context).push(MaterialPageRoute(builder: (_) => Screen()))`.
20
+ - **Named Routes**: Define `routes` map in `MaterialApp` or use `onGenerateRoute` for dynamic routing.
21
+ - **Passing Arguments**:
22
+ - For named routes: Use `Navigator.pushNamed(context, '/path', arguments: data)`.
23
+ - For `onGenerateRoute`: Extract arguments using `settings.arguments`.
24
+ - **Returning Data**: `final result = await Navigator.push(...)` and `Navigator.pop(context, data)`.
25
+ - **Replacing Screens**: Use `pushReplacement` or `pushAndRemoveUntil` for auth/splash flows.
26
+
27
+ ## Code Example
28
+
29
+ ```dart
30
+ // Basic Push
31
+ Navigator.push(
32
+ context,
33
+ MaterialPageRoute(builder: (context) => const DetailScreen()),
34
+ );
35
+
36
+ // Named Routes Configuration
37
+ MaterialApp(
38
+ initialRoute: '/',
39
+ onGenerateRoute: (settings) {
40
+ if (settings.name == '/details') {
41
+ final args = settings.arguments as Map;
42
+ return MaterialPageRoute(
43
+ builder: (context) => DetailScreen(id: args['id']),
44
+ );
45
+ }
46
+ return null;
47
+ },
48
+ );
49
+
50
+ // Navigation with Arguments
51
+ Navigator.pushNamed(
52
+ context,
53
+ '/details',
54
+ arguments: {'id': 123},
55
+ );
56
+ ```
57
+
58
+ ## Anti-Patterns
59
+
60
+ - **Deep Nesting**: Avoid anonymous routes for complex apps; use `onGenerateRoute`.
61
+ - **Manual String Paths**: Always use constants for route names.
62
+ - **Context Leaks**: Ensure `BuildContext` is valid when calling `Navigator.of(context)`. Use `ScaffoldMessenger` or global keys if navigation is needed outside `build`.
63
+
64
+ ## Reference & Examples
65
+
66
+ For centralized `onGenerateRoute` implementation:
67
+ See [references/on-generate-route.md](references/on-generate-route.md).
68
+
69
+ ## Related Topics
70
+
71
+ idiomatic-flutter | widgets
@@ -0,0 +1,48 @@
1
+ # Navigator v1: Centralized onGenerateRoute
2
+
3
+ Using an abstract class for route names and a centralized router for navigation logic.
4
+
5
+ ```dart
6
+ // route_names.dart
7
+ abstract class Routes {
8
+ static const home = '/';
9
+ static const details = '/details';
10
+ }
11
+
12
+ // app_router.dart
13
+ class AppRouter {
14
+ static Route<dynamic> onGenerateRoute(RouteSettings settings) {
15
+ switch (settings.name) {
16
+ case Routes.home:
17
+ return MaterialPageRoute(builder: (_) => const HomeScreen());
18
+
19
+ case Routes.details:
20
+ // Safe argument extraction
21
+ final args = settings.arguments;
22
+ if (args is int) {
23
+ return MaterialPageRoute(
24
+ builder: (_) => DetailScreen(id: args),
25
+ );
26
+ }
27
+ return _errorRoute();
28
+
29
+ default:
30
+ return _errorRoute();
31
+ }
32
+ }
33
+
34
+ static Route<dynamic> _errorRoute() {
35
+ return MaterialPageRoute(
36
+ builder: (_) => const Scaffold(body: Center(child: Text('Error'))),
37
+ );
38
+ }
39
+ }
40
+
41
+ // main.dart
42
+ MaterialApp(
43
+ onGenerateRoute: AppRouter.onGenerateRoute,
44
+ )
45
+
46
+ // Usage
47
+ Navigator.pushNamed(context, Routes.details, arguments: 42);
48
+ ```
@@ -0,0 +1,24 @@
1
+ ---
2
+ name: Flutter Performance
3
+ description: Optimization standards for rebuilds and memory.
4
+ metadata:
5
+ labels: [performance]
6
+ triggers:
7
+ files: ['lib/presentation/**', 'pubspec.yaml']
8
+ keywords: [const, buildWhen, ListView.builder, Isolate, RepaintBoundary]
9
+ ---
10
+
11
+ # Performance (P1)
12
+
13
+ - **Rebuilds**: Use `const` widgets and `buildWhen` / `select` for granular updates.
14
+ - **Lists**: Always use `ListView.builder` for item recycling.
15
+ - **Heavy Tasks**: Use `compute()` or `Isolates` for parsing/logic.
16
+ - **Repaints**: Use `RepaintBoundary` for complex animations. Use `debugRepaintRainbowEnabled` to debug.
17
+ - **Images**: Use `CachedNetworkImage` + `memCacheWidth`. `precachePicture` for SVGs.
18
+
19
+ ```dart
20
+ BlocBuilder<UserBloc, UserState>(
21
+ buildWhen: (p, c) => p.id != c.id,
22
+ builder: (context, state) => Text(state.name),
23
+ )
24
+ ```
@@ -0,0 +1,51 @@
1
+ ---
2
+ name: Flutter Networking (Retrofit & Dio)
3
+ description: HTTP networking standards using Dio and Retrofit with Auth interceptors.
4
+ metadata:
5
+ labels: [networking, retrofit, dio]
6
+ triggers:
7
+ files: ['**/data_sources/**', '**/api/**']
8
+ keywords: [Retrofit, Dio, RestClient, GET, POST, Interceptor, refreshing]
9
+ ---
10
+
11
+ # Retrofit & Dio Networking
12
+
13
+ ## **Priority: P0 (CRITICAL)**
14
+
15
+ Type-safe REST API communication using `Dio` and `Retrofit`.
16
+
17
+ ## Structure
18
+
19
+ ```text
20
+ infrastructure/
21
+ ├── data_sources/
22
+ │ ├── remote/ # Retrofit abstract classes
23
+ │ └── local/ # Cache/Storage
24
+ └── network/
25
+ ├── dio_client.dart # Custom Dio setup
26
+ └── interceptors/ # Auth, Logging, Cache
27
+ ```
28
+
29
+ ## Implementation Guidelines
30
+
31
+ - **Retrofit Clients**: Define abstract classes with `@RestApi()`. Use standard HTTP annotations (`@GET`, `@POST`).
32
+ - **DTOs (Data Transfer Objects)**: Use `@freezed` and `json_serializable` for all response/request bodies.
33
+ - **Mapping**: Data sources MUST map DTOs to Domain Entities (e.g., `userDto.toDomain()`).
34
+ - **AuthInterceptor**: Logic for `Authorization: Bearer <token>` injection in `onRequest`.
35
+ - **Token Refresh**: Handle `401 Unauthorized` in `onError` by locking Dio, refreshing, and retrying.
36
+ - **Failures**: Map `DioException` to custom `Failure` objects (ServerFailure, NetworkFailure).
37
+
38
+ ## Anti-Patterns
39
+
40
+ - **No Manual JSON Parsing**: Do not use `jsonDecode(response.body)`; use Retrofit's generated mappers.
41
+ - **No Global Dio**: Do not use a static global Dio instance; use dependency injection.
42
+ - **No Try-Catch in API**: Do not put `try-catch` inside the Retrofit interface methods.
43
+
44
+ ## Reference & Examples
45
+
46
+ For RestClient definitions and Auth Interceptor implementation:
47
+ See [references/REFERENCE.md](references/REFERENCE.md).
48
+
49
+ ## Related Topics
50
+
51
+ feature-based-clean-architecture | error-handling
@@ -0,0 +1,19 @@
1
+ # Retrofit & Dio Reference
2
+
3
+ Standards for API communication and networking logic.
4
+
5
+ ## References
6
+
7
+ - [**RestClient Setup**](client-definition.md) - Standard Retrofit interface examples.
8
+ - [**Auth Interceptors**](auth-interceptor.md) - Handling Bearer tokens and Auth headers.
9
+ - [**Token Refresh Logic**](token-refresh.md) - The 401 Lock-Refresh-Retry pattern.
10
+
11
+ ## **Quick Definition**
12
+
13
+ ```dart
14
+ @RestApi()
15
+ abstract class ApiClient {
16
+ @GET("/items")
17
+ Future<List<ItemDto>> getItems(@Query("limit") int limit);
18
+ }
19
+ ```
@@ -0,0 +1,40 @@
1
+ # Token Refresh Pattern
2
+
3
+ When a `401 Unauthorized` error occurs, the networking layer should handle the refresh cycle transparently.
4
+
5
+ ## **Implementation Flow (Dio Interceptor)**
6
+
7
+ ```dart
8
+ class AuthInterceptor extends QueuedInterceptorsWrapper {
9
+ final Dio dio;
10
+ final SecureStorage storage;
11
+
12
+ AuthInterceptor(this.dio, this.storage);
13
+
14
+ @override
15
+ void onError(DioException err, ErrorInterceptorHandler handler) async {
16
+ if (err.response?.statusCode == 401) {
17
+ // 1. Refresh the token
18
+ final newToken = await _performRefresh();
19
+
20
+ if (newToken != null) {
21
+ // 2. Retry the original request with new token
22
+ final options = err.requestOptions;
23
+ options.headers['Authorization'] = 'Bearer $newToken';
24
+
25
+ final response = await dio.fetch(options);
26
+ return handler.resolve(response);
27
+ }
28
+ }
29
+ return handler.next(err);
30
+ }
31
+
32
+ Future<String?> _performRefresh() async {
33
+ // Logic to call refresh endpoint and update storage
34
+ }
35
+ }
36
+ ```
37
+
38
+ ## **Why QueuedInterceptorsWrapper?**
39
+
40
+ Using `QueuedInterceptorsWrapper` ensures that if multiple requests trigger a 401 at the same time, they are queued while the first one performs the token refresh, preventing multiple redundant refresh calls.
@@ -0,0 +1,53 @@
1
+ ---
2
+ name: Flutter Riverpod State Management
3
+ description: Reactive state management using Riverpod 2.0 with code generation.
4
+ metadata:
5
+ labels: [state-management, riverpod, dependency-injection, reactive]
6
+ triggers:
7
+ files: ['**_provider.dart', '**_notifier.dart']
8
+ keywords: [riverpod, ProviderScope, ConsumerWidget, Notifier, AsyncValue, ref.watch, "@riverpod"]
9
+ ---
10
+
11
+ # Riverpod State Management
12
+
13
+ ## **Priority: P0 (CRITICAL)**
14
+
15
+ Type-safe, compile-time safe reactive state management using `riverpod` and `riverpod_generator`.
16
+
17
+ ## Structure
18
+
19
+ ```text
20
+ lib/
21
+ ├── providers/ # Global providers and services
22
+ └── features/
23
+ └── user/
24
+ ├── providers/ # Feature-specific providers
25
+ └── models/ # @freezed domain models
26
+ ```
27
+
28
+ ## Implementation Guidelines
29
+
30
+ - **Generator First**: Use `@riverpod` annotations and `riverpod_generator`. Avoid manual `Provider` definitions.
31
+ - **Immutability**: Maintain immutable states. Use `Freezed` for all state models.
32
+ - **Provider Methods**:
33
+ - `ref.watch()`: Use inside `build()` to rebuild on changes.
34
+ - `ref.listen()`: Use for side-effects (navigation, dialogs).
35
+ - `ref.read()`: Use ONLY in callbacks (onPressed).
36
+ - **Asynchronous Data**: Use `AsyncNotifier` for complex async logic. Access data via `.when()` or `AsyncValue` pattern-matching.
37
+ - **Architecture**: Enforce 3-layer separation (Data, Domain, Presentation).
38
+ - **Linting**: Enable `riverpod_lint` and `custom_lint` for dependency cycle detection.
39
+
40
+ ## Anti-Patterns
41
+
42
+ - **Building Inside Providers**: Don't perform side-effects inside provider initialization.
43
+ - **Context Access**: Never pass `BuildContext` into a Notifier/Provider.
44
+ - **Dynamic Providers**: Avoid local provider instantiation; keep them global.
45
+
46
+ ## Reference & Examples
47
+
48
+ For architecture details, best practices, and testing overrides:
49
+ See [references/architecture.md](references/architecture.md), [references/best-practices.md](references/best-practices.md), and [references/testing.md](references/testing.md).
50
+
51
+ ## Related Topics
52
+
53
+ feature-based-clean-architecture | dependency-injection | testing
@@ -0,0 +1,124 @@
1
+ # Architecture & Layers
2
+
3
+ ## 1. Data Layer: Repository Interface & Providers
4
+
5
+ Always separate interface from implementation to enable easy mocking.
6
+
7
+ ```dart
8
+ // domain/repository/user_repository.dart
9
+ import 'package:riverpod_annotation/riverpod_annotation.dart';
10
+ import '../../data/repository/api_user_repository.dart';
11
+ import '../models/user.dart';
12
+
13
+ part 'user_repository.g.dart';
14
+
15
+ // 1. Define the Provider returning the INTERFACE
16
+ @riverpod
17
+ UserRepository userRepository(UserRepositoryRef ref) {
18
+ // Return the specific implementation here.
19
+ // Can be swapped for MockUserRepository based on environment flags.
20
+ return ApiUserRepository(ref.watch(apiClientProvider));
21
+ }
22
+
23
+ // 2. Define the Interface
24
+ abstract interface class UserRepository {
25
+ Future<List<User>> getAllUsers();
26
+ Future<void> deleteUser(String id);
27
+ }
28
+ ```
29
+
30
+ ```dart
31
+ // data/repository/api_user_repository.dart
32
+ class ApiUserRepository implements UserRepository {
33
+ final UserApiClient _client;
34
+
35
+ ApiUserRepository(this._client);
36
+
37
+ @override
38
+ Future<List<User>> getAllUsers() async {
39
+ return _client.fetchUsers();
40
+ }
41
+ }
42
+ ```
43
+
44
+ ## 2. Presentation Layer: AsyncNotifier Controller
45
+
46
+ Use `AsyncNotifier` (via `@riverpod` class) to handle loading/error/data states naturally.
47
+
48
+ ```dart
49
+ // features/users/user_controller.dart
50
+ import 'package:riverpod_annotation/riverpod_annotation.dart';
51
+ import '../../domain/repository/user_repository.dart';
52
+ import '../../domain/models/user.dart';
53
+
54
+ part 'user_controller.g.dart';
55
+
56
+ @riverpod
57
+ class UserController extends _$UserController {
58
+ @override
59
+ FutureOr<List<User>> build() async {
60
+ // 1. Fetch initial data
61
+ return ref.watch(userRepositoryProvider).getAllUsers();
62
+ }
63
+
64
+ // 2. Mutation Methods
65
+ Future<void> deleteUser(String id) async {
66
+ // Set loading state (optional, for optimisic UI usually prefer local)
67
+ // state = const AsyncLoading();
68
+
69
+ // Perform action
70
+ state = await AsyncValue.guard(() async {
71
+ await ref.read(userRepositoryProvider).deleteUser(id);
72
+ // Refresh logic:
73
+ // Option A: Refetch everything
74
+ return ref.refresh(userRepositoryProvider).getAllUsers();
75
+
76
+ // Option B: Optimistic Update (Better performance)
77
+ // final currentList = state.requireValue;
78
+ // return currentList.where((u) => u.id != id).toList();
79
+ });
80
+ }
81
+ }
82
+ ```
83
+
84
+ ## 3. UI Layer: ConsumerWidget
85
+
86
+ Handle all 3 states (`data`, `loading`, `error`) using `.when`.
87
+
88
+ ```dart
89
+ // features/users/user_list_screen.dart
90
+ import 'package:flutter_riverpod/flutter_riverpod.dart';
91
+
92
+ class UserListScreen extends ConsumerWidget {
93
+ const UserListScreen({super.key});
94
+
95
+ @override
96
+ Widget build(BuildContext context, WidgetRef ref) {
97
+ // 1. Watch the Notifier Provider
98
+ final state = ref.watch(userControllerProvider);
99
+
100
+ return Scaffold(
101
+ body: state.when(
102
+ data: (users) => ListView.builder(
103
+ itemCount: users.length,
104
+ itemBuilder: (ctx, index) {
105
+ final user = users[index];
106
+ return ListTile(
107
+ title: Text(user.name),
108
+ // 2. Call mutation methods via .read()
109
+ trailing: IconButton(
110
+ icon: const Icon(Icons.delete),
111
+ onPressed: () {
112
+ ref.read(userControllerProvider.notifier).deleteUser(user.id);
113
+ },
114
+ ),
115
+ );
116
+ },
117
+ ),
118
+ loading: () => const Center(child: CircularProgressIndicator()),
119
+ error: (err, st) => Center(child: Text('Error: $err')),
120
+ ),
121
+ );
122
+ }
123
+ }
124
+ ```
@@ -0,0 +1,89 @@
1
+ # Best Practices & DCM Rules
2
+
3
+ ## Code Generation (`riverpod_generator`)
4
+
5
+ Always use code generation. It prevents syntax errors and handles "family" parameters automatically.
6
+
7
+ **❌ Bad (Legacy)**
8
+
9
+ ```dart
10
+ final myProvider = Provider<String>((ref) => 'Hello'); // Manual typing, error prone
11
+ ```
12
+
13
+ **✅ Good (Generated)**
14
+
15
+ ```dart
16
+ @riverpod
17
+ String my(MyRef ref) => 'Hello'; // Type-safe, auto-disposal by default
18
+ ```
19
+
20
+ ## Immutability & State Updates
21
+
22
+ Riverpod relies on strict object equality (`==`) to detect changes.
23
+
24
+ **❌ Bad (Mutation)**
25
+
26
+ ```dart
27
+ state.add(newItem); // Same reference, listeners won't fire
28
+ state = state;
29
+ ```
30
+
31
+ **✅ Good (New Reference)**
32
+
33
+ ```dart
34
+ state = [...state, newItem]; // New list, new reference
35
+ ```
36
+
37
+ ## DCM & Linter Rules (`riverpod_lint`)
38
+
39
+ Enable strict rules in `analysis_options.yaml` via `custom_lint`.
40
+
41
+ ### 1. `avoid-ref-read-inside-build`
42
+
43
+ **Rule**: Never use `ref.read` inside the `build()` method. It causes bugs where widgets don't update on change.
44
+ **Correct**: Use `ref.watch`.
45
+
46
+ ### 2. `avoid-calling-notifier-members-inside-build`
47
+
48
+ **Rule**: Do not trigger side effects (API calls, internal mutations) inside `build`.
49
+ **Correct**: Use `build()` purely for initialization. Trigger actions via user interaction (onPressed) or `useEffect` (flutter_hooks).
50
+
51
+ ### 3. `dispose-provided-instances`
52
+
53
+ **Rule**: If a provider creates a `ChangeNotifier` or stream controller, make sure it is disposed.
54
+ **Correct**:
55
+
56
+ ```dart
57
+ @riverpod
58
+ StreamController myController(Ref ref) {
59
+ final controller = StreamController();
60
+ ref.onDispose(controller.close); // ✅ Register disposal
61
+ return controller;
62
+ }
63
+ ```
64
+
65
+ ### 4. `use-ref-and-state-synchronously`
66
+
67
+ **Rule**: Don't use `ref` or setter `state` after an `await` without checking if the provider is still active.
68
+ **Context**: If a provider is disposed (e.g. user leaves screen) while an async task is running, setting state will throw.
69
+
70
+ **✅ Good**:
71
+
72
+ ```dart
73
+ final result = await repo.fetch();
74
+ if (ref.context.mounted) { // Or simply rely on `AsyncValue.guard` which handles this somewhat safely
75
+ state = AsyncData(result);
76
+ }
77
+ ```
78
+
79
+ ## `keepAlive` Strategy
80
+
81
+ By default, auto-generated providers are `autoDispose`. This is good for memory but bad for caching.
82
+
83
+ - **Use `keepAlive: true`** for global data (User Session, App Config).
84
+ - **Use Default (`keepAlive: false`)** for screen-specific data (Product Details), so it clears to save memory when the screen is popped.
85
+
86
+ ```dart
87
+ @Riverpod(keepAlive: true)
88
+ class UserSession extends _$UserSession { ... }
89
+ ```
@@ -0,0 +1,73 @@
1
+ # Testing with Riverpod
2
+
3
+ Riverpod is designed for testability. You do not need complex dependency injection containers; you simply "override" providers in the test scope.
4
+
5
+ ## Unit Testing (Notifiers)
6
+
7
+ Test notifiers in isolation using a `ProviderContainer`.
8
+
9
+ ```dart
10
+ test('increment adds 1 to state', () {
11
+ // 1. Create container
12
+ final container = ProviderContainer();
13
+ addTearDown(container.dispose);
14
+
15
+ // 2. Listen to provider (required to initialize it)
16
+ container.listen(counterProvider, (_, __) {});
17
+
18
+ // 3. Act
19
+ container.read(counterProvider.notifier).increment();
20
+
21
+ // 4. Assert
22
+ expect(container.read(counterProvider), 1);
23
+ });
24
+ ```
25
+
26
+ ## Widget/Integration Testing (Overrides)
27
+
28
+ When testing widgets, wrap them in a `ProviderScope` and override the repository providers with mocks.
29
+
30
+ ```dart
31
+ testWidgets('shows loading then data', (tester) async {
32
+ final mockRepo = MockUserRepository();
33
+ when(() => mockRepo.getAllUsers()).thenAnswer((_) async => [User(id: 1, name: 'Bob')]);
34
+
35
+ await tester.pumpWidget(
36
+ ProviderScope(
37
+ overrides: [
38
+ // 🔑 Replace the REAL repository with the MOCK
39
+ userRepositoryProvider.overrideWithValue(mockRepo),
40
+ ],
41
+ child: const MaterialApp(home: UserListScreen()),
42
+ ),
43
+ );
44
+
45
+ // Assert Loading
46
+ expect(find.byType(CircularProgressIndicator), findsOneWidget);
47
+
48
+ // Assert Data
49
+ await tester.pumpAndSettle();
50
+ expect(find.text('Bob'), findsOneWidget);
51
+ });
52
+ ```
53
+
54
+ ## Mocking `AsyncNotifiers`
55
+
56
+ Sometimes you want to mock the _entire_ Controller/Notifier state, not just the repository.
57
+
58
+ ```dart
59
+ // 1. Extend the generated class (or create a mock)
60
+ class MockUserController extends AutoDisposeAsyncNotifier<List<User>>
61
+ implements UserController {
62
+ @override
63
+ FutureOr<List<User>> build() => [];
64
+ }
65
+
66
+ // 2. Override in ProviderScope
67
+ ProviderScope(
68
+ overrides: [
69
+ userControllerProvider.overrideWith(() => MockUserController()),
70
+ ],
71
+ child: ...
72
+ )
73
+ ```