@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,275 +1,229 @@
1
1
  ---
2
2
  name: swiftui-webkit
3
- description: "Embeds and controls web content in SwiftUI with WebKit for SwiftUI, including WebView, WebPage, navigation policies, JavaScript execution, observable page state, link interception, local HTML or data loading, and custom URL schemes. Use when building iOS 26+ article/detail views, help centers, in-app documentation, or other embedded web experiences backed by HTML, CSS, and JavaScript."
3
+ description: "Web content in SwiftUI with WebKit for SwiftUI: WebView, WebPage, observable page state, navigation policies, link interception, JavaScript calls, local HTML or data, custom URL schemes. Use when an iOS 26+ screen shows articles, detail pages, help centers, in-app docs or other embedded HTML, CSS and JavaScript, or when replacing a WKWebView wrapper. Not for OAuth or deep-link routing."
4
4
  metadata:
5
- source: "dpearson2699/swift-ios-skills (PolyForm Perimeter 1.0.0)"
5
+ source: multi-agent-pipeline
6
6
  ---
7
7
 
8
- # SwiftUI WebKit
8
+ # WebKit for SwiftUI
9
9
 
10
- Embed and manage web content in SwiftUI using the native WebKit-for-SwiftUI APIs introduced for iOS 26, iPadOS 26, macOS 26, and visionOS 26. Use this skill when the app needs an integrated web surface, app-owned HTML content, JavaScript-backed page interaction, or custom navigation policy control.
10
+ Starting with the 26 releases (iOS, iPadOS, macOS, visionOS), WebKit ships a SwiftUI
11
+ surface of its own: `WebView` draws web content and `WebPage` is the
12
+ observable model behind it. Everything below needs `import WebKit` and those
13
+ OS versions.
11
14
 
12
- ## Contents
15
+ ## Picking the container
13
16
 
14
- - [Choose the Right Web Container](#choose-the-right-web-container)
15
- - [Displaying Web Content](#displaying-web-content)
16
- - [Loading and Observing with WebPage](#loading-and-observing-with-webpage)
17
- - [Navigation Policies](#navigation-policies)
18
- - [JavaScript Integration](#javascript-integration)
19
- - [Local Content and Custom URL Schemes](#local-content-and-custom-url-schemes)
20
- - [WebView Customization](#webview-customization)
21
- - [Common Mistakes](#common-mistakes)
22
- - [Review Checklist](#review-checklist)
23
- - [References](#references)
24
-
25
- ## Choose the Right Web Container
26
-
27
- Use the narrowest tool that matches the job.
28
-
29
- | Need | Default choice |
17
+ | Situation | Use |
30
18
  |---|---|
31
- | Embedded app-owned web content in SwiftUI | `WebView` + `WebPage` |
32
- | Simple external site presentation with Safari behavior | `SFSafariViewController` |
33
- | OAuth or third-party sign-in | `ASWebAuthenticationSession` |
34
- | Back-deploy below iOS 26 or use missing legacy-only WebKit features | `WKWebView` fallback |
19
+ | Web content that belongs to the app, shown inside a SwiftUI screen | `WebView` with a `WebPage` |
20
+ | Sending the user to an outside site with Safari behaviour | `SFSafariViewController` |
21
+ | OAuth or any third-party sign-in | `ASWebAuthenticationSession` |
22
+ | Deployment target below iOS 26, or a capability only the old API has | a `WKWebView` fallback |
35
23
 
36
- Prefer `WebView` and `WebPage` for modern SwiftUI apps targeting iOS 26+. Apple's WWDC25 guidance explicitly recommends migrating SwiftUI apps away from UIKit/AppKit WebKit wrappers when possible.
24
+ Apple's WWDC25 WebKit guidance points SwiftUI apps away from UIKit and AppKit
25
+ web view wrappers wherever the new API covers the need. Sign-in never runs in
26
+ an embedded web view.
37
27
 
38
- Do not use embedded web views for OAuth. That stays an `ASWebAuthenticationSession` flow.
28
+ ## Showing a page
39
29
 
40
- ## Displaying Web Content
41
-
42
- Use the simple `WebView(url:)` form when the app only needs to render a URL and SwiftUI state drives navigation.
30
+ The shortest path renders a URL and lets SwiftUI state decide which one:
43
31
 
44
32
  ```swift
45
33
  import SwiftUI
46
34
  import WebKit
47
35
 
48
- struct ArticleView: View {
49
- let url: URL
36
+ struct ReleaseNotesView: View {
37
+ let address: URL
50
38
 
51
39
  var body: some View {
52
- WebView(url: url)
40
+ WebView(url: address)
53
41
  }
54
42
  }
55
43
  ```
56
44
 
57
- Create a `WebPage` when the app needs to load requests directly, observe state, call JavaScript, or customize navigation behavior.
45
+ As soon as you need to issue requests yourself, watch state, run
46
+ JavaScript or steer navigation, own a `WebPage` and pass it to
47
+ `WebView(page)`. Deciding this up front is cheaper than retrofitting it.
58
48
 
59
49
  ```swift
60
50
  @Observable
61
51
  @MainActor
62
- final class ArticleModel {
52
+ final class GuideModel {
63
53
  let page = WebPage()
64
54
 
65
- func load(_ url: URL) async throws {
66
- for try await _ in page.load(URLRequest(url: url)) {
67
- }
55
+ func open(_ address: URL) async throws {
56
+ let events = page.load(URLRequest(url: address))
57
+ for try await _ in events { }
68
58
  }
69
59
  }
70
60
 
71
- struct ArticleDetailView: View {
72
- @State private var model = ArticleModel()
73
- let url: URL
61
+ struct GuideScreen: View {
62
+ @State private var model = GuideModel()
63
+ let start: URL
74
64
 
75
65
  var body: some View {
76
66
  WebView(model.page)
77
- .task {
78
- try? await model.load(url)
79
- }
67
+ .task { try? await model.open(start) }
80
68
  }
81
69
  }
82
70
  ```
83
71
 
84
- See [references/loading-and-observation.md](references/loading-and-observation.md) for full examples.
85
-
86
- ## Loading and Observing with WebPage
72
+ ## Loading and observing
87
73
 
88
- `WebPage` is an `@MainActor` observable type. Use it when you need page state in SwiftUI.
74
+ `WebPage` is an observable class isolated to the main actor. Its load
75
+ methods:
89
76
 
90
- Common loading entry points:
91
- - `load(URLRequest)`
92
- - `load(URL)`
93
- - `load(html:baseURL:)`
94
- - `load(_:mimeType:characterEncoding:baseURL:)`
77
+ - `load(_ request: URLRequest)` and `load(_ url: URL?)`
78
+ - `load(html:baseURL:)` for a string of markup
79
+ - `load(_:mimeType:characterEncoding:baseURL:)` for raw `Data`; the encoding
80
+ is a `String.Encoding` such as `.utf8`
95
81
 
96
- Common observable properties:
97
- - `title`
98
- - `url`
99
- - `isLoading`
100
- - `estimatedProgress`
101
- - `currentNavigationEvent`
102
- - `backForwardList`
82
+ Each returns an async sequence of navigation events that throws when the
83
+ navigation fails. Observable properties include `title` (a non-optional
84
+ `String`), `url`, `isLoading`, `estimatedProgress`, `backForwardList`,
85
+ `hasOnlySecureContent` and, from the SwiftUI overlay, `themeColor`.
103
86
 
104
87
  ```swift
105
- struct ReaderView: View {
88
+ struct ArticleReader: View {
106
89
  @State private var page = WebPage()
90
+ let story: URL
107
91
 
108
92
  var body: some View {
109
93
  WebView(page)
110
- .navigationTitle(page.title ?? "Loading")
111
- .overlay {
94
+ .navigationTitle(page.title.isEmpty ? "Article" : page.title)
95
+ .overlay(alignment: .top) {
112
96
  if page.isLoading {
113
97
  ProgressView(value: page.estimatedProgress)
114
98
  }
115
99
  }
116
100
  .task {
117
101
  do {
118
- for try await _ in page.load(URLRequest(url: URL(string: "https://example.com")!)) {
119
- }
102
+ let events = page.load(story)
103
+ for try await _ in events { }
120
104
  } catch {
121
- // Handle load failure.
105
+ // show an inline error state
122
106
  }
123
107
  }
124
108
  }
125
109
  }
126
110
  ```
127
111
 
128
- When you need to react to every navigation, observe the navigation sequence rather than only checking a single property.
129
-
130
- ```swift
131
- Task {
132
- for await event in page.navigations {
133
- // Handle finish, redirect, or failure events.
134
- }
135
- }
136
- ```
137
-
138
- See [references/loading-and-observation.md](references/loading-and-observation.md) for stronger patterns and the load-sequence examples.
112
+ To react to every navigation rather than sampling one property, iterate
113
+ `page.navigations` with `for try await`. The released SDK has no
114
+ `currentNavigationEvent` property; the event sequences are the way to follow
115
+ progress. Details are in [page loading notes](references/loading-and-observation.md).
139
116
 
140
- ## Navigation Policies
117
+ ## Navigation policy
141
118
 
142
- Use `WebPage.NavigationDeciding` to allow, cancel, or customize navigations based on the request or response.
119
+ A type conforming to `WebPage.NavigationDeciding` can permit, cancel or adjust
120
+ navigations by request or by response. Typical jobs:
143
121
 
144
- Typical uses:
145
- - keep app-owned domains inside the embedded web view
146
- - cancel external domains and hand them off with `openURL`
147
- - intercept special callback URLs
148
- - tune `NavigationPreferences`
122
+ - keep the app's own domains inside the web view,
123
+ - cancel links to other domains and hand them to `openURL`,
124
+ - catch callback URLs,
125
+ - adjust `WebPage.NavigationPreferences` for a request.
149
126
 
150
127
  ```swift
151
128
  @MainActor
152
- final class ArticleNavigationDecider: WebPage.NavigationDeciding {
153
- var urlToOpenExternally: URL?
154
-
155
- func decidePolicy(
156
- for action: WebPage.NavigationAction,
157
- preferences: inout WebPage.NavigationPreferences
158
- ) async -> WKNavigationActionPolicy {
159
- guard let url = action.request.url else { return .allow }
160
-
161
- if url.host == "example.com" {
162
- return .allow
163
- }
164
-
165
- urlToOpenExternally = url
129
+ final class DomainGate: WebPage.NavigationDeciding {
130
+ var leaving: URL?
131
+
132
+ func decidePolicy(for step: WebPage.NavigationAction,
133
+ preferences prefs: inout WebPage.NavigationPreferences)
134
+ async -> WKNavigationActionPolicy {
135
+ guard let target = step.request.url, let host = target.host() else { return .allow }
136
+ if host.hasSuffix("docs.example.org") { return .allow }
137
+ leaving = target // opened outside the app by the view
166
138
  return .cancel
167
139
  }
168
140
  }
169
141
  ```
170
142
 
171
- Keep app-level deep-link routing in the navigation skill. This skill owns navigation that happens inside embedded web content.
172
-
173
- See [references/navigation-and-javascript.md](references/navigation-and-javascript.md) for complete patterns.
174
-
175
- ## JavaScript Integration
143
+ This skill covers navigation inside web content. Routing the app itself from
144
+ a deep link belongs to the `swiftui-navigation` skill.
176
145
 
177
- Use `callJavaScript(_:arguments:in:contentWorld:)` to evaluate JavaScript functions against the page.
146
+ ## JavaScript
178
147
 
179
- ```swift
180
- let script = """
181
- const headings = [...document.querySelectorAll('h1, h2')];
182
- return headings.map(node => ({
183
- id: node.id,
184
- text: node.textContent?.trim()
185
- }));
186
- """
187
-
188
- let result = try await page.callJavaScript(script)
189
- let headings = result as? [[String: Any]] ?? []
190
- ```
191
-
192
- You can pass values through the `arguments` dictionary and cast the returned `Any` into the Swift type you actually need.
148
+ `callJavaScript(_:arguments:in:contentWorld:)` runs the string as the body of
149
+ an async JavaScript function, so the script uses `return`. The result comes
150
+ back as `Any?`; cast it to the Swift shape you expect straight away, and pass
151
+ values through `arguments` rather than building them into the script text.
193
152
 
194
153
  ```swift
195
- let result = try await page.callJavaScript(
196
- "return document.getElementById(sectionID)?.getBoundingClientRect().top ?? null;",
197
- arguments: ["sectionID": selectedSectionID]
154
+ let raw = try await page.callJavaScript(
155
+ "return [...document.querySelectorAll(selector)].map(n => ({ id: n.id, text: n.textContent }))",
156
+ arguments: ["selector": "h2"]
198
157
  )
158
+ let headings = raw as? [[String: Any]] ?? []
199
159
  ```
200
160
 
201
- Important boundary: the native SwiftUI WebKit API clearly supports Swift-to-JavaScript calls, but it does not expose an obvious direct replacement for `WKScriptMessageHandler`. If you need coarse JS-to-native signaling, a custom navigation or callback-URL pattern can work, but document it as a workaround pattern, not a guaranteed one-to-one replacement.
161
+ `callJavaScript` is not a message channel from the page to the app. For
162
+ simple one-off signals, the page can navigate to a custom callback URL that
163
+ the navigation decider intercepts; that is a workaround, not a full
164
+ replacement for `WKScriptMessageHandler`. `WebPage.Configuration` does expose
165
+ a `userContentController` (a `WKUserContentController`) for apps that need
166
+ structured script messages. See
167
+ [policy and script notes](references/navigation-and-javascript.md).
202
168
 
203
- See [references/navigation-and-javascript.md](references/navigation-and-javascript.md).
169
+ ## Local content and custom schemes
204
170
 
205
- ## Local Content and Custom URL Schemes
206
-
207
- Use `WebPage.Configuration` and `URLSchemeHandler` when the app needs bundled HTML, offline documents, or app-provided resources under a custom scheme.
171
+ For bundled HTML, offline documentation or resources the app generates,
172
+ register a `URLSchemeHandler` on a `WebPage.Configuration`:
208
173
 
209
174
  ```swift
210
- var configuration = WebPage.Configuration()
211
- configuration.urlSchemeHandlers[URLScheme("docs")!] = DocsSchemeHandler(bundle: .main)
212
-
213
- let page = WebPage(configuration: configuration)
214
- for try await _ in page.load(URL(string: "docs://article/welcome")!) {
175
+ var setup = WebPage.Configuration()
176
+ if let scheme = URLScheme("manual") {
177
+ setup.urlSchemeHandlers[scheme] = ManualFiles()
215
178
  }
216
-
179
+ let page = WebPage(configuration: setup)
180
+ // later: page.load(URL(string: "manual://getting-started"))
217
181
  ```
218
182
 
219
- Use this for:
220
- - bundled documentation or article content
221
- - offline HTML/CSS/JS assets
222
- - app-owned resource loading under a custom scheme
223
-
224
- Do not overuse custom schemes for normal remote content. Prefer standard HTTPS for server-hosted pages.
225
-
226
- See [references/local-content-and-custom-schemes.md](references/local-content-and-custom-schemes.md).
227
-
228
- ## WebView Customization
229
-
230
- Use WebView modifiers to match the intended browsing experience.
231
-
232
- Useful modifiers and related APIs:
233
- - `webViewBackForwardNavigationGestures(_:)`
234
- - `findNavigator(isPresented:)`
235
- - `webViewScrollPosition(_:)`
236
- - `webViewOnScrollGeometryChange(...)`
237
-
238
- Apply them only when the user experience needs them.
239
-
240
- - Enable back/forward gestures when people are likely to visit multiple pages.
241
- - Add Find in Page when the content is document-like.
242
- - Sync scroll position only when the app has a sidebar, table of contents, or other explicit navigation affordance.
243
-
244
- Apple's HIG also applies here: support back/forward navigation when appropriate, but do not turn an app web view into a general-purpose browser.
245
-
246
- ## Common Mistakes
247
-
248
- - Using `WKWebView` wrappers by default in an iOS 26+ SwiftUI app instead of starting with `WebView` and `WebPage`
249
- - Using embedded web views for OAuth instead of `ASWebAuthenticationSession`
250
- - Reaching for `WebPage` only after building a plain `WebView(url:)` path that now needs state, JS, or navigation control
251
- - Treating `callJavaScript` as a direct replacement for `WKScriptMessageHandler`
252
- - Keeping all links inside the app when external domains should open outside the embedded surface
253
- - Building a browser-style app shell around WebView instead of a focused embedded experience
254
- - Using custom URL schemes for content that should just load over HTTPS
255
- - Forgetting that `WebPage` is main-actor-isolated
256
-
257
- ## Review Checklist
258
-
259
- - [ ] `WebView` and `WebPage` are the default path for iOS 26+ SwiftUI web content
260
- - [ ] `ASWebAuthenticationSession` is used for auth flows instead of embedded web views
261
- - [ ] `WebPage` is used whenever the app needs state observation, JS calls, or policy control
262
- - [ ] Navigation policies only intercept the URLs the app actually owns or needs to reroute
263
- - [ ] External domains open externally when appropriate
264
- - [ ] JavaScript return values are cast defensively to concrete Swift types
265
- - [ ] Custom URL schemes are used only for real app-owned resources
266
- - [ ] Back/forward gestures or controls are enabled when multi-page browsing is expected
267
- - [ ] The web experience adds focused native value instead of behaving like a thin browser shell
268
- - [ ] Fallback to `WKWebView` is justified by deployment target or missing API needs
183
+ Ordinary remote content should come over HTTPS, not through a custom scheme.
184
+ Handler implementation and cancellation are covered in
185
+ [scheme handler notes](references/local-content-and-custom-schemes.md).
186
+
187
+ ## View modifiers
188
+
189
+ - `webViewBackForwardNavigationGestures(_:)`: turn on swipe back and forward
190
+ when people will visit several pages.
191
+ - `findNavigator(isPresented:)`: Find in Page for long, document-like content.
192
+ - `webViewScrollPosition(_:)` and `webViewOnScrollGeometryChange(for:of:action:)`:
193
+ sync scrolling only when there is a sidebar, a table of contents or another
194
+ explicit navigation control.
195
+
196
+ The HIG asks for back and forward support where it helps, but an app's web
197
+ view should not grow into a general-purpose browser.
198
+
199
+ ## Common mistakes
200
+
201
+ - Reaching for a `WKWebView` wrapper in a SwiftUI app that targets iOS 26+.
202
+ - Running OAuth inside an embedded web view.
203
+ - Starting with `WebView(url:)` and bolting on `WebPage` later once state,
204
+ JavaScript or navigation control turns out to be needed.
205
+ - Treating `callJavaScript` as if it were `WKScriptMessageHandler`.
206
+ - Keeping every link in the app when other domains should open outside it.
207
+ - Building a browser shell (address bar, tabs) around the web view.
208
+ - Using a custom scheme for content that should load over HTTPS.
209
+ - Touching a `WebPage` off the main actor; the type is `@MainActor`.
210
+
211
+ ## Review checklist
212
+
213
+ - [ ] iOS 26+ screens start from `WebView` plus `WebPage`
214
+ - [ ] Sign-in goes through `ASWebAuthenticationSession`
215
+ - [ ] A `WebPage` exists wherever state, JavaScript or policy control is needed
216
+ - [ ] The navigation decider only intercepts URLs the app owns or reroutes
217
+ - [ ] Other domains open outside the app where that is the better experience
218
+ - [ ] JavaScript results are cast defensively
219
+ - [ ] Custom schemes serve only genuine app-owned resources
220
+ - [ ] Multi-page browsing has back and forward gestures or controls
221
+ - [ ] The screen offers something native and specific, not a wrapped website
222
+ - [ ] Each remaining `WKWebView` has a reason: an older deployment target or a missing API
269
223
 
270
224
  ## References
271
225
 
272
- - Loading and observation: [references/loading-and-observation.md](references/loading-and-observation.md)
273
- - Navigation and JavaScript: [references/navigation-and-javascript.md](references/navigation-and-javascript.md)
274
- - Local content and custom schemes: [references/local-content-and-custom-schemes.md](references/local-content-and-custom-schemes.md)
275
- - Migration and fallbacks: [references/migration-and-fallbacks.md](references/migration-and-fallbacks.md)
226
+ - [page loading notes](references/loading-and-observation.md): URL-only views, controlled loading, progress and title, navigation events, ephemeral pages, user agents
227
+ - [policy and script notes](references/navigation-and-javascript.md): deciders, external links, calling JavaScript, arguments, page-to-app signals
228
+ - [scheme handler notes](references/local-content-and-custom-schemes.md): scheme handlers, responses, bundled files, cancellation
229
+ - [migration notes](references/migration-and-fallbacks.md): moving off `WKWebView` wrappers, Safari and sign-in boundaries, testing
@@ -1,151 +1,140 @@
1
- # Loading and Observation
1
+ # Loading and observing pages
2
2
 
3
- ## Contents
4
- - Simple `WebView(url:)`
5
- - Controlled `WebPage` loading
6
- - Observing progress and title
7
- - Observing navigation events
8
- - Ephemeral pages and custom user agents
3
+ Part of the `swiftui-webkit` skill ([../SKILL.md](../SKILL.md)). All code
4
+ needs iOS 26, iPadOS 26, macOS 26 or visionOS 26 and `import WebKit`.
9
5
 
10
- ## Simple `WebView(url:)`
6
+ ## The URL-only view
11
7
 
12
- Use `WebView(url:)` when the app only needs to display a URL and does not need explicit page control.
8
+ When all you need is to show a page and let people move back and forth,
9
+ `WebView(url:)` plus the gesture modifier is the least code:
13
10
 
14
11
  ```swift
15
- import SwiftUI
16
- import WebKit
17
-
18
- struct MarketingPageView: View {
19
- let url: URL
12
+ struct PolicyPage: View {
13
+ let link: URL
20
14
 
21
15
  var body: some View {
22
- WebView(url: url)
16
+ WebView(url: link)
23
17
  .webViewBackForwardNavigationGestures(.enabled)
24
18
  }
25
19
  }
26
20
  ```
27
21
 
28
- This is the lowest-friction path for embedded content.
29
-
30
- ## Controlled `WebPage` loading
22
+ ## Loading through a WebPage
31
23
 
32
- Create a `WebPage` when the app needs to drive loading itself.
24
+ A model that owns the page can keep the last failure for the UI:
33
25
 
34
26
  ```swift
35
27
  @Observable
36
28
  @MainActor
37
- final class ArticleModel {
29
+ final class HelpCenterModel {
38
30
  let page = WebPage()
39
- var lastError: String?
31
+ var failure: Error?
40
32
 
41
- func load(_ url: URL) async {
33
+ func show(_ address: URL) async {
34
+ failure = nil
42
35
  do {
43
- for try await _ in page.load(URLRequest(url: url)) {
44
- }
36
+ for try await _ in page.load(URLRequest(url: address)) { }
45
37
  } catch {
46
- lastError = error.localizedDescription
38
+ failure = error
47
39
  }
48
40
  }
49
41
  }
50
42
  ```
51
43
 
52
- ```swift
53
- struct ArticleDetailView: View {
54
- @State private var model = ArticleModel()
55
- let url: URL
44
+ The other load entry points return the same kind of event sequence:
56
45
 
57
- var body: some View {
58
- WebView(model.page)
59
- .task {
60
- await model.load(url)
61
- }
62
- }
63
- }
46
+ ```swift
47
+ _ = page.load(address)
48
+ _ = page.load(html: "<h1>Offline</h1><p>Try again later.</p>") // baseURL defaults to about:blank
49
+ _ = page.load(markupData,
50
+ mimeType: "text/html",
51
+ characterEncoding: .utf8,
52
+ baseURL: bundleFolder)
64
53
  ```
65
54
 
66
- You can also load:
67
- - `for try await _ in page.load(url) { }`
68
- - `for try await _ in page.load(html: htmlString, baseURL: baseURL) { }`
69
- - `for try await _ in page.load(data, mimeType: "text/html", characterEncoding: "utf-8", baseURL: baseURL) { }`
55
+ Iterate the returned sequence (or ignore it) depending on whether the caller
56
+ cares when the load ends. `characterEncoding` takes a `String.Encoding`, not a
57
+ string like `"utf-8"`.
70
58
 
71
- ## Observing progress and title
59
+ ## Progress, title and other state
72
60
 
73
- `WebPage` is observable, so SwiftUI can bind directly to its state.
61
+ Besides `title`, `url`, `isLoading`, `estimatedProgress` and
62
+ `backForwardList`, a page reports `themeColor` (the page's theme colour, if
63
+ any) and `hasOnlySecureContent`.
74
64
 
75
65
  ```swift
76
- struct ReaderView: View {
77
- @State private var page = WebPage()
66
+ struct DocsPane: View {
67
+ @State private var model = HelpCenterModel()
68
+ let home: URL
78
69
 
79
70
  var body: some View {
80
- WebView(page)
81
- .navigationTitle(page.title ?? "Loading")
71
+ WebView(model.page)
72
+ .navigationTitle(model.page.title)
73
+ .toolbarBackground(model.page.themeColor ?? .clear, for: .navigationBar)
82
74
  .overlay(alignment: .top) {
83
- if page.isLoading {
84
- ProgressView(value: page.estimatedProgress)
85
- .padding()
86
- }
87
- }
88
- .task {
89
- do {
90
- for try await _ in page.load(URLRequest(url: URL(string: "https://example.com/docs")!)) {
91
- }
92
- } catch {
93
- // Handle load failure.
75
+ if model.page.isLoading {
76
+ ProgressView(value: model.page.estimatedProgress)
77
+ .padding(.horizontal)
94
78
  }
95
79
  }
80
+ .task { await model.show(home) }
96
81
  }
97
82
  }
98
83
  ```
99
84
 
100
- Useful properties:
101
- - `title`
102
- - `url`
103
- - `isLoading`
104
- - `estimatedProgress`
105
- - `themeColor`
106
- - `hasOnlySecureContent`
107
- - `backForwardList`
108
-
109
- ## Observing navigation events
85
+ ## Following navigation events
110
86
 
111
- Use `currentNavigationEvent` for a lightweight current-state view. Use `navigations` to observe the full sequence of navigation events.
87
+ `load` returns the events of that one navigation; `page.navigations` delivers
88
+ the events of every navigation the page makes, including link taps. Both are
89
+ throwing sequences. The event cases are `.startedProvisionalNavigation`,
90
+ `.receivedServerRedirect`, `.committed` and `.finished`. Failures are not
91
+ events: they arrive as thrown errors, typically a `WebPage.NavigationError`
92
+ such as `.failedProvisionalNavigation(_:)`, `.webContentProcessTerminated`
93
+ or `.pageClosed`.
112
94
 
113
95
  ```swift
114
96
  @MainActor
115
- func observeNavigations(for page: WebPage) {
116
- Task {
117
- for await event in page.navigations {
97
+ func watch(_ page: WebPage) async {
98
+ do {
99
+ for try await event in page.navigations {
118
100
  switch event {
119
101
  case .finished:
120
- print("Navigation finished")
121
- case .failed(let error), .failedProvisionalNavigation(let error):
122
- print("Navigation failed: \(error)")
102
+ await collectHeadings(from: page) // follow-up work goes here
123
103
  default:
124
104
  break
125
105
  }
126
106
  }
107
+ } catch WebPage.NavigationError.failedProvisionalNavigation(let reason) {
108
+ report(reason)
109
+ } catch {
110
+ report(error)
127
111
  }
128
112
  }
129
113
  ```
130
114
 
131
- This is the right place to trigger follow-up work like parsing headings after a finished navigation.
115
+ The finished event is the right moment for work that needs the loaded
116
+ document, such as reading its headings. For lightweight UI, the observable
117
+ properties (`isLoading`, `estimatedProgress`) are usually enough; there is no
118
+ separate "current event" property.
132
119
 
133
- ## Ephemeral pages and custom user agents
120
+ ## Throwaway pages and custom user agents
134
121
 
135
- Use `WebPage.Configuration` when you need a nonpersistent page, custom user agent, or tighter loading rules.
122
+ For a quick metadata fetch or an isolated session, configure a page that
123
+ keeps nothing around:
136
124
 
137
125
  ```swift
138
126
  @MainActor
139
- func makeMetadataPage() -> WebPage {
140
- var configuration = WebPage.Configuration()
141
- configuration.loadsSubresources = false
142
- configuration.defaultNavigationPreferences.allowsContentJavaScript = false
143
- configuration.websiteDataStore = .nonPersistent()
144
-
145
- let page = WebPage(configuration: configuration)
146
- page.customUserAgent = "MetadataBot/1.0"
127
+ func makeScratchPage() -> WebPage {
128
+ var setup = WebPage.Configuration()
129
+ setup.loadsSubresources = false
130
+ setup.defaultNavigationPreferences.allowsContentJavaScript = false
131
+ setup.websiteDataStore = .nonPersistent()
132
+
133
+ let page = WebPage(configuration: setup)
134
+ page.customUserAgent = "ExampleReader/2.1"
147
135
  return page
148
136
  }
149
137
  ```
150
138
 
151
- Use nonpersistent pages when you want an isolated web session or metadata fetch path without shared cookies or long-lived website data.
139
+ A non-persistent data store means no shared cookies and no long-lived website
140
+ data, so each such page is its own sealed session.