@mmerterden/multi-agent-pipeline 20.6.0 → 20.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (326) hide show
  1. package/CHANGELOG.md +27 -0
  2. package/LICENSE +0 -10
  3. package/docs/facts.json +1 -1
  4. package/manifest.json +328 -329
  5. package/package.json +2 -2
  6. package/pipeline/multi-agent-refs/features/design-conformance.md +62 -64
  7. package/pipeline/scripts/_notices.mjs +12 -1
  8. package/pipeline/scripts/gen-skills-index.mjs +1 -1
  9. package/pipeline/skills/.skill-manifest.json +106 -106
  10. package/pipeline/skills/shared/README.md +71 -71
  11. package/pipeline/skills/shared/external/agent-introspection-debugging/SKILL.md +1 -0
  12. package/pipeline/skills/shared/external/alarmkit/SKILL.md +373 -381
  13. package/pipeline/skills/shared/external/alarmkit/evals/evals.json +23 -18
  14. package/pipeline/skills/shared/external/alarmkit/references/alarmkit-patterns.md +328 -378
  15. package/pipeline/skills/shared/external/android-architecture/SKILL.md +2 -0
  16. package/pipeline/skills/shared/external/android-performance/SKILL.md +2 -0
  17. package/pipeline/skills/shared/external/android-security/SKILL.md +2 -0
  18. package/pipeline/skills/shared/external/app-clips/SKILL.md +260 -160
  19. package/pipeline/skills/shared/external/app-clips/evals/evals.json +27 -27
  20. package/pipeline/skills/shared/external/app-clips/references/data-handoff-notifications-location.md +150 -83
  21. package/pipeline/skills/shared/external/app-clips/references/routing-and-experiences.md +135 -83
  22. package/pipeline/skills/shared/external/app-clips/references/size-capabilities-and-promotion.md +143 -85
  23. package/pipeline/skills/shared/external/app-intents/SKILL.md +302 -304
  24. package/pipeline/skills/shared/external/app-intents/evals/evals.json +21 -21
  25. package/pipeline/skills/shared/external/app-intents/references/appintents-advanced.md +594 -894
  26. package/pipeline/skills/shared/external/app-store-optimization/SKILL.md +339 -277
  27. package/pipeline/skills/shared/external/app-store-optimization/evals/evals.json +27 -23
  28. package/pipeline/skills/shared/external/app-store-optimization/references/keyword-research-methodology.md +105 -122
  29. package/pipeline/skills/shared/external/app-store-optimization/references/product-page-variants.md +143 -166
  30. package/pipeline/skills/shared/external/app-store-review/SKILL.md +307 -326
  31. package/pipeline/skills/shared/external/app-store-review/evals/evals.json +21 -21
  32. package/pipeline/skills/shared/external/app-store-review/references/privacy-manifest.md +105 -67
  33. package/pipeline/skills/shared/external/app-store-review/references/review-checklists.md +114 -101
  34. package/pipeline/skills/shared/external/apple-on-device-ai/SKILL.md +333 -360
  35. package/pipeline/skills/shared/external/apple-on-device-ai/evals/evals.json +24 -27
  36. package/pipeline/skills/shared/external/apple-on-device-ai/references/coreml-conversion.md +215 -322
  37. package/pipeline/skills/shared/external/apple-on-device-ai/references/coreml-optimization.md +161 -256
  38. package/pipeline/skills/shared/external/apple-on-device-ai/references/foundation-models.md +277 -387
  39. package/pipeline/skills/shared/external/apple-on-device-ai/references/mlx-swift.md +196 -210
  40. package/pipeline/skills/shared/external/authentication/SKILL.md +265 -381
  41. package/pipeline/skills/shared/external/authentication/evals/evals.json +25 -25
  42. package/pipeline/skills/shared/external/authentication/references/keychain-biometric.md +133 -178
  43. package/pipeline/skills/shared/external/authentication/references/passkeys.md +111 -147
  44. package/pipeline/skills/shared/external/avkit/SKILL.md +267 -364
  45. package/pipeline/skills/shared/external/avkit/evals/evals.json +26 -26
  46. package/pipeline/skills/shared/external/avkit/references/avkit-patterns.md +375 -493
  47. package/pipeline/skills/shared/external/background-processing/SKILL.md +270 -382
  48. package/pipeline/skills/shared/external/background-processing/evals/evals.json +22 -22
  49. package/pipeline/skills/shared/external/background-processing/references/background-task-patterns.md +169 -317
  50. package/pipeline/skills/shared/external/backlog/BACKLOG.md +1 -1
  51. package/pipeline/skills/shared/external/backlog/SKILL.md +56 -33
  52. package/pipeline/skills/shared/external/callkit-voip/SKILL.md +290 -371
  53. package/pipeline/skills/shared/external/callkit-voip/evals/evals.json +24 -24
  54. package/pipeline/skills/shared/external/callkit-voip/references/callkit-patterns.md +175 -343
  55. package/pipeline/skills/shared/external/ci-cd-pipelines/SKILL.md +1 -0
  56. package/pipeline/skills/shared/external/cloudkit-sync/SKILL.md +292 -381
  57. package/pipeline/skills/shared/external/cloudkit-sync/evals/evals.json +33 -30
  58. package/pipeline/skills/shared/external/cloudkit-sync/references/cloudkit-patterns.md +227 -355
  59. package/pipeline/skills/shared/external/compose-components/SKILL.md +2 -0
  60. package/pipeline/skills/shared/external/compose-navigation/SKILL.md +3 -2
  61. package/pipeline/skills/shared/external/compose-testing/SKILL.md +2 -0
  62. package/pipeline/skills/shared/external/contacts-framework/SKILL.md +197 -346
  63. package/pipeline/skills/shared/external/contacts-framework/evals/evals.json +19 -21
  64. package/pipeline/skills/shared/external/contacts-framework/references/contacts-patterns.md +169 -308
  65. package/pipeline/skills/shared/external/core-bluetooth/SKILL.md +226 -376
  66. package/pipeline/skills/shared/external/core-bluetooth/evals/evals.json +25 -22
  67. package/pipeline/skills/shared/external/core-bluetooth/references/ble-patterns.md +257 -337
  68. package/pipeline/skills/shared/external/core-data/SKILL.md +292 -368
  69. package/pipeline/skills/shared/external/core-data/evals/evals.json +30 -27
  70. package/pipeline/skills/shared/external/core-motion/SKILL.md +235 -324
  71. package/pipeline/skills/shared/external/core-motion/evals/evals.json +31 -27
  72. package/pipeline/skills/shared/external/core-motion/references/motion-patterns.md +210 -310
  73. package/pipeline/skills/shared/external/core-nfc/SKILL.md +292 -366
  74. package/pipeline/skills/shared/external/core-nfc/evals/evals.json +22 -24
  75. package/pipeline/skills/shared/external/core-nfc/references/nfc-patterns.md +233 -329
  76. package/pipeline/skills/shared/external/coreml/SKILL.md +323 -367
  77. package/pipeline/skills/shared/external/coreml/evals/evals.json +24 -21
  78. package/pipeline/skills/shared/external/coreml/references/coreml-swift-integration.md +562 -565
  79. package/pipeline/skills/shared/external/council/SKILL.md +1 -0
  80. package/pipeline/skills/shared/external/cryptokit/SKILL.md +253 -394
  81. package/pipeline/skills/shared/external/cryptokit/evals/evals.json +20 -18
  82. package/pipeline/skills/shared/external/cryptokit/references/cryptokit-patterns.md +299 -488
  83. package/pipeline/skills/shared/external/css-modern/SKILL.md +1 -0
  84. package/pipeline/skills/shared/external/database-patterns/SKILL.md +1 -0
  85. package/pipeline/skills/shared/external/debugging-instruments/SKILL.md +270 -323
  86. package/pipeline/skills/shared/external/debugging-instruments/evals/evals.json +27 -30
  87. package/pipeline/skills/shared/external/debugging-instruments/references/instruments-guide.md +167 -315
  88. package/pipeline/skills/shared/external/debugging-instruments/references/lldb-patterns.md +140 -193
  89. package/pipeline/skills/shared/external/device-integrity/SKILL.md +230 -353
  90. package/pipeline/skills/shared/external/device-integrity/evals/evals.json +25 -21
  91. package/pipeline/skills/shared/external/device-integrity/references/device-integrity-patterns.md +159 -197
  92. package/pipeline/skills/shared/external/energykit/SKILL.md +225 -392
  93. package/pipeline/skills/shared/external/energykit/evals/evals.json +29 -28
  94. package/pipeline/skills/shared/external/energykit/references/energykit-patterns.md +174 -470
  95. package/pipeline/skills/shared/external/eventkit-calendar/SKILL.md +261 -383
  96. package/pipeline/skills/shared/external/eventkit-calendar/evals/evals.json +25 -22
  97. package/pipeline/skills/shared/external/eventkit-calendar/references/eventkit-patterns.md +165 -268
  98. package/pipeline/skills/shared/external/evidence-github/SKILL.md +2 -0
  99. package/pipeline/skills/shared/external/evidence-registry/SKILL.md +2 -0
  100. package/pipeline/skills/shared/external/gradle-kotlin-dsl/SKILL.md +2 -0
  101. package/pipeline/skills/shared/external/healthkit/SKILL.md +252 -303
  102. package/pipeline/skills/shared/external/healthkit/evals/evals.json +24 -23
  103. package/pipeline/skills/shared/external/healthkit/references/healthkit-patterns.md +369 -523
  104. package/pipeline/skills/shared/external/homekit-matter/SKILL.md +233 -348
  105. package/pipeline/skills/shared/external/homekit-matter/evals/evals.json +27 -22
  106. package/pipeline/skills/shared/external/homekit-matter/references/matter-commissioning.md +199 -305
  107. package/pipeline/skills/shared/external/html-semantic/SKILL.md +1 -0
  108. package/pipeline/skills/shared/external/humanizer/SKILL.md +1 -0
  109. package/pipeline/skills/shared/external/ios-accessibility/SKILL.md +368 -340
  110. package/pipeline/skills/shared/external/ios-accessibility/evals/evals.json +28 -27
  111. package/pipeline/skills/shared/external/ios-accessibility/references/a11y-patterns.md +314 -260
  112. package/pipeline/skills/shared/external/ios-accessibility/references/media-accessibility.md +97 -67
  113. package/pipeline/skills/shared/external/ios-accessibility/references/nutrition-labels.md +165 -101
  114. package/pipeline/skills/shared/external/ios-coding-standard/SKILL.md +1 -0
  115. package/pipeline/skills/shared/external/ios-localization/SKILL.md +258 -371
  116. package/pipeline/skills/shared/external/ios-localization/evals/evals.json +23 -23
  117. package/pipeline/skills/shared/external/ios-localization/references/formatstyle-locale.md +283 -491
  118. package/pipeline/skills/shared/external/ios-localization/references/string-catalogs.md +313 -440
  119. package/pipeline/skills/shared/external/ios-module-structure/SKILL.md +1 -0
  120. package/pipeline/skills/shared/external/ios-networking/SKILL.md +265 -341
  121. package/pipeline/skills/shared/external/ios-networking/evals/evals.json +24 -24
  122. package/pipeline/skills/shared/external/ios-networking/references/background-websocket.md +425 -652
  123. package/pipeline/skills/shared/external/ios-networking/references/file-storage-patterns.md +143 -285
  124. package/pipeline/skills/shared/external/ios-networking/references/lightweight-clients.md +93 -53
  125. package/pipeline/skills/shared/external/ios-networking/references/network-framework.md +231 -456
  126. package/pipeline/skills/shared/external/ios-networking/references/urlsession-patterns.md +517 -784
  127. package/pipeline/skills/shared/external/ios-security/SKILL.md +2 -0
  128. package/pipeline/skills/shared/external/ios-simulator/SKILL.md +265 -393
  129. package/pipeline/skills/shared/external/ios-simulator/evals/evals.json +21 -21
  130. package/pipeline/skills/shared/external/ios-simulator/references/simctl-commands.md +177 -270
  131. package/pipeline/skills/shared/external/live-activities/SKILL.md +318 -360
  132. package/pipeline/skills/shared/external/live-activities/evals/evals.json +21 -21
  133. package/pipeline/skills/shared/external/live-activities/references/activitykit-patterns.md +478 -710
  134. package/pipeline/skills/shared/external/localization-reuse-map/SKILL.md +91 -283
  135. package/pipeline/skills/shared/external/localization-reuse-map/reference/format-and-output.md +119 -151
  136. package/pipeline/skills/shared/external/localization-reuse-map/reference/publish-and-snapshot.md +60 -90
  137. package/pipeline/skills/shared/external/localization-reuse-map/reference/sources-and-recipes.md +119 -156
  138. package/pipeline/skills/shared/external/localization-reuse-map/scripts/build-artifact.py +726 -787
  139. package/pipeline/skills/shared/external/localization-reuse-map/scripts/build-spreadsheet.py +253 -288
  140. package/pipeline/skills/shared/external/localization-reuse-map/scripts/fetch-annotations.py +243 -304
  141. package/pipeline/skills/shared/external/localization-reuse-map/scripts/fetch-legacy-labels.py +88 -104
  142. package/pipeline/skills/shared/external/localization-reuse-map/scripts/publish-confluence.py +181 -235
  143. package/pipeline/skills/shared/external/localization-reuse-map/scripts/render-key-shots.py +198 -263
  144. package/pipeline/skills/shared/external/localization-reuse-map/scripts/render-overlay.py +461 -466
  145. package/pipeline/skills/shared/external/localization-reuse-map/scripts/resolve-legacy-values.py +145 -151
  146. package/pipeline/skills/shared/external/localization-reuse-map/scripts/resolve-new-values.py +123 -141
  147. package/pipeline/skills/shared/external/localization-reuse-map/scripts/scan-screen-keys.py +146 -157
  148. package/pipeline/skills/shared/external/localization-reuse-map/scripts/snapshot-resources.sh +22 -19
  149. package/pipeline/skills/shared/external/localization-reuse-map/scripts/verify-map.py +156 -140
  150. package/pipeline/skills/shared/external/mapkit-location/SKILL.md +295 -267
  151. package/pipeline/skills/shared/external/mapkit-location/evals/evals.json +28 -24
  152. package/pipeline/skills/shared/external/mapkit-location/references/mapkit-corelocation-patterns.md +378 -532
  153. package/pipeline/skills/shared/external/mapkit-location/references/mapkit-patterns.md +397 -499
  154. package/pipeline/skills/shared/external/metrickit-diagnostics/SKILL.md +165 -348
  155. package/pipeline/skills/shared/external/metrickit-diagnostics/evals/evals.json +26 -23
  156. package/pipeline/skills/shared/external/metrickit-diagnostics/references/metrickit-patterns.md +123 -130
  157. package/pipeline/skills/shared/external/musickit-audio/SKILL.md +189 -315
  158. package/pipeline/skills/shared/external/musickit-audio/evals/evals.json +22 -21
  159. package/pipeline/skills/shared/external/musickit-audio/references/musickit-patterns.md +181 -270
  160. package/pipeline/skills/shared/external/natural-language/SKILL.md +188 -340
  161. package/pipeline/skills/shared/external/natural-language/evals/evals.json +21 -21
  162. package/pipeline/skills/shared/external/natural-language/references/translation-patterns.md +171 -225
  163. package/pipeline/skills/shared/external/nextjs-app-router/SKILL.md +1 -0
  164. package/pipeline/skills/shared/external/passkit-wallet/SKILL.md +258 -392
  165. package/pipeline/skills/shared/external/passkit-wallet/evals/evals.json +30 -29
  166. package/pipeline/skills/shared/external/passkit-wallet/references/wallet-passes.md +164 -231
  167. package/pipeline/skills/shared/external/pdfkit/SKILL.md +312 -344
  168. package/pipeline/skills/shared/external/pdfkit/evals/evals.json +19 -19
  169. package/pipeline/skills/shared/external/pdfkit/references/pdfkit-patterns.md +413 -624
  170. package/pipeline/skills/shared/external/pencilkit-drawing/SKILL.md +242 -358
  171. package/pipeline/skills/shared/external/pencilkit-drawing/evals/evals.json +25 -21
  172. package/pipeline/skills/shared/external/pencilkit-drawing/references/pencilkit-patterns.md +161 -226
  173. package/pipeline/skills/shared/external/permissionkit/SKILL.md +282 -400
  174. package/pipeline/skills/shared/external/permissionkit/evals/evals.json +27 -30
  175. package/pipeline/skills/shared/external/permissionkit/references/permissionkit-patterns.md +237 -350
  176. package/pipeline/skills/shared/external/photos-camera-media/SKILL.md +276 -325
  177. package/pipeline/skills/shared/external/photos-camera-media/references/av-playback.md +299 -545
  178. package/pipeline/skills/shared/external/photos-camera-media/references/camera-capture.md +344 -588
  179. package/pipeline/skills/shared/external/photos-camera-media/references/image-loading-caching.md +316 -660
  180. package/pipeline/skills/shared/external/photos-camera-media/references/photokit-patterns.md +270 -416
  181. package/pipeline/skills/shared/external/play-store-review/SKILL.md +2 -0
  182. package/pipeline/skills/shared/external/push-notifications/SKILL.md +312 -340
  183. package/pipeline/skills/shared/external/push-notifications/evals/evals.json +27 -26
  184. package/pipeline/skills/shared/external/push-notifications/references/notification-patterns.md +328 -485
  185. package/pipeline/skills/shared/external/push-notifications/references/rich-notifications.md +327 -560
  186. package/pipeline/skills/shared/external/python-patterns/SKILL.md +1 -0
  187. package/pipeline/skills/shared/external/react-best-practices/SKILL.md +1 -0
  188. package/pipeline/skills/shared/external/realitykit-ar/SKILL.md +218 -410
  189. package/pipeline/skills/shared/external/realitykit-ar/evals/evals.json +24 -27
  190. package/pipeline/skills/shared/external/realitykit-ar/references/realitykit-patterns.md +221 -348
  191. package/pipeline/skills/shared/external/rest-api-design/SKILL.md +1 -0
  192. package/pipeline/skills/shared/external/retrofit-networking/SKILL.md +2 -0
  193. package/pipeline/skills/shared/external/room-database/SKILL.md +2 -0
  194. package/pipeline/skills/shared/external/search-first/SKILL.md +1 -0
  195. package/pipeline/skills/shared/external/shareplay-activities/SKILL.md +222 -393
  196. package/pipeline/skills/shared/external/shareplay-activities/evals/evals.json +23 -24
  197. package/pipeline/skills/shared/external/shareplay-activities/references/shareplay-patterns.md +280 -420
  198. package/pipeline/skills/shared/external/signal-community/SKILL.md +2 -0
  199. package/pipeline/skills/shared/external/skill-creator/SKILL.md +80 -41
  200. package/pipeline/skills/shared/external/skill-creator/audit.md +63 -59
  201. package/pipeline/skills/shared/external/skill-creator/checklist.md +28 -20
  202. package/pipeline/skills/shared/external/skill-creator/examples.md +40 -40
  203. package/pipeline/skills/shared/external/skill-creator/label-check.md +48 -36
  204. package/pipeline/skills/shared/external/skill-creator/scripts/audit-panel.js +91 -100
  205. package/pipeline/skills/shared/external/skill-creator/template.md +51 -39
  206. package/pipeline/skills/shared/external/speech-recognition/SKILL.md +217 -421
  207. package/pipeline/skills/shared/external/speech-recognition/evals/evals.json +23 -26
  208. package/pipeline/skills/shared/external/speech-recognition/references/speechanalyzer-patterns.md +133 -125
  209. package/pipeline/skills/shared/external/storekit/SKILL.md +228 -204
  210. package/pipeline/skills/shared/external/storekit/evals/evals.json +27 -24
  211. package/pipeline/skills/shared/external/storekit/references/app-review-guidelines.md +98 -109
  212. package/pipeline/skills/shared/external/storekit/references/core-patterns.md +298 -242
  213. package/pipeline/skills/shared/external/storekit/references/storekit-advanced.md +356 -649
  214. package/pipeline/skills/shared/external/swift-api-design-guidelines/SKILL.md +274 -399
  215. package/pipeline/skills/shared/external/swift-api-design-guidelines/evals/evals.json +22 -24
  216. package/pipeline/skills/shared/external/swift-api-design-guidelines/references/argument-labels-and-parameters.md +107 -108
  217. package/pipeline/skills/shared/external/swift-api-design-guidelines/references/conventions-and-special-rules.md +93 -165
  218. package/pipeline/skills/shared/external/swift-api-design-guidelines/references/naming-and-clarity.md +99 -137
  219. package/pipeline/skills/shared/external/swift-api-design-guidelines/references/side-effects-and-mutating-pairs.md +77 -120
  220. package/pipeline/skills/shared/external/swift-architecture/SKILL.md +334 -350
  221. package/pipeline/skills/shared/external/swift-architecture/evals/evals.json +22 -22
  222. package/pipeline/skills/shared/external/swift-charts/SKILL.md +208 -394
  223. package/pipeline/skills/shared/external/swift-charts/evals/evals.json +27 -30
  224. package/pipeline/skills/shared/external/swift-charts/references/charts-patterns.md +351 -762
  225. package/pipeline/skills/shared/external/swift-codable/SKILL.md +339 -343
  226. package/pipeline/skills/shared/external/swift-codable/evals/evals.json +20 -20
  227. package/pipeline/skills/shared/external/swift-concurrency/SKILL.md +303 -351
  228. package/pipeline/skills/shared/external/swift-concurrency/evals/evals.json +27 -24
  229. package/pipeline/skills/shared/external/swift-concurrency/references/approachable-concurrency.md +65 -80
  230. package/pipeline/skills/shared/external/swift-concurrency/references/async-algorithms.md +48 -84
  231. package/pipeline/skills/shared/external/swift-concurrency/references/bridging-interop.md +134 -79
  232. package/pipeline/skills/shared/external/swift-concurrency/references/concurrency-patterns.md +145 -167
  233. package/pipeline/skills/shared/external/swift-concurrency/references/diagnostics.md +62 -50
  234. package/pipeline/skills/shared/external/swift-concurrency/references/swiftui-concurrency.md +92 -121
  235. package/pipeline/skills/shared/external/swift-concurrency/references/synchronization-primitives.md +177 -241
  236. package/pipeline/skills/shared/external/swift-formatstyle/SKILL.md +258 -234
  237. package/pipeline/skills/shared/external/swift-language/SKILL.md +342 -382
  238. package/pipeline/skills/shared/external/swift-language/evals/evals.json +24 -27
  239. package/pipeline/skills/shared/external/swift-language/references/swift-attributes-interop.md +79 -56
  240. package/pipeline/skills/shared/external/swift-language/references/swift-patterns-extended.md +297 -340
  241. package/pipeline/skills/shared/external/swift-security/SKILL.md +180 -161
  242. package/pipeline/skills/shared/external/swift-security/evals/evals.json +25 -25
  243. package/pipeline/skills/shared/external/swift-security/references/biometric-authentication.md +314 -469
  244. package/pipeline/skills/shared/external/swift-security/references/certificate-trust.md +408 -476
  245. package/pipeline/skills/shared/external/swift-security/references/common-anti-patterns.md +260 -530
  246. package/pipeline/skills/shared/external/swift-security/references/compliance-owasp-mapping.md +270 -477
  247. package/pipeline/skills/shared/external/swift-security/references/credential-storage-patterns.md +573 -571
  248. package/pipeline/skills/shared/external/swift-security/references/cryptokit-public-key.md +370 -441
  249. package/pipeline/skills/shared/external/swift-security/references/cryptokit-symmetric.md +332 -433
  250. package/pipeline/skills/shared/external/swift-security/references/keychain-access-control.md +346 -468
  251. package/pipeline/skills/shared/external/swift-security/references/keychain-fundamentals.md +352 -472
  252. package/pipeline/skills/shared/external/swift-security/references/keychain-item-classes.md +431 -432
  253. package/pipeline/skills/shared/external/swift-security/references/keychain-sharing.md +328 -425
  254. package/pipeline/skills/shared/external/swift-security/references/migration-legacy-stores.md +341 -579
  255. package/pipeline/skills/shared/external/swift-security/references/secure-enclave.md +396 -457
  256. package/pipeline/skills/shared/external/swift-security/references/testing-security-code.md +354 -614
  257. package/pipeline/skills/shared/external/swift-testing/SKILL.md +188 -175
  258. package/pipeline/skills/shared/external/swift-testing/evals/evals.json +26 -24
  259. package/pipeline/skills/shared/external/swift-testing/references/testing-advanced.md +80 -84
  260. package/pipeline/skills/shared/external/swift-testing/references/testing-patterns.md +317 -433
  261. package/pipeline/skills/shared/external/swiftdata/SKILL.md +392 -256
  262. package/pipeline/skills/shared/external/swiftdata/evals/evals.json +24 -24
  263. package/pipeline/skills/shared/external/swiftdata/references/core-data-coexistence.md +206 -402
  264. package/pipeline/skills/shared/external/swiftdata/references/indexing.md +59 -52
  265. package/pipeline/skills/shared/external/swiftdata/references/predicate-pitfalls.md +57 -33
  266. package/pipeline/skills/shared/external/swiftdata/references/swiftdata-advanced.md +354 -747
  267. package/pipeline/skills/shared/external/swiftdata/references/swiftdata-queries.md +300 -508
  268. package/pipeline/skills/shared/external/swiftlint/SKILL.md +175 -226
  269. package/pipeline/skills/shared/external/swiftlint/references/adoption-and-configuration.md +141 -208
  270. package/pipeline/skills/shared/external/swiftlint/references/custom-rules-and-analyze.md +100 -109
  271. package/pipeline/skills/shared/external/swiftlint/references/plugins-run-scripts-and-integrations.md +159 -179
  272. package/pipeline/skills/shared/external/swiftlint/references/rule-reference.md +383 -18
  273. package/pipeline/skills/shared/external/swiftlint/references/rules-suppressions-and-baselines.md +143 -229
  274. package/pipeline/skills/shared/external/swiftui-animation/SKILL.md +283 -366
  275. package/pipeline/skills/shared/external/swiftui-animation/references/animation-advanced.md +396 -608
  276. package/pipeline/skills/shared/external/swiftui-animation/references/core-animation-bridge.md +336 -385
  277. package/pipeline/skills/shared/external/swiftui-gestures/SKILL.md +239 -349
  278. package/pipeline/skills/shared/external/swiftui-gestures/references/gesture-patterns.md +228 -310
  279. package/pipeline/skills/shared/external/swiftui-layout-components/SKILL.md +260 -249
  280. package/pipeline/skills/shared/external/swiftui-layout-components/references/form.md +92 -74
  281. package/pipeline/skills/shared/external/swiftui-layout-components/references/grids.md +112 -177
  282. package/pipeline/skills/shared/external/swiftui-layout-components/references/list.md +61 -64
  283. package/pipeline/skills/shared/external/swiftui-layout-components/references/scrollview.md +94 -134
  284. package/pipeline/skills/shared/external/swiftui-liquid-glass/SKILL.md +193 -225
  285. package/pipeline/skills/shared/external/swiftui-liquid-glass/references/liquid-glass.md +173 -327
  286. package/pipeline/skills/shared/external/swiftui-navigation/SKILL.md +193 -168
  287. package/pipeline/skills/shared/external/swiftui-navigation/references/deeplinks.md +127 -150
  288. package/pipeline/skills/shared/external/swiftui-navigation/references/navigationstack.md +132 -133
  289. package/pipeline/skills/shared/external/swiftui-navigation/references/sheets.md +152 -117
  290. package/pipeline/skills/shared/external/swiftui-navigation/references/tabview.md +106 -140
  291. package/pipeline/skills/shared/external/swiftui-patterns/SKILL.md +316 -252
  292. package/pipeline/skills/shared/external/swiftui-patterns/references/architecture-patterns.md +341 -332
  293. package/pipeline/skills/shared/external/swiftui-patterns/references/deprecated-migration.md +547 -854
  294. package/pipeline/skills/shared/external/swiftui-patterns/references/design-polish.md +485 -537
  295. package/pipeline/skills/shared/external/swiftui-patterns/references/platform-and-sharing.md +417 -499
  296. package/pipeline/skills/shared/external/swiftui-performance/SKILL.md +213 -376
  297. package/pipeline/skills/shared/external/swiftui-performance/references/demystify-swiftui-performance-wwdc23.md +86 -175
  298. package/pipeline/skills/shared/external/swiftui-performance/references/optimizing-swiftui-performance-instruments.md +89 -195
  299. package/pipeline/skills/shared/external/swiftui-performance/references/understanding-hangs-in-your-app.md +95 -182
  300. package/pipeline/skills/shared/external/swiftui-performance/references/understanding-improving-swiftui-performance.md +71 -149
  301. package/pipeline/skills/shared/external/swiftui-performance/references/wwdc-session-sources.md +21 -27
  302. package/pipeline/skills/shared/external/swiftui-uikit-interop/SKILL.md +303 -295
  303. package/pipeline/skills/shared/external/swiftui-uikit-interop/references/hosting-migration.md +204 -387
  304. package/pipeline/skills/shared/external/swiftui-uikit-interop/references/representable-recipes.md +469 -683
  305. package/pipeline/skills/shared/external/swiftui-webkit/SKILL.md +140 -186
  306. package/pipeline/skills/shared/external/swiftui-webkit/references/loading-and-observation.md +75 -86
  307. package/pipeline/skills/shared/external/swiftui-webkit/references/local-content-and-custom-schemes.md +63 -60
  308. package/pipeline/skills/shared/external/swiftui-webkit/references/migration-and-fallbacks.md +69 -137
  309. package/pipeline/skills/shared/external/swiftui-webkit/references/navigation-and-javascript.md +95 -67
  310. package/pipeline/skills/shared/external/tailwind-css/SKILL.md +1 -0
  311. package/pipeline/skills/shared/external/testing-backend/SKILL.md +1 -0
  312. package/pipeline/skills/shared/external/tipkit/SKILL.md +220 -335
  313. package/pipeline/skills/shared/external/tipkit/references/tipkit-patterns.md +356 -494
  314. package/pipeline/skills/shared/external/typescript-patterns/SKILL.md +1 -0
  315. package/pipeline/skills/shared/external/vision-framework/SKILL.md +260 -375
  316. package/pipeline/skills/shared/external/vision-framework/references/vision-requests.md +393 -515
  317. package/pipeline/skills/shared/external/vision-framework/references/visionkit-scanner.md +363 -539
  318. package/pipeline/skills/shared/external/vue-composition/SKILL.md +1 -0
  319. package/pipeline/skills/shared/external/weatherkit/SKILL.md +152 -310
  320. package/pipeline/skills/shared/external/weatherkit/references/weatherkit-patterns.md +288 -407
  321. package/pipeline/skills/shared/external/web-accessibility/SKILL.md +1 -0
  322. package/pipeline/skills/shared/external/web-performance/SKILL.md +1 -0
  323. package/pipeline/skills/shared/external/web-testing/SKILL.md +1 -0
  324. package/pipeline/skills/shared/external/widgetkit/SKILL.md +216 -288
  325. package/pipeline/skills/shared/external/widgetkit/references/widgetkit-advanced.md +414 -719
  326. package/pipeline/skills/shared/external/NOTICE-swift-ios-skills.md +0 -39
@@ -1,220 +1,131 @@
1
- # Demystify SwiftUI Performance (WWDC23) (Summary)
1
+ # Mental Model: Dependencies, Identity and Lifecycle
2
2
 
3
- Context: WWDC23 session on building a mental model for SwiftUI performance and
4
- triaging hangs, hitches, and excessive update work.
3
+ Notes drawn from the WWDC23 session "Demystify SwiftUI performance". Use them
4
+ to explain why a SwiftUI screen does more work than it should.
5
5
 
6
- ## Contents
7
- - Core mental model
8
- - Dependencies and invalidation
9
- - Expensive body work
10
- - Identity rules for lists and tables
11
- - Initialization and lifecycle pitfalls
12
- - Debugging tools
13
- - Fix patterns
14
- - What to verify after a change
6
+ ## The Model
15
7
 
16
- ## Core mental model
8
+ - For each frame, SwiftUI should do only the work the current state requires.
9
+ - A slow screen almost always has one of three problems: each update does too
10
+ much, updates happen too often, or identity is unstable and work gets thrown
11
+ away and redone.
12
+ - Work in a loop: measure, find the cause, change one thing, measure again.
13
+ Always measure again; gains are hard to judge by eye.
17
14
 
18
- SwiftUI performance starts with one rule: only work that is required for the
19
- current state should happen for the current frame.
15
+ ## Dependencies Decide What Updates
20
16
 
21
- A slow screen usually means one of these is false:
17
+ A view is re-evaluated when something it depends on changes. Dependencies come
18
+ from:
22
19
 
23
- - too much work happens per update
24
- - updates happen too often
25
- - identity is unstable, so SwiftUI redoes work it could have reused
20
+ - `@State` and `@Binding`
21
+ - `@Observable` models and `@ObservedObject`
22
+ - `@Environment` values
23
+ - identity supplied by containers such as `ForEach`, `List` and `Table`
26
24
 
27
- The session's practical loop is:
25
+ Aim for dependencies that are exact, not just few:
28
26
 
29
- - Measure
30
- - Identify
31
- - Optimize
32
- - Re-measure
27
+ - A row that shows one element should not depend on the whole collection.
28
+ - Values that change quickly (scroll offsets, timers, playback position) should
29
+ not travel through the environment, where they reach many views.
30
+ - Extract subviews so each one reads a smaller part of the state.
33
31
 
34
- Do not skip the last step. SwiftUI optimizations are easy to misjudge by eye.
32
+ `Self._printChanges()` tells you which property changed, whether a parent
33
+ re-rendered the view, and whether the view reacts to state it does not
34
+ display. It is a debugging aid; do not ship it and do not treat it as a
35
+ profiler.
35
36
 
36
- ## Dependencies and invalidation
37
+ ## Work That Does Not Belong in `body`
37
38
 
38
- A view updates when one of its dependencies changes.
39
-
40
- Common dependency sources:
41
-
42
- - `@State`
43
- - `@Binding`
44
- - `@Observable` / `@ObservedObject`
45
- - `@Environment`
46
- - container-derived identity (`ForEach`, `List`, `Table`)
47
-
48
- The performance goal is not "fewer dependencies" in the abstract. The goal is
49
- **precise dependencies** so only the view that needs to update actually updates.
50
-
51
- ### Practical implications
52
-
53
- - Avoid a row depending on a whole collection if it only needs one element.
54
- - Avoid broad environment-driven updates for fast-changing values.
55
- - Extract subviews when a smaller view can read a smaller state surface.
56
-
57
- ### Debug-only dependency inspection
58
-
59
- `Self._printChanges()` is useful in debug builds when you are not sure why a
60
- view keeps updating.
61
-
62
- Use it to answer:
63
-
64
- - which property changed?
65
- - which parent view re-rendered?
66
- - is the view reacting to state it should not care about?
67
-
68
- Do not treat `_printChanges()` output as a shipping-time profiling tool.
69
-
70
- ## Expensive body work
71
-
72
- View bodies need to stay cheap.
73
-
74
- Typical mistakes:
75
-
76
- - string formatting in `body`
77
- - array filtering and sorting in `body`
78
- - expensive image work in `body`
79
- - constructing large attributed strings during render
80
- - initializing heavy models in-line with view creation
39
+ Frequent offenders: formatting strings, filtering and sorting, image
40
+ processing, building large attributed strings, and constructing heavy model
41
+ objects inline.
81
42
 
82
43
  ```swift
83
- // DON'T
84
- var body: some View {
85
- List(items.filter(shouldShow).sorted(by: sortRule)) { item in
86
- Text(numberFormatter.string(from: item.value as NSNumber) ?? "")
87
- }
44
+ // Every evaluation filters, sorts and formats each row again.
45
+ List(orders.filter { $0.isOpen }.sorted { $0.date > $1.date }) { order in
46
+ Text(order.amount.formatted(.currency(code: "EUR")))
88
47
  }
89
48
 
90
- // DO
91
- var body: some View {
92
- List(viewModel.visibleItems) { item in
93
- Text(item.formattedValue)
94
- }
49
+ // The model prepares rows once, when its inputs change.
50
+ List(board.openRows) { row in
51
+ Text(row.amountText)
95
52
  }
96
53
  ```
97
54
 
98
- The winning pattern is precomputation at the model boundary, not clever work in
99
- `body`.
100
-
101
- ## Identity rules for lists and tables
102
-
103
- Identity is one of the biggest hidden performance levers in SwiftUI.
55
+ Do this preparation where data enters the model, not in the view.
104
56
 
105
- ### Stable identity matters
57
+ ## Identity for Lists and Tables
106
58
 
107
- Use stable IDs that survive refreshes and sorting. If identity churns, SwiftUI
108
- cannot reuse rows, preserve animations, or diff efficiently.
109
-
110
- ### Constant row count matters
111
-
112
- Inside `ForEach`, SwiftUI expects a predictable mapping between data elements and
113
- rendered views.
114
-
115
- Avoid patterns like:
59
+ - Ids must survive a refresh and a re-sort. When they churn, SwiftUI cannot
60
+ reuse rows, keep animations or diff efficiently.
61
+ - `ForEach` expects each element to map to a predictable view. Do not wrap rows
62
+ in `if item.isVisible { ... }`; iterate a collection that is already filtered
63
+ so every element yields exactly one row.
116
64
 
117
65
  ```swift
118
- ForEach(items) { item in
119
- if item.isVisible {
120
- Row(item: item)
121
- }
66
+ ForEach(shelf.visibleBooks) { book in
67
+ BookRow(book: book)
122
68
  }
123
69
  ```
124
70
 
125
- Prefer:
71
+ - Keep `AnyView` out of list rows that are rendered often.
72
+ - A `TableRow` resolves to exactly one row. Keep row structure predictable and
73
+ prefer the simpler `Table` initialisers when they fit.
126
74
 
127
- ```swift
128
- ForEach(visibleItems) { item in
129
- Row(item: item)
130
- }
131
- ```
132
-
133
- ### Avoid `AnyView` in hot list rows
134
-
135
- Type erasure can hide useful structural information and increase work in large
136
- lists or tables.
137
-
138
- ### Table-specific note
139
-
140
- `TableRow` resolves to a single row. Keep row structure predictable and use the
141
- streamlined `Table` APIs when possible.
75
+ ## Initialisation and Lifecycle
142
76
 
143
- ## Initialization and lifecycle pitfalls
144
-
145
- ### Heavy model creation in view init/body
146
-
147
- Keep view initialization lightweight. Start async work with `.task` or from a
148
- model object.
77
+ Keep `init` cheap; SwiftUI can create view values many times. Start expensive
78
+ or asynchronous work from `.task` or from a model:
149
79
 
150
80
  ```swift
151
- // DON'T
152
- struct DetailView: View {
153
- let loader = BigLoader() // heavy construction
154
- }
155
-
156
- // DO
157
- struct DetailView: View {
158
- @State private var model: DetailModel?
81
+ struct InvoiceDetail: View {
82
+ let invoiceID: Invoice.ID
83
+ @State private var loader: InvoiceLoader?
159
84
 
160
85
  var body: some View {
161
- content
162
- .task {
163
- model = await loadDetailModel()
86
+ Group {
87
+ if let loader {
88
+ InvoiceSummary(loader: loader)
89
+ } else {
90
+ ProgressView()
164
91
  }
92
+ }
93
+ .task(id: invoiceID) {
94
+ loader = await InvoiceLoader.prepare(for: invoiceID)
95
+ }
165
96
  }
166
97
  }
167
98
  ```
168
99
 
169
- ### Hidden work from computed properties
170
-
171
- A computed property can still be body work if it runs during render. If it is
172
- expensive, treat it like body work and precompute it.
173
-
174
- ## Debugging tools
175
-
176
- ### Instruments
177
-
178
- Use Instruments for hangs, hitches, update counts, and expensive frames.
179
-
180
- ### `_printChanges()`
181
-
182
- Use it in debug to inspect dependency behavior.
183
-
184
- ### Release-build validation
185
-
186
- A debug build can make SwiftUI performance look worse or different than a
187
- shipping build. Validate important performance changes in Release on device.
188
-
189
- ## Fix patterns
190
-
191
- ### Split views by dependency boundary
192
-
193
- If one small piece of state changes frequently, isolate the subview that reads
194
- it.
195
-
196
- ### Pre-filter and cache collections
100
+ The version to avoid stores `let loader = InvoiceLoader(id:)` as a property, so
101
+ the loader is rebuilt every time the parent creates the view.
197
102
 
198
- Do filtering, mapping, sorting, and grouping before rendering.
103
+ An expensive computed property read during rendering counts as body work too.
104
+ Compute it ahead of time.
199
105
 
200
- ### Avoid broad environment reads in hot paths
106
+ ## Tools
201
107
 
202
- Environment is convenient but not free. Keep fast-changing values local unless
203
- multiple subtrees truly need them.
108
+ Instruments shows hangs, hitches, update counts and expensive frames. Confirm
109
+ findings in a Release build on a device; a Debug build can look worse, or just
110
+ different.
204
111
 
205
- ### Reduce hidden allocations
112
+ ## Fix Patterns
206
113
 
207
- Move formatters, bundle lookups, and derived strings out of repeated body paths.
114
+ - Split views along dependency boundaries.
115
+ - Filter, map, sort and group before rendering.
116
+ - Keep reads of broad environment values out of hot paths; keep values that
117
+ change quickly local.
118
+ - Move formatters, bundle lookups and derived strings out of code that runs on
119
+ every update.
208
120
 
209
- ## What to verify after a change
121
+ ## Checking a Fix
210
122
 
211
- After optimizing, check all of the following:
123
+ After a change, check that:
212
124
 
213
- - the target interaction feels smoother
214
- - update counts dropped in Instruments
215
- - row identity stayed stable across reloads
216
- - animation behavior still matches product intent
217
- - no correctness bugs were introduced by caching or splitting views
125
+ - the interaction is visibly smoother,
126
+ - update counts went down,
127
+ - row identity stays the same across reloads,
128
+ - animations still do what was intended,
129
+ - caching or splitting did not introduce a correctness bug.
218
130
 
219
- A performance fix that breaks state ownership or animation correctness is not a
220
- real fix.
131
+ A change that breaks state ownership or animation is not a fix.
@@ -1,234 +1,128 @@
1
- # Optimizing SwiftUI Performance with Instruments (Summary)
1
+ # Profiling with the SwiftUI Instrument
2
2
 
3
- Context: WWDC session introducing the SwiftUI Instrument in Instruments 26 and
4
- how to diagnose SwiftUI-specific bottlenecks.
3
+ Based on the WWDC25 session "Optimize SwiftUI performance with Instruments".
4
+ The SwiftUI Instrument described here ships with Instruments 26.
5
5
 
6
- ## Contents
7
- - When to use the SwiftUI Instrument
8
- - Recommended capture setup
9
- - Reading the SwiftUI timeline
10
- - Workflow for long view body updates
11
- - Workflow for frequent updates
12
- - Cause and Effect Graph usage
13
- - Common hotspots
14
- - Fix patterns
15
- - Re-measure checklist
6
+ ## When It Is the Right Tool
16
7
 
17
- ## When to use the SwiftUI Instrument
8
+ Reach for it when the symptom points at view updates, layout, rendering or
9
+ state spreading too far:
18
10
 
19
- Use the SwiftUI Instrument when the symptom is clearly tied to view updates,
20
- layout, rendering, or state fan-out.
11
+ - scrolling stutters,
12
+ - a push to a new screen pauses first,
13
+ - an animation is uneven although nothing obviously blocks the main thread,
14
+ - a timer or observable model triggers far more updates than expected.
21
15
 
22
- Good fits:
16
+ When the whole app freezes and nothing points at the UI, start with Hangs or
17
+ Time Profiler and come to the SwiftUI lanes afterwards.
23
18
 
24
- - scrolling stutters in a SwiftUI-heavy screen
25
- - pushing a destination causes a pause during view construction
26
- - an animation feels inconsistent even without obvious main-thread blocking
27
- - a timer or observable object causes too many updates
19
+ ## Capture Setup
28
20
 
29
- If the symptom is a broad app freeze with no clear UI source, start with Hangs
30
- or Time Profiler first, then move to SwiftUI-specific tools.
21
+ - Release build on a real device.
22
+ - A sequence you can repeat exactly.
23
+ - As little debug logging as possible.
24
+ - Enough repetitions that a pattern shows.
31
25
 
32
- ## Recommended capture setup
26
+ A good default set: the SwiftUI Instrument plus Time Profiler, and Hangs or
27
+ Animation Hitches when the symptom calls for it.
33
28
 
34
- Profile with the same assumptions you use for shipping code:
29
+ ## The SwiftUI Lanes
35
30
 
36
- - Release build
37
- - real device
38
- - reproducible interaction sequence
39
- - minimal debug logging
40
- - enough repetitions to show a pattern, not a one-off spike
31
+ | Lane | What it tells you |
32
+ |------|-------------------|
33
+ | Update Groups | Coarse buckets of work. Shows bursts even when no single update is slow. |
34
+ | Long View Body Updates | `body` evaluations that took too long. Orange is worth a look, red is clearly too slow. |
35
+ | Long Platform View Updates | Time in hosted UIKit or AppKit views: `UIViewRepresentable`, `UIViewControllerRepresentable`, heavy list or table bridging, embedded media or web views. |
36
+ | Other Long Updates | Text layout, geometry, list diffing and update coordination. |
41
37
 
42
- A good baseline template is:
38
+ ## Workflow: One Update Is Too Slow
43
39
 
44
- - SwiftUI Instrument
45
- - Time Profiler
46
- - Hangs or Animation Hitches when relevant
47
-
48
- ## Reading the SwiftUI timeline
49
-
50
- Key lanes to understand:
51
-
52
- ### Update Groups
53
-
54
- High-level buckets of SwiftUI work over time. Useful for spotting bursts of
55
- activity even when no single update is individually slow.
56
-
57
- ### Long View Body Updates
58
-
59
- Use this lane when a view `body` itself is expensive.
60
-
61
- Interpretation:
62
-
63
- - orange indicates notable cost
64
- - red indicates clearly too-slow view updates
65
-
66
- ### Long Platform View Updates
67
-
68
- This usually points to UIKit/AppKit work hosted inside SwiftUI, including:
69
-
70
- - `UIViewRepresentable`
71
- - `UIViewControllerRepresentable`
72
- - heavy `List`/table bridging
73
- - embedded media or web views
74
-
75
- ### Other Long Updates
76
-
77
- Catches expensive work outside pure body computation, such as:
78
-
79
- - text layout
80
- - geometry
81
- - list diffing
82
- - update coordination
83
-
84
- ## Workflow for long view body updates
85
-
86
- ### 1. Find a red or orange update
87
-
88
- Start with one obviously expensive update rather than a long trace window.
89
-
90
- ### 2. Set inspection range
91
-
92
- Select the update window so Time Profiler aligns with the same time slice.
93
-
94
- ### 3. Inspect the call tree or flame graph
95
-
96
- Look for work that should not be happening during body evaluation.
97
-
98
- Common surprises:
99
-
100
- - formatter allocation
101
- - sorting or filtering collections
102
- - image decoding
103
- - string building
104
- - model initialization
105
- - synchronous persistence reads
106
-
107
- ### 4. Move heavy work out of `body`
40
+ 1. Pick a single red or orange update, not a long stretch of timeline.
41
+ 2. Set the inspection range to that update so Time Profiler shows the same
42
+ interval.
43
+ 3. Read the call tree or flame graph. Typical findings: a formatter being
44
+ created, sorting or filtering, image decoding, string building, model
45
+ construction, a synchronous read from storage.
46
+ 4. Move that work out of `body`:
108
47
 
109
48
  ```swift
110
- // DON'T
111
- var body: some View {
112
- Text(items.sorted(by: \.date).map(\.title).joined(separator: ", "))
113
- }
49
+ // Before: runs on every evaluation.
50
+ Text(playlist.tracks.sorted { $0.position < $1.position }
51
+ .map(\.title).joined(separator: ", "))
114
52
 
115
- // DO
116
- var body: some View {
117
- Text(viewModel.joinedTitles)
118
- }
53
+ // After: the model keeps the joined string current.
54
+ Text(playlist.trackSummary)
119
55
  ```
120
56
 
121
- ### 5. Re-record the same flow
122
-
123
- If the trace still shows long view body updates, the expensive work likely just
124
- moved into a child view or another dependency path.
57
+ 5. Record again. If long updates remain, the work probably moved into a child
58
+ view or reaches the view through another dependency.
125
59
 
126
- ## Workflow for frequent updates
60
+ ## Workflow: Too Many Updates
127
61
 
128
- Some screens feel slow because updates happen too often, not because any one
129
- update is catastrophic.
62
+ A screen can feel slow because it updates constantly, even if every single
63
+ update is cheap.
130
64
 
131
- ### 1. Use Update Groups first
132
-
133
- Look for long active ranges with many updates but no large red spikes.
134
-
135
- ### 2. Inspect counts, not just duration
136
-
137
- A screen doing cheap work 200 times can still feel worse than one doing one
138
- moderately expensive update.
139
-
140
- ### 3. Open Cause and Effect Graph
141
-
142
- This is often the fastest way to answer:
143
-
144
- - what changed?
145
- - which dependency triggered the update?
146
- - why did that change fan out to unrelated views?
147
-
148
- ### 4. Narrow the dependency scope
65
+ - Start with Update Groups: look for long active stretches full of updates with
66
+ no red spikes.
67
+ - Look at counts, not only durations. Cheap work done 200 times can feel worse
68
+ than one moderately expensive update.
69
+ - Open the Cause and Effect Graph to see what changed, which dependency fired
70
+ and why the update spread.
149
71
 
150
72
  Typical fixes:
73
+ - extract subviews that read only the state they show,
74
+ - replace a broad shared model with narrower derived state,
75
+ - stop passing fast-changing data through the environment,
76
+ - split a large `@Observable` model whose unrelated properties change together.
151
77
 
152
- - extract subviews so they only read the state they need
153
- - replace broad shared models with narrower derived state
154
- - avoid environment values for fast-changing data
155
- - split large `@Observable` models if unrelated properties change together
156
-
157
- ## Cause and Effect Graph usage
158
-
159
- Use it when backtraces are misleading.
160
-
161
- SwiftUI is declarative, so the expensive work may not appear near the code that
162
- caused the update chain.
163
-
164
- Good uses:
165
-
166
- - a selection change updates an unrelated sidebar
167
- - a timer invalidates a full list
168
- - geometry updates ripple through many subviews
169
- - a global favorites model causes every row to re-evaluate
170
-
171
- ## Common hotspots
78
+ ## Cause and Effect Graph
172
79
 
173
- ### Formatter allocation
80
+ Use it when backtraces point in the wrong direction; in a declarative UI the
81
+ code that did the work is often far from the code that caused it. Good uses:
174
82
 
175
- Avoid constructing `DateFormatter`, `NumberFormatter`, or `MeasurementFormatter`
176
- in `body` or per-row views.
83
+ - changing the selection also updates an unrelated sidebar,
84
+ - a timer invalidates an entire list,
85
+ - a geometry change ripples through many subviews,
86
+ - a global favourites model makes every row re-evaluate.
177
87
 
178
- ### Filtering or sorting in the view tree
88
+ ## Hot Spots and How to Fix Them
179
89
 
180
- Precompute filtered collections before render.
90
+ - Never build `DateFormatter`, `NumberFormatter` or `MeasurementFormatter` in
91
+ `body` or per row.
92
+ - Filter collections before rendering; do not route raw geometry through a
93
+ broadly observed model.
94
+ - Unstable identity and a row count that changes between passes make lists
95
+ and tables expensive.
96
+ - Check representables for configuration repeated on every
97
+ `updateUIView` or `updateUIViewController` call.
181
98
 
182
- ### Geometry-driven layout churn
183
-
184
- Avoid feeding raw geometry values through broad observable state.
185
-
186
- ### Identity instability
187
-
188
- Lists and tables get expensive when identity changes or row counts vary in ways
189
- SwiftUI cannot efficiently diff.
190
-
191
- ### Platform view bridging
192
-
193
- Audit representables for repeated configuration work in `updateUIView` or
194
- `updateUIViewController`.
195
-
196
- ## Fix patterns
197
-
198
- ### Cache presentation data
99
+ Cache presentation values in a model:
199
100
 
200
101
  ```swift
201
102
  @Observable
202
- final class TripPresentationModel {
203
- var formattedDistance: String = ""
103
+ final class RunSummary {
104
+ private(set) var distanceText = ""
204
105
 
205
- func update(distance: Measurement<UnitLength>, formatter: MeasurementFormatter) {
206
- formattedDistance = formatter.string(from: distance)
106
+ func update(metres: Double, using formatter: MeasurementFormatter) {
107
+ let distance = Measurement<UnitLength>(value: metres, unit: .meters)
108
+ distanceText = formatter.string(from: distance)
207
109
  }
208
110
  }
209
111
  ```
210
112
 
211
- ### Scope observable dependencies
212
-
213
- Prefer models where a row reads only row-local state.
214
-
215
- ### Keep representable updates idempotent
216
-
217
- Only mutate the hosted platform view when input values actually changed.
218
-
219
- ### Gate noisy signals
220
-
221
- A geometry or timer signal may need thresholding, debouncing, or coalescing.
222
-
223
- ## Re-measure checklist
113
+ - Scope observable dependencies so a row reads only its own state.
114
+ - Make representable updates idempotent: touch the hosted view only when an
115
+ input actually changed.
116
+ - Tame noisy geometry or timer signals with a threshold, debouncing or
117
+ coalescing.
224
118
 
225
- After every change:
119
+ ## Measuring Again
226
120
 
227
- - record the same flow again
228
- - compare update count, not just total runtime
229
- - verify hitch frequency went down
230
- - verify no new Long Platform View Updates appeared
231
- - verify behavior in Release on device
121
+ - Record the same flow again.
122
+ - Compare how many updates happen, not only how long they take.
123
+ - Confirm there are fewer hitches.
124
+ - Confirm no new Long Platform View Updates appeared.
125
+ - Check in Release on a device.
232
126
 
233
- If a change makes one screen faster but causes more updates elsewhere, keep
234
- following the dependency graph until the fan-out is truly reduced.
127
+ If one screen gets faster while updates rise somewhere else, keep following the
128
+ dependency graph until the fan-out really goes down.