@jskit-ai/agent-docs 0.1.149 → 0.1.151

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 (240) hide show
  1. package/guide/agent/app-setup/existing-application-migration.md +8 -6
  2. package/guide/agent/app-setup/initial-scaffolding.md +9 -7
  3. package/guide/agent/app-setup/quickstart.md +9 -6
  4. package/guide/agent/framework/application-operations.md +91 -0
  5. package/guide/agent/framework/crud-operations.md +83 -0
  6. package/guide/agent/framework/material-3.md +113 -0
  7. package/guide/agent/framework/ui-operations.md +79 -0
  8. package/guide/agent/index.md +13 -3
  9. package/package.json +1 -1
  10. package/patterns/feature-package/example/booking-engine/package.json +1 -1
  11. package/patterns/minimal-foundation/PATTERN.md +2 -0
  12. package/patterns/minimal-foundation/example/AGENTS.md +12 -8
  13. package/patterns/minimal-foundation/example/Procfile +0 -1
  14. package/patterns/minimal-foundation/example/package.json +4 -5
  15. package/patterns/minimal-foundation/example/src/pages/home/index.vue +0 -27
  16. package/patterns/minimal-foundation/example/tests/e2e/base-shell.spec.ts +1 -1
  17. package/patterns/page-scaffolding.md +5 -3
  18. package/patterns/shell-foundation/PATTERN.md +2 -0
  19. package/patterns/shell-foundation/example/AGENTS.md +12 -8
  20. package/patterns/shell-foundation/example/Procfile +0 -1
  21. package/patterns/shell-foundation/example/package.json +5 -6
  22. package/patterns/shell-foundation/example/packages/main/package.json +1 -1
  23. package/patterns/shell-foundation/example/src/pages/home/index.vue +5 -31
  24. package/patterns/shell-foundation/example/src/pages/home/settings/general/index.vue +3 -6
  25. package/patterns/shell-foundation/example/src/pages/home/settings.vue +0 -19
  26. package/patterns/shell-foundation/example/tests/e2e/base-shell.spec.ts +1 -1
  27. package/patterns/ui-contract.md +2 -0
  28. package/patterns/ui-testing.md +1 -1
  29. package/reference/autogen/PATTERN_INDEX.md +61 -61
  30. package/skills/jskit/SKILL.md +8 -5
  31. package/skills/jskit/references/app-operations.md +12 -11
  32. package/skills/jskit/references/crud-operations.md +10 -6
  33. package/skills/jskit/references/existing-application-migration.md +9 -12
  34. package/skills/jskit/references/material-3.md +5 -2
  35. package/skills/jskit/references/pattern-index.md +61 -61
  36. package/skills/jskit/references/patterns/app/minimal-foundation/PATTERN.md +107 -0
  37. package/skills/jskit/references/patterns/app/minimal-foundation/example/.nvmrc +1 -0
  38. package/skills/jskit/references/patterns/app/minimal-foundation/example/AGENTS.md +21 -0
  39. package/skills/jskit/references/patterns/app/minimal-foundation/example/Procfile +1 -0
  40. package/skills/jskit/references/patterns/app/minimal-foundation/example/app.json +14 -0
  41. package/skills/jskit/references/patterns/app/minimal-foundation/example/bin/develop.js +71 -0
  42. package/skills/jskit/references/patterns/app/minimal-foundation/example/bin/server.js +8 -0
  43. package/skills/jskit/references/patterns/app/minimal-foundation/example/config/public.js +40 -0
  44. package/skills/jskit/references/patterns/app/minimal-foundation/example/config/server.js +1 -0
  45. package/skills/jskit/references/patterns/app/minimal-foundation/example/config/surfaceAccessPolicies.js +3 -0
  46. package/skills/jskit/references/patterns/app/minimal-foundation/example/eslint.config.mjs +19 -0
  47. package/skills/jskit/references/patterns/app/minimal-foundation/example/favicon.svg +7 -0
  48. package/skills/jskit/references/patterns/app/minimal-foundation/example/gitignore +9 -0
  49. package/skills/jskit/references/patterns/app/minimal-foundation/example/index.html +13 -0
  50. package/skills/jskit/references/patterns/app/minimal-foundation/example/jsconfig.json +8 -0
  51. package/skills/jskit/references/patterns/app/minimal-foundation/example/package.json +62 -0
  52. package/skills/jskit/references/patterns/app/minimal-foundation/example/packages/main/package.json +42 -0
  53. package/skills/jskit/references/patterns/app/minimal-foundation/example/packages/main/src/shared/index.js +10 -0
  54. package/skills/jskit/references/patterns/app/minimal-foundation/example/packages/main/src/shared/schemas/index.js +22 -0
  55. package/skills/jskit/references/patterns/app/minimal-foundation/example/playwright.config.mjs +31 -0
  56. package/skills/jskit/references/patterns/app/minimal-foundation/example/server/lib/runtimeEnv.js +45 -0
  57. package/skills/jskit/references/patterns/app/minimal-foundation/example/server/lib/surfaceRuntime.js +10 -0
  58. package/skills/jskit/references/patterns/app/minimal-foundation/example/server.js +195 -0
  59. package/skills/jskit/references/patterns/app/minimal-foundation/example/src/App.vue +13 -0
  60. package/skills/jskit/references/patterns/app/minimal-foundation/example/src/main.js +85 -0
  61. package/skills/jskit/references/patterns/app/minimal-foundation/example/src/pages/home/index.vue +21 -0
  62. package/skills/jskit/references/patterns/app/minimal-foundation/example/src/pages/home.vue +13 -0
  63. package/skills/jskit/references/patterns/app/minimal-foundation/example/src/views/NotFound.vue +13 -0
  64. package/skills/jskit/references/patterns/app/minimal-foundation/example/tests/client/smoke.vitest.js +7 -0
  65. package/skills/jskit/references/patterns/app/minimal-foundation/example/tests/e2e/base-shell.spec.ts +23 -0
  66. package/skills/jskit/references/patterns/app/minimal-foundation/example/tests/server/smoke.test.js +16 -0
  67. package/skills/jskit/references/patterns/app/minimal-foundation/example/vite.config.mjs +80 -0
  68. package/skills/jskit/references/patterns/app/shell-foundation/PATTERN.md +113 -0
  69. package/skills/jskit/references/patterns/app/shell-foundation/example/.nvmrc +1 -0
  70. package/skills/jskit/references/patterns/app/shell-foundation/example/AGENTS.md +21 -0
  71. package/skills/jskit/references/patterns/app/shell-foundation/example/Procfile +1 -0
  72. package/skills/jskit/references/patterns/app/shell-foundation/example/app.json +14 -0
  73. package/skills/jskit/references/patterns/app/shell-foundation/example/bin/develop.js +71 -0
  74. package/skills/jskit/references/patterns/app/shell-foundation/example/bin/server.js +8 -0
  75. package/skills/jskit/references/patterns/app/shell-foundation/example/config/public.js +40 -0
  76. package/skills/jskit/references/patterns/app/shell-foundation/example/config/server.js +1 -0
  77. package/skills/jskit/references/patterns/app/shell-foundation/example/config/surfaceAccessPolicies.js +3 -0
  78. package/skills/jskit/references/patterns/app/shell-foundation/example/eslint.config.mjs +19 -0
  79. package/skills/jskit/references/patterns/app/shell-foundation/example/favicon.svg +7 -0
  80. package/skills/jskit/references/patterns/app/shell-foundation/example/gitignore +9 -0
  81. package/skills/jskit/references/patterns/app/shell-foundation/example/index.html +13 -0
  82. package/skills/jskit/references/patterns/app/shell-foundation/example/jsconfig.json +8 -0
  83. package/skills/jskit/references/patterns/app/shell-foundation/example/package.json +64 -0
  84. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/package.json +56 -0
  85. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/src/client/index.js +9 -0
  86. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/src/client/providers/MainClientProvider.js +18 -0
  87. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/src/shared/index.js +10 -0
  88. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/src/shared/schemas/index.js +22 -0
  89. package/skills/jskit/references/patterns/app/shell-foundation/example/playwright.config.mjs +31 -0
  90. package/skills/jskit/references/patterns/app/shell-foundation/example/server/lib/runtimeEnv.js +45 -0
  91. package/skills/jskit/references/patterns/app/shell-foundation/example/server/lib/surfaceRuntime.js +10 -0
  92. package/skills/jskit/references/patterns/app/shell-foundation/example/server.js +195 -0
  93. package/skills/jskit/references/patterns/app/shell-foundation/example/src/App.vue +11 -0
  94. package/skills/jskit/references/patterns/app/shell-foundation/example/src/components/ShellLayout.vue +12 -0
  95. package/skills/jskit/references/patterns/app/shell-foundation/example/src/components/menus/MenuLinkItem.vue +30 -0
  96. package/skills/jskit/references/patterns/app/shell-foundation/example/src/components/menus/SurfaceAwareMenuLinkItem.vue +42 -0
  97. package/skills/jskit/references/patterns/app/shell-foundation/example/src/components/menus/TabLinkItem.vue +42 -0
  98. package/skills/jskit/references/patterns/app/shell-foundation/example/src/error.js +19 -0
  99. package/skills/jskit/references/patterns/app/shell-foundation/example/src/main.js +85 -0
  100. package/skills/jskit/references/patterns/app/shell-foundation/example/src/pages/home/index.vue +90 -0
  101. package/skills/jskit/references/patterns/app/shell-foundation/example/src/pages/home/settings/general/index.vue +37 -0
  102. package/skills/jskit/references/patterns/app/shell-foundation/example/src/pages/home/settings/index.vue +7 -0
  103. package/skills/jskit/references/patterns/app/shell-foundation/example/src/pages/home/settings.vue +90 -0
  104. package/skills/jskit/references/patterns/app/shell-foundation/example/src/pages/home.vue +20 -0
  105. package/skills/jskit/references/patterns/app/shell-foundation/example/src/placement.js +56 -0
  106. package/skills/jskit/references/patterns/app/shell-foundation/example/src/placementTopology.js +149 -0
  107. package/skills/jskit/references/patterns/app/shell-foundation/example/src/views/NotFound.vue +13 -0
  108. package/skills/jskit/references/patterns/app/shell-foundation/example/tests/client/smoke.vitest.js +7 -0
  109. package/skills/jskit/references/patterns/app/shell-foundation/example/tests/e2e/adaptive-shell.spec.ts +10 -0
  110. package/skills/jskit/references/patterns/app/shell-foundation/example/tests/e2e/base-shell.spec.ts +23 -0
  111. package/skills/jskit/references/patterns/app/shell-foundation/example/tests/server/smoke.test.js +16 -0
  112. package/skills/jskit/references/patterns/app/shell-foundation/example/vite.config.mjs +80 -0
  113. package/skills/jskit/references/patterns/assistant/assistant-surface/PATTERN.md +77 -0
  114. package/skills/jskit/references/patterns/assistant/assistant-surface/example/config/public.js +19 -0
  115. package/skills/jskit/references/patterns/assistant/assistant-surface/example/config/server.js +9 -0
  116. package/skills/jskit/references/patterns/assistant/assistant-surface/example/src/pages/admin/assistant/index.vue +7 -0
  117. package/skills/jskit/references/patterns/assistant/assistant-surface/example/src/pages/admin/settings/assistant/index.vue +7 -0
  118. package/skills/jskit/references/patterns/assistant/assistant-surface/example/src/placement.js +38 -0
  119. package/skills/jskit/references/patterns/auth/auth-surface/PATTERN.md +90 -0
  120. package/skills/jskit/references/patterns/auth/auth-surface/example/src/pages/auth/login.vue +17 -0
  121. package/skills/jskit/references/patterns/auth/auth-surface/example/src/pages/auth/reset-password.vue +17 -0
  122. package/skills/jskit/references/patterns/auth/auth-surface/example/src/pages/auth/signout.vue +17 -0
  123. package/skills/jskit/references/patterns/auth/auth-surface/example/src/runtime/authGuardRuntime.js +7 -0
  124. package/skills/jskit/references/patterns/auth/auth-surface/example/src/runtime/authHttpClient.js +1 -0
  125. package/skills/jskit/references/patterns/auth/auth-surface/example/src/runtime/useSignOut.js +1 -0
  126. package/skills/jskit/references/patterns/auth/auth-surface/example/src/views/auth/LoginView.vue +7 -0
  127. package/skills/jskit/references/patterns/auth/auth-surface/example/src/views/auth/ResetPasswordView.vue +7 -0
  128. package/skills/jskit/references/patterns/auth/auth-surface/example/src/views/auth/SignOutView.vue +7 -0
  129. package/skills/jskit/references/patterns/auth/auth-surface/example/tools/preview-identity +5 -0
  130. package/skills/jskit/references/patterns/auth/supabase-auth/PATTERN.md +67 -0
  131. package/skills/jskit/references/patterns/auth/supabase-auth/example/.env.example +4 -0
  132. package/skills/jskit/references/patterns/auth/supabase-auth/example/config/server.js +11 -0
  133. package/skills/jskit/references/patterns/auth/supabase-auth/example/package.json +7 -0
  134. package/skills/jskit/references/patterns/console/console-surface/PATTERN.md +59 -0
  135. package/skills/jskit/references/patterns/console/console-surface/example/src/pages/console/index.vue +43 -0
  136. package/skills/jskit/references/patterns/console/console-surface/example/src/pages/console/settings/index.vue +16 -0
  137. package/skills/jskit/references/patterns/console/console-surface/example/src/pages/console/settings.vue +81 -0
  138. package/skills/jskit/references/patterns/console/console-surface/example/src/pages/console.vue +20 -0
  139. package/skills/jskit/references/patterns/crud/crud-screen-set/PATTERN.md +89 -0
  140. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/BookEditPage.vue +52 -0
  141. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/BookFormFields.vue +52 -0
  142. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/BookListPage.vue +50 -0
  143. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/BookNewPage.vue +43 -0
  144. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/BookViewPage.vue +49 -0
  145. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/formFields.js +31 -0
  146. package/skills/jskit/references/patterns/crud/crud-screen-set/example/books/listExtensions.js +9 -0
  147. package/skills/jskit/references/patterns/crud/json-api-resource-package/PATTERN.md +160 -0
  148. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/migrations/20260815000000_books.cjs +22 -0
  149. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/packages/books/package.json +41 -0
  150. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/packages/books/src/server/BooksFeature.js +13 -0
  151. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/packages/books/src/shared/bookResource.js +83 -0
  152. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/packages/books/src/shared/index.js +1 -0
  153. package/skills/jskit/references/patterns/crud/resource-contract/PATTERN.md +102 -0
  154. package/skills/jskit/references/patterns/crud/resource-contract/example/bookResource.js +87 -0
  155. package/skills/jskit/references/patterns/database/mysql-application/PATTERN.md +80 -0
  156. package/skills/jskit/references/patterns/database/mysql-application/example/.env.example +5 -0
  157. package/skills/jskit/references/patterns/database/mysql-application/example/.github/workflows/verify.yml +39 -0
  158. package/skills/jskit/references/patterns/database/mysql-application/example/knexfile.js +11 -0
  159. package/skills/jskit/references/patterns/database/mysql-application/example/package.json +13 -0
  160. package/skills/jskit/references/patterns/database/mysql-application/example/scripts/prepare-database.js +3 -0
  161. package/skills/jskit/references/patterns/database/postgres-application/PATTERN.md +80 -0
  162. package/skills/jskit/references/patterns/database/postgres-application/example/.env.example +5 -0
  163. package/skills/jskit/references/patterns/database/postgres-application/example/.github/workflows/verify.yml +38 -0
  164. package/skills/jskit/references/patterns/database/postgres-application/example/knexfile.js +11 -0
  165. package/skills/jskit/references/patterns/database/postgres-application/example/package.json +13 -0
  166. package/skills/jskit/references/patterns/database/postgres-application/example/scripts/prepare-database.js +3 -0
  167. package/skills/jskit/references/patterns/mobile/android-application/PATTERN.md +71 -0
  168. package/skills/jskit/references/patterns/mobile/android-application/example/capacitor.config.json +10 -0
  169. package/skills/jskit/references/patterns/realtime/realtime-application/PATTERN.md +69 -0
  170. package/skills/jskit/references/patterns/realtime/realtime-application/example/.env.example +1 -0
  171. package/skills/jskit/references/patterns/realtime/realtime-application/example/package.json +8 -0
  172. package/skills/jskit/references/patterns/realtime/realtime-application/example/src/placement.js +17 -0
  173. package/skills/jskit/references/patterns/server/feature-package/PATTERN.md +108 -0
  174. package/skills/jskit/references/patterns/server/feature-package/example/booking-engine/package.json +48 -0
  175. package/skills/jskit/references/patterns/server/feature-package/example/booking-engine/src/server/BookingEngineProvider.js +33 -0
  176. package/skills/jskit/references/patterns/server/feature-package/example/booking-engine/src/server/actions.js +26 -0
  177. package/skills/jskit/references/patterns/server/feature-package/example/booking-engine/src/server/inputSchemas.js +19 -0
  178. package/skills/jskit/references/patterns/server/feature-package/example/variations/AvailabilityEngineProvider.js +31 -0
  179. package/skills/jskit/references/patterns/server/feature-package/example/variations/InvoiceRollupProvider.js +36 -0
  180. package/skills/jskit/references/patterns/server/feature-package/example/variations/customKnexRepository.js +34 -0
  181. package/skills/jskit/references/patterns/server/feature-package/example/variations/orchestratorService.js +23 -0
  182. package/skills/jskit/references/patterns/shell/application-shell/PATTERN.md +67 -0
  183. package/skills/jskit/references/patterns/shell/application-shell/example/expected-existing/src/App.vue +13 -0
  184. package/skills/jskit/references/patterns/shell/application-shell/example/expected-existing/src/pages/home/index.vue +21 -0
  185. package/skills/jskit/references/patterns/shell/application-shell/example/expected-existing/src/pages/home.vue +13 -0
  186. package/skills/jskit/references/patterns/shell/application-shell/example/src/App.vue +11 -0
  187. package/skills/jskit/references/patterns/shell/application-shell/example/src/components/ShellLayout.vue +13 -0
  188. package/skills/jskit/references/patterns/shell/application-shell/example/src/components/menus/MenuLinkItem.vue +30 -0
  189. package/skills/jskit/references/patterns/shell/application-shell/example/src/components/menus/SurfaceAwareMenuLinkItem.vue +42 -0
  190. package/skills/jskit/references/patterns/shell/application-shell/example/src/components/menus/TabLinkItem.vue +42 -0
  191. package/skills/jskit/references/patterns/shell/application-shell/example/src/error.js +19 -0
  192. package/skills/jskit/references/patterns/shell/application-shell/example/src/pages/home/index.vue +80 -0
  193. package/skills/jskit/references/patterns/shell/application-shell/example/src/pages/home/settings/general/index.vue +37 -0
  194. package/skills/jskit/references/patterns/shell/application-shell/example/src/pages/home/settings/index.vue +7 -0
  195. package/skills/jskit/references/patterns/shell/application-shell/example/src/pages/home/settings.vue +90 -0
  196. package/skills/jskit/references/patterns/shell/application-shell/example/src/pages/home.vue +20 -0
  197. package/skills/jskit/references/patterns/shell/application-shell/example/src/placement.js +56 -0
  198. package/skills/jskit/references/patterns/shell/application-shell/example/src/placementTopology.js +149 -0
  199. package/skills/jskit/references/patterns/shell/application-shell/example/tests/e2e/adaptive-shell.spec.ts +10 -0
  200. package/skills/jskit/references/patterns/ui/page-and-placement/PATTERN.md +77 -0
  201. package/skills/jskit/references/patterns/ui/page-and-placement/example/packages/main/src/client/providers/MainClientProvider.js +14 -0
  202. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/components/SyncStatusElement.vue +16 -0
  203. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/pages/home/reports/activity.vue +7 -0
  204. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/pages/home/reports/index.vue +7 -0
  205. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/pages/home/reports/overview.vue +7 -0
  206. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/pages/home/reports.vue +25 -0
  207. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/placement.js +52 -0
  208. package/skills/jskit/references/patterns/ui/page-and-placement/example/src/placementTopology.js +29 -0
  209. package/skills/jskit/references/patterns/users/account-settings/PATTERN.md +63 -0
  210. package/skills/jskit/references/patterns/users/account-settings/example/src/components/account/settings/AccountSettingsNotificationsSection.vue +67 -0
  211. package/skills/jskit/references/patterns/users/account-settings/example/src/components/account/settings/AccountSettingsPreferencesSection.vue +137 -0
  212. package/skills/jskit/references/patterns/users/account-settings/example/src/components/account/settings/AccountSettingsProfileSection.vue +106 -0
  213. package/skills/jskit/references/patterns/users/account-settings/example/src/pages/account/index.vue +17 -0
  214. package/skills/jskit/references/patterns/users/user-administration-server/PATTERN.md +64 -0
  215. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users/package.json +42 -0
  216. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users/src/server/UsersFeature.js +13 -0
  217. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users/src/shared/index.js +1 -0
  218. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users/src/shared/userResource.js +69 -0
  219. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users-workspace/package.json +43 -0
  220. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users-workspace/src/server/UsersWorkspaceFeature.js +22 -0
  221. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users-workspace/src/shared/index.js +1 -0
  222. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users-workspace/src/shared/userResource.js +56 -0
  223. package/skills/jskit/references/patterns/workspaces/workspace-server/PATTERN.md +60 -0
  224. package/skills/jskit/references/patterns/workspaces/workspace-server/example/config/roles.js +27 -0
  225. package/skills/jskit/references/patterns/workspaces/workspace-server/example/packages/main/src/server/email/workspaceInviteEmail.js +23 -0
  226. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/PATTERN.md +65 -0
  227. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/packages/main/src/client/components/AccountPendingInvitesCue.vue +106 -0
  228. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/packages/main/src/client/components/AccountSettingsInvitesSection.vue +7 -0
  229. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/components/WorkspaceNotFoundCard.vue +42 -0
  230. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/composables/useWorkspaceNotFoundState.js +41 -0
  231. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/pages/admin/members/index.vue +7 -0
  232. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/pages/admin/workspace/settings/index.vue +15 -0
  233. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/pages/admin/workspace/settings.vue +81 -0
  234. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/pages/invite/[token].vue +7 -0
  235. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/surfaces/admin/index.vue +58 -0
  236. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/surfaces/admin/root.vue +20 -0
  237. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/surfaces/app/index.vue +31 -0
  238. package/skills/jskit/references/patterns/workspaces/workspace-surfaces/example/src/surfaces/app/root.vue +20 -0
  239. package/skills/jskit/references/ui-operations.md +7 -4
  240. package/templates/app/AGENTS.md +12 -8
@@ -0,0 +1,80 @@
1
+ <script setup>
2
+ import { computed } from "vue";
3
+ import { useQuery } from "@tanstack/vue-query";
4
+
5
+ const healthQuery = useQuery({
6
+ queryKey: ["shell-web", "health"],
7
+ queryFn: async () => {
8
+ const response = await fetch("/api/health");
9
+ if (!response.ok) {
10
+ throw new Error("Health request failed.");
11
+ }
12
+ return response.json();
13
+ },
14
+ refetchOnWindowFocus: false
15
+ });
16
+
17
+ const health = computed(() => {
18
+ if (healthQuery.isPending.value || healthQuery.isFetching.value) {
19
+ return "loading...";
20
+ }
21
+
22
+ if (healthQuery.error.value) {
23
+ return "unreachable";
24
+ }
25
+
26
+ return healthQuery.data.value?.ok ? "ok" : "unhealthy";
27
+ });
28
+ </script>
29
+
30
+ <template>
31
+ <section class="home-surface-screen d-flex flex-column ga-4">
32
+ <div class="home-surface-screen__actions">
33
+ <v-btn color="primary" variant="flat" to="/home/settings/general">Settings</v-btn>
34
+ </div>
35
+
36
+ <v-sheet rounded="lg" border class="home-surface-screen__panel">
37
+ <div class="home-surface-screen__status">
38
+ <span class="text-caption text-medium-emphasis">Service health</span>
39
+ <strong>{{ health }}</strong>
40
+ </div>
41
+ <v-divider vertical class="d-none d-sm-block" />
42
+ <div class="home-surface-screen__status">
43
+ <span class="text-caption text-medium-emphasis">Route</span>
44
+ <strong>/home</strong>
45
+ </div>
46
+ </v-sheet>
47
+ </section>
48
+ </template>
49
+
50
+ <style scoped>
51
+ .home-surface-screen {
52
+ --home-surface-panel-padding: 1rem;
53
+ }
54
+
55
+ .home-surface-screen__actions {
56
+ display: flex;
57
+ justify-content: flex-end;
58
+ }
59
+
60
+ .home-surface-screen__panel {
61
+ align-items: stretch;
62
+ display: flex;
63
+ flex-wrap: wrap;
64
+ gap: 1rem;
65
+ padding: var(--home-surface-panel-padding);
66
+ }
67
+
68
+ .home-surface-screen__status {
69
+ display: grid;
70
+ gap: 0.15rem;
71
+ min-width: 9rem;
72
+ }
73
+
74
+ @media (max-width: 640px) {
75
+ .home-surface-screen__actions :deep(.v-btn) {
76
+ min-height: 48px;
77
+ width: 100%;
78
+ }
79
+ }
80
+ </style>
@@ -0,0 +1,37 @@
1
+ <script setup>
2
+ import { computed } from "vue";
3
+ import { useShellLayoutState } from "@jskit-ai/shell-web/client/composables/useShellLayoutState";
4
+
5
+ const { drawerDefaultOpen, setDrawerDefaultOpen } = useShellLayoutState();
6
+
7
+ const drawerDefaultOpenModel = computed({
8
+ get() {
9
+ return drawerDefaultOpen.value;
10
+ },
11
+ set(value) {
12
+ setDrawerDefaultOpen(Boolean(value));
13
+ }
14
+ });
15
+ </script>
16
+
17
+ <template>
18
+ <section class="settings-general-screen d-flex flex-column ga-4">
19
+ <p class="text-body-2 text-medium-emphasis mb-0">
20
+ On wider screens, collapsed navigation remains available as a rail. Phone layouts close the drawer and keep primary navigation in the bottom bar.
21
+ </p>
22
+
23
+ <v-switch
24
+ v-model="drawerDefaultOpenModel"
25
+ color="primary"
26
+ inset
27
+ hide-details="auto"
28
+ label="Start with expanded navigation on wider screens"
29
+ />
30
+ </section>
31
+ </template>
32
+
33
+ <style scoped>
34
+ .settings-general-screen :deep(.v-switch) {
35
+ min-height: 48px;
36
+ }
37
+ </style>
@@ -0,0 +1,7 @@
1
+ <script setup>
2
+ import { redirectToChild } from "@jskit-ai/kernel/client/pageRedirects";
3
+
4
+ definePage({
5
+ redirect: redirectToChild("general")
6
+ });
7
+ </script>
@@ -0,0 +1,90 @@
1
+ <script setup>
2
+ import ShellOutlet from "@jskit-ai/shell-web/client/components/ShellOutlet";
3
+ import { RouterView } from "vue-router";
4
+ </script>
5
+
6
+ <template>
7
+ <section class="settings-shell d-flex flex-column ga-4">
8
+ <v-sheet rounded="lg" border class="settings-shell__panel">
9
+ <div class="settings-shell__body">
10
+ <nav class="settings-shell__nav" aria-label="Home settings sections">
11
+ <v-list nav density="compact" rounded="lg">
12
+ <ShellOutlet target="home-settings:primary-menu" />
13
+ </v-list>
14
+ </nav>
15
+
16
+ <main class="settings-shell__content">
17
+ <RouterView />
18
+ </main>
19
+ </div>
20
+ </v-sheet>
21
+ </section>
22
+ </template>
23
+
24
+ <style scoped>
25
+ .settings-shell {
26
+ --settings-shell-panel-padding: 1rem;
27
+ }
28
+
29
+ .settings-shell__panel {
30
+ overflow: hidden;
31
+ }
32
+
33
+ .settings-shell__body {
34
+ display: grid;
35
+ gap: 1rem;
36
+ grid-template-columns: minmax(12rem, 16rem) minmax(0, 1fr);
37
+ padding: var(--settings-shell-panel-padding);
38
+ }
39
+
40
+ .settings-shell__content {
41
+ border-left: 1px solid rgba(var(--v-theme-on-surface), 0.18);
42
+ min-width: 0;
43
+ padding-left: 1rem;
44
+ }
45
+
46
+ .settings-shell__nav :deep(.v-list) {
47
+ padding: 0.35rem;
48
+ }
49
+
50
+ .settings-shell__nav :deep(.v-list-item) {
51
+ min-height: 48px;
52
+ padding-inline: 0.6rem 0.7rem;
53
+ }
54
+
55
+ .settings-shell__nav :deep(.v-list-item__prepend) {
56
+ margin-inline-end: 0;
57
+ }
58
+
59
+ .settings-shell__nav :deep(.v-list-item__spacer) {
60
+ min-width: 0.5rem;
61
+ width: 0.5rem;
62
+ }
63
+
64
+ .settings-shell__nav :deep(.v-list-item-title) {
65
+ line-height: 1.2;
66
+ }
67
+
68
+ @media (max-width: 960px) {
69
+ .settings-shell__body {
70
+ grid-template-columns: 1fr;
71
+ }
72
+
73
+ .settings-shell__nav :deep(.v-list) {
74
+ display: flex;
75
+ gap: 0.25rem;
76
+ overflow-x: auto;
77
+ scrollbar-width: thin;
78
+ }
79
+
80
+ .settings-shell__nav :deep(.v-list-item) {
81
+ flex: 0 0 auto;
82
+ min-height: 48px;
83
+ }
84
+
85
+ .settings-shell__content {
86
+ border-left: 0;
87
+ padding-left: 0;
88
+ }
89
+ }
90
+ </style>
@@ -0,0 +1,20 @@
1
+ <route lang="json">
2
+ {
3
+ "meta": {
4
+ "jskit": {
5
+ "surface": "home"
6
+ }
7
+ }
8
+ }
9
+ </route>
10
+
11
+ <script setup>
12
+ import ShellLayout from "@/components/ShellLayout.vue";
13
+ import { RouterView } from "vue-router";
14
+ </script>
15
+
16
+ <template>
17
+ <ShellLayout title="" subtitle="">
18
+ <RouterView />
19
+ </ShellLayout>
20
+ </template>
@@ -0,0 +1,56 @@
1
+ import { createPlacementRegistry } from "@jskit-ai/shell-web/client/placement";
2
+
3
+ const registry = createPlacementRegistry();
4
+ const { addPlacement } = registry;
5
+
6
+ export { addPlacement };
7
+
8
+ // Keep the default export near the top so module installers can append addPlacement(...)
9
+ // blocks at the bottom of this file without changing the export section.
10
+ export default function getPlacements() {
11
+ return registry.build();
12
+ }
13
+
14
+ addPlacement({
15
+ id: "shell-web.home.menu.home",
16
+ target: "shell.primary-nav",
17
+ kind: "link",
18
+ surfaces: ["home"],
19
+ order: 50,
20
+ props: {
21
+ label: "Home",
22
+ surface: "home",
23
+ scopedSuffix: "/",
24
+ unscopedSuffix: "/",
25
+ exact: true
26
+ }
27
+ });
28
+
29
+ addPlacement({
30
+ id: "shell-web.home.menu.settings",
31
+ target: "shell.primary-nav",
32
+ kind: "link",
33
+ surfaces: ["home"],
34
+ order: 100,
35
+ props: {
36
+ label: "Settings",
37
+ surface: "home",
38
+ scopedSuffix: "/settings",
39
+ unscopedSuffix: "/settings"
40
+ }
41
+ });
42
+
43
+ addPlacement({
44
+ id: "shell-web.home.settings.general",
45
+ target: "page.section-nav",
46
+ owner: "home-settings",
47
+ kind: "link",
48
+ surfaces: ["home"],
49
+ order: 100,
50
+ props: {
51
+ label: "General",
52
+ surface: "home",
53
+ scopedSuffix: "/settings/general",
54
+ unscopedSuffix: "/settings/general"
55
+ }
56
+ });
@@ -0,0 +1,149 @@
1
+ const placements = [];
2
+
3
+ function addPlacementTopology(value = {}) {
4
+ placements.push(value);
5
+ }
6
+
7
+ export { addPlacementTopology };
8
+ export default { placements };
9
+
10
+ const menuLinkRenderers = Object.freeze({
11
+ link: "local.main.ui.surface-aware-menu-link-item"
12
+ });
13
+
14
+ const bottomNavLinkRenderers = Object.freeze({
15
+ link: "local.main.ui.tab-link-item"
16
+ });
17
+
18
+ addPlacementTopology({
19
+ id: "shell.primary-nav",
20
+ description: "Primary top-level navigation for the current surface.",
21
+ surfaces: ["*"],
22
+ default: true,
23
+ variants: {
24
+ compact: {
25
+ outlet: "shell-layout:primary-bottom-nav",
26
+ renderers: bottomNavLinkRenderers
27
+ },
28
+ medium: {
29
+ outlet: "shell-layout:primary-menu",
30
+ renderers: menuLinkRenderers
31
+ },
32
+ expanded: {
33
+ outlet: "shell-layout:primary-menu",
34
+ renderers: menuLinkRenderers
35
+ }
36
+ }
37
+ });
38
+
39
+ addPlacementTopology({
40
+ id: "shell.secondary-nav",
41
+ description: "Secondary navigation for the current surface.",
42
+ surfaces: ["*"],
43
+ variants: {
44
+ compact: {
45
+ outlet: "shell-layout:secondary-menu",
46
+ renderers: menuLinkRenderers
47
+ },
48
+ medium: {
49
+ outlet: "shell-layout:secondary-menu",
50
+ renderers: menuLinkRenderers
51
+ },
52
+ expanded: {
53
+ outlet: "shell-layout:secondary-menu",
54
+ renderers: menuLinkRenderers
55
+ }
56
+ }
57
+ });
58
+
59
+ addPlacementTopology({
60
+ id: "shell.identity",
61
+ description: "Current surface identity and switcher controls.",
62
+ surfaces: ["*"],
63
+ variants: {
64
+ compact: {
65
+ outlet: "shell-layout:top-left"
66
+ },
67
+ medium: {
68
+ outlet: "shell-layout:top-left"
69
+ },
70
+ expanded: {
71
+ outlet: "shell-layout:top-left"
72
+ }
73
+ }
74
+ });
75
+
76
+ addPlacementTopology({
77
+ id: "shell.status",
78
+ description: "Surface status, connection, and utility indicators.",
79
+ surfaces: ["*"],
80
+ variants: {
81
+ compact: {
82
+ outlet: "shell-layout:top-right"
83
+ },
84
+ medium: {
85
+ outlet: "shell-layout:top-right"
86
+ },
87
+ expanded: {
88
+ outlet: "shell-layout:top-right"
89
+ }
90
+ }
91
+ });
92
+
93
+ addPlacementTopology({
94
+ id: "shell.global-actions",
95
+ description: "Global surface actions that should stay outside primary navigation.",
96
+ surfaces: ["*"],
97
+ variants: {
98
+ compact: {
99
+ outlet: "shell-layout:top-right",
100
+ renderers: menuLinkRenderers
101
+ },
102
+ medium: {
103
+ outlet: "shell-layout:top-right",
104
+ renderers: menuLinkRenderers
105
+ },
106
+ expanded: {
107
+ outlet: "shell-layout:top-right",
108
+ renderers: menuLinkRenderers
109
+ }
110
+ }
111
+ });
112
+
113
+ addPlacementTopology({
114
+ id: "page.supporting-content",
115
+ description: "Supporting page content that opens as a bottom sheet on compact layouts and a side panel on wider layouts.",
116
+ surfaces: ["*"],
117
+ variants: {
118
+ compact: {
119
+ outlet: "shell-layout:supporting-bottom-sheet"
120
+ },
121
+ medium: {
122
+ outlet: "shell-layout:supporting-side-panel"
123
+ },
124
+ expanded: {
125
+ outlet: "shell-layout:supporting-side-panel"
126
+ }
127
+ }
128
+ });
129
+
130
+ addPlacementTopology({
131
+ id: "page.section-nav",
132
+ owner: "home-settings",
133
+ description: "Navigation between child pages in the home settings section.",
134
+ surfaces: ["home"],
135
+ variants: {
136
+ compact: {
137
+ outlet: "home-settings:primary-menu",
138
+ renderers: menuLinkRenderers
139
+ },
140
+ medium: {
141
+ outlet: "home-settings:primary-menu",
142
+ renderers: menuLinkRenderers
143
+ },
144
+ expanded: {
145
+ outlet: "home-settings:primary-menu",
146
+ renderers: menuLinkRenderers
147
+ }
148
+ }
149
+ });
@@ -0,0 +1,10 @@
1
+ import { expect, test } from "@playwright/test";
2
+ import { DEFAULT_VIEWPORTS, runAdaptiveShellSmokeCase } from "@jskit-ai/shell-web/test/adaptiveShellSmoke";
3
+
4
+ test.describe("generated adaptive shell smoke", () => {
5
+ for (const viewport of DEFAULT_VIEWPORTS) {
6
+ test(`${viewport.name} layout has reachable navigation and no horizontal overflow`, async ({ page }) => {
7
+ await runAdaptiveShellSmokeCase({ page, expect, viewport });
8
+ });
9
+ }
10
+ });
@@ -0,0 +1,77 @@
1
+ ---
2
+ id: ui/page-and-placement
3
+ title: Routed page, section navigation, and placed element
4
+ summary: Add product routes and shell extensions through file routing, semantic placements, topology, and registered component tokens.
5
+ keywords: component, navigation, outlet, page, placement, routes, section, shell, subpages, vue
6
+ requires: @jskit-ai/kernel, @jskit-ai/shell-web
7
+ ---
8
+
9
+ # Routed page, section navigation, and placed element
10
+
11
+ ## Use when
12
+
13
+ Use this pattern for an application-owned route page, a section with child
14
+ routes, or a component rendered in an existing shell placement. It demonstrates
15
+ the same public contracts for all three without a page generator.
16
+
17
+ ## Do not use when
18
+
19
+ Do not use section navigation for a single page, add a primary link for a detail
20
+ or workflow route, or create a new placement system when an existing semantic
21
+ placement fits. CRUD routes should use the CRUD screen pattern.
22
+
23
+ ## Product decisions
24
+
25
+ Decide the route, surface, navigation role, label, icon, section ownership,
26
+ ordering, and whether the content belongs in navigation or a component outlet.
27
+ These are product information architecture decisions, not defaults to infer from
28
+ a filename alone.
29
+
30
+ ## Invariants
31
+
32
+ - File routes and placement destinations agree.
33
+ - Route pages do not add a page header or standalone heading by default.
34
+ - Placement ids describe product ownership, not the authoring mechanism.
35
+ - Child links share an explicit section owner.
36
+ - Topology maps each semantic placement to concrete responsive outlets.
37
+ - Placed components are registered by token through a client provider.
38
+ - Compact navigation controls remain accessible and at least 48 CSS pixels.
39
+ - Application source has no generated-file marker, receipt, or overwrite state.
40
+
41
+ ## Framework APIs
42
+
43
+ Use `createPlacementRegistry()`, `addPlacement()`, `addPlacementTopology()`, and
44
+ `ShellOutlet` from `@jskit-ai/shell-web`. Use file routes and
45
+ `redirectToChild()` from `@jskit-ai/kernel`. Register app-owned component tokens
46
+ through the application's normal client provider.
47
+
48
+ ## Example files
49
+
50
+ `example/` contains a Reports section with Overview and Activity child routes,
51
+ the matching section-navigation placements/topology, and a Sync Status component
52
+ placed in the existing shell status area.
53
+
54
+ ## Variation points
55
+
56
+ Change the route hierarchy, surface, semantic target, section owner, component
57
+ token, order, label, icon, and responsive outlet mapping. Omit the parent host
58
+ and topology when no child navigation is needed. Omit provider registration for
59
+ link-only placements.
60
+
61
+ ## Verification
62
+
63
+ - navigate directly to each route and through each visible link
64
+ - verify the section index redirects to its intended child
65
+ - verify the placed component resolves through its provider token
66
+ - exercise compact, medium, and expanded variants
67
+ - verify current-link state, keyboard operation, target size, and no overflow
68
+ - run client tests and the production build
69
+
70
+ ## Avoid
71
+
72
+ - generator-branded placement ids or CSS classes
73
+ - navigation links for detail/workflow routes unless explicitly chosen
74
+ - duplicated route tables beside file routing
75
+ - hard-coded component instances where a semantic placement is required
76
+ - placeholder pages that instruct developers to replace their content
77
+ - provenance comments, receipts, or hidden mutation markers
@@ -0,0 +1,14 @@
1
+ import { defineProvider } from "@jskit-ai/kernel/shared/capabilities";
2
+ import SyncStatusElement from "/src/components/SyncStatusElement.vue";
3
+
4
+ const MainClientProvider = defineProvider({
5
+ id: "local.main.client",
6
+ requires: {
7
+ components: "client.components"
8
+ },
9
+ setup({ components }) {
10
+ components.register("local.main.ui.sync-status", SyncStatusElement);
11
+ }
12
+ });
13
+
14
+ export { MainClientProvider };
@@ -0,0 +1,16 @@
1
+ <template>
2
+ <div class="sync-status" role="status" aria-label="Catalogue synchronized">
3
+ <v-icon icon="mdi-cloud-check-outline" size="small" aria-hidden="true" />
4
+ <span class="text-body-2">Synced</span>
5
+ </div>
6
+ </template>
7
+
8
+ <style scoped>
9
+ .sync-status {
10
+ align-items: center;
11
+ display: inline-flex;
12
+ gap: 0.5rem;
13
+ min-height: 48px;
14
+ min-width: 0;
15
+ }
16
+ </style>
@@ -0,0 +1,7 @@
1
+ <template>
2
+ <section>
3
+ <p class="text-body-1 text-medium-emphasis mb-0">
4
+ Recent catalogue changes appear here.
5
+ </p>
6
+ </section>
7
+ </template>
@@ -0,0 +1,7 @@
1
+ <script setup>
2
+ import { redirectToChild } from "@jskit-ai/kernel/client/pageRedirects";
3
+
4
+ definePage({
5
+ redirect: redirectToChild("overview")
6
+ });
7
+ </script>
@@ -0,0 +1,7 @@
1
+ <template>
2
+ <section>
3
+ <p class="text-body-1 text-medium-emphasis mb-0">
4
+ Your reading and catalogue summary appears here.
5
+ </p>
6
+ </section>
7
+ </template>
@@ -0,0 +1,25 @@
1
+ <script setup>
2
+ import ShellOutlet from "@jskit-ai/shell-web/client/components/ShellOutlet";
3
+ import { RouterView } from "vue-router";
4
+ </script>
5
+
6
+ <template>
7
+ <section class="reports-section d-flex flex-column ga-4">
8
+ <nav aria-label="Report sections">
9
+ <v-tabs density="comfortable">
10
+ <ShellOutlet target="reports:section-nav" />
11
+ </v-tabs>
12
+ </nav>
13
+
14
+ <main class="reports-section__content">
15
+ <RouterView />
16
+ </main>
17
+ </section>
18
+ </template>
19
+
20
+ <style scoped>
21
+ .reports-section,
22
+ .reports-section__content {
23
+ min-width: 0;
24
+ }
25
+ </style>
@@ -0,0 +1,52 @@
1
+ import { createPlacementRegistry } from "@jskit-ai/shell-web/client/placement";
2
+
3
+ const registry = createPlacementRegistry();
4
+ const { addPlacement } = registry;
5
+
6
+ addPlacement({
7
+ id: "catalogue.reports.link",
8
+ target: "shell.primary-nav",
9
+ kind: "link",
10
+ surfaces: ["home"],
11
+ order: 120,
12
+ props: {
13
+ label: "Reports",
14
+ icon: "mdi-chart-box-outline",
15
+ surface: "home",
16
+ scopedSuffix: "/reports",
17
+ unscopedSuffix: "/reports"
18
+ }
19
+ });
20
+
21
+ for (const [id, label, suffix, order] of [
22
+ ["overview", "Overview", "/reports/overview", 100],
23
+ ["activity", "Activity", "/reports/activity", 110]
24
+ ]) {
25
+ addPlacement({
26
+ id: `catalogue.reports.${id}.link`,
27
+ target: "page.section-nav",
28
+ owner: "reports",
29
+ kind: "link",
30
+ surfaces: ["home"],
31
+ order,
32
+ props: {
33
+ label,
34
+ surface: "home",
35
+ scopedSuffix: suffix,
36
+ unscopedSuffix: suffix
37
+ }
38
+ });
39
+ }
40
+
41
+ addPlacement({
42
+ id: "catalogue.sync-status",
43
+ target: "shell.status",
44
+ kind: "component",
45
+ surfaces: ["home"],
46
+ order: 100,
47
+ componentToken: "local.main.ui.sync-status"
48
+ });
49
+
50
+ export default function getPlacements() {
51
+ return registry.build();
52
+ }