@wix/himalaya-cli 0.1029.0 → 0.1031.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 (185) hide show
  1. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/dev-server/src/app-config.d.ts +7 -0
  2. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/dev-server/src/wix-gateway.d.ts +32 -0
  3. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/dev-server/src/wix-gateway.rules.d.ts +2 -1
  4. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/core/ts/src/define-app.d.ts +7 -0
  5. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/_types/stdlib/wix-sdk/genie-chat/src/index.d.ts +64 -0
  6. package/dist/authoring-runtime/node_modules/@wix/himalaya/dist/wix-genie-chat.mjs +41 -1
  7. package/dist/cli.mjs +298 -114
  8. package/dist/preview-assets.generated.bin +0 -0
  9. package/guides/component-reference.json +0 -7
  10. package/guides/component-reference.md +0 -2
  11. package/guides/sdk-reference.json +50 -2
  12. package/package.json +2 -2
  13. package/templates/beauty-salon/dev/index.ts +575 -214
  14. package/templates/beauty-salon/tier5-src/_shared/collection-contract.ts +4 -1
  15. package/templates/beauty-salon/tier5-src/_shared/owner-load-error.ts +7 -1
  16. package/templates/beauty-salon/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  17. package/templates/beauty-salon/tier5-src/himi-store-product/index.ts +36 -5
  18. package/templates/beauty-salon/tier5-src/wix-spaces-app-language/index.ts +4 -2
  19. package/templates/beauty-salon-owner/config.ts +1 -1
  20. package/templates/beauty-salon-owner/dev/index.ts +247 -9
  21. package/templates/beauty-salon-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  22. package/templates/beauty-salon-owner/tier5-src/_shared/aria-chat.ts +405 -20
  23. package/templates/beauty-salon-owner/tier5-src/_shared/collection-contract.ts +4 -1
  24. package/templates/beauty-salon-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  25. package/templates/beauty-salon-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  26. package/templates/beauty-salon-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  27. package/templates/beauty-salon-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  28. package/templates/beauty-salon-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  29. package/templates/branded-lite/dev/index.ts +699 -228
  30. package/templates/branded-lite/tier5-src/_shared/collection-contract.ts +4 -1
  31. package/templates/branded-lite/tier5-src/_shared/owner-load-error.ts +7 -1
  32. package/templates/branded-lite/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  33. package/templates/branded-lite/tier5-src/himi-branded-lite-notifsettings/index.ts +11 -6
  34. package/templates/branded-lite/tier5-src/himi-branded-lite-reviews/index.ts +11 -6
  35. package/templates/branded-lite/tier5-src/himi-store-product/index.ts +36 -5
  36. package/templates/branded-lite/tier5-src/wix-spaces-app-language/index.ts +4 -2
  37. package/templates/community-club/dev/index.ts +451 -204
  38. package/templates/community-club/tier5-src/_shared/collection-contract.ts +4 -1
  39. package/templates/community-club/tier5-src/_shared/owner-load-error.ts +7 -1
  40. package/templates/community-club/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  41. package/templates/community-club/tier5-src/wix-spaces-app-language/index.ts +4 -2
  42. package/templates/community-club-owner/config.ts +1 -1
  43. package/templates/community-club-owner/dev/index.ts +247 -9
  44. package/templates/community-club-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  45. package/templates/community-club-owner/tier5-src/_shared/aria-chat.ts +405 -20
  46. package/templates/community-club-owner/tier5-src/_shared/collection-contract.ts +4 -1
  47. package/templates/community-club-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  48. package/templates/community-club-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  49. package/templates/community-club-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  50. package/templates/community-club-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  51. package/templates/community-club-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  52. package/templates/events-meetups/dev/index.ts +451 -204
  53. package/templates/events-meetups/tier5-src/_shared/collection-contract.ts +4 -1
  54. package/templates/events-meetups/tier5-src/_shared/owner-load-error.ts +7 -1
  55. package/templates/events-meetups/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  56. package/templates/events-meetups/tier5-src/wix-spaces-app-language/index.ts +4 -2
  57. package/templates/events-meetups-owner/config.ts +1 -1
  58. package/templates/events-meetups-owner/dev/index.ts +247 -9
  59. package/templates/events-meetups-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  60. package/templates/events-meetups-owner/tier5-src/_shared/aria-chat.ts +405 -20
  61. package/templates/events-meetups-owner/tier5-src/_shared/collection-contract.ts +4 -1
  62. package/templates/events-meetups-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  63. package/templates/events-meetups-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  64. package/templates/events-meetups-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  65. package/templates/events-meetups-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  66. package/templates/events-meetups-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  67. package/templates/gym-fitness/dev/index.ts +575 -214
  68. package/templates/gym-fitness/tier5-src/_shared/collection-contract.ts +4 -1
  69. package/templates/gym-fitness/tier5-src/_shared/owner-load-error.ts +7 -1
  70. package/templates/gym-fitness/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  71. package/templates/gym-fitness/tier5-src/himi-store-product/index.ts +36 -5
  72. package/templates/gym-fitness/tier5-src/wix-spaces-app-language/index.ts +4 -2
  73. package/templates/gym-fitness-owner/config.ts +1 -1
  74. package/templates/gym-fitness-owner/dev/index.ts +247 -9
  75. package/templates/gym-fitness-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  76. package/templates/gym-fitness-owner/tier5-src/_shared/aria-chat.ts +405 -20
  77. package/templates/gym-fitness-owner/tier5-src/_shared/collection-contract.ts +4 -1
  78. package/templates/gym-fitness-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  79. package/templates/gym-fitness-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  80. package/templates/gym-fitness-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  81. package/templates/gym-fitness-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  82. package/templates/gym-fitness-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  83. package/templates/himi-chat/tier5-src/_shared/owner-load-error.ts +7 -1
  84. package/templates/nonprofit-cause/dev/index.ts +451 -204
  85. package/templates/nonprofit-cause/tier5-src/_shared/collection-contract.ts +4 -1
  86. package/templates/nonprofit-cause/tier5-src/_shared/owner-load-error.ts +7 -1
  87. package/templates/nonprofit-cause/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  88. package/templates/nonprofit-cause/tier5-src/wix-spaces-app-language/index.ts +4 -2
  89. package/templates/nonprofit-cause-owner/config.ts +1 -1
  90. package/templates/nonprofit-cause-owner/dev/index.ts +247 -9
  91. package/templates/nonprofit-cause-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  92. package/templates/nonprofit-cause-owner/tier5-src/_shared/aria-chat.ts +405 -20
  93. package/templates/nonprofit-cause-owner/tier5-src/_shared/collection-contract.ts +4 -1
  94. package/templates/nonprofit-cause-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  95. package/templates/nonprofit-cause-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  96. package/templates/nonprofit-cause-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  97. package/templates/nonprofit-cause-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  98. package/templates/nonprofit-cause-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  99. package/templates/owner-lite/config.ts +1 -1
  100. package/templates/owner-lite/dev/index.ts +247 -9
  101. package/templates/owner-lite/tier5-src/_shared/aria-attachments.ts +179 -0
  102. package/templates/owner-lite/tier5-src/_shared/aria-chat.ts +405 -20
  103. package/templates/owner-lite/tier5-src/_shared/collection-contract.ts +4 -1
  104. package/templates/owner-lite/tier5-src/_shared/owner-bookings.ts +20 -0
  105. package/templates/owner-lite/tier5-src/_shared/owner-load-error.ts +7 -1
  106. package/templates/owner-lite/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  107. package/templates/owner-lite/tier5-src/himi-owner-lite-home/index.ts +2 -12
  108. package/templates/owner-lite/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  109. package/templates/podcast-creator/dev/index.ts +451 -204
  110. package/templates/podcast-creator/tier5-src/_shared/collection-contract.ts +4 -1
  111. package/templates/podcast-creator/tier5-src/_shared/owner-load-error.ts +7 -1
  112. package/templates/podcast-creator/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  113. package/templates/podcast-creator/tier5-src/wix-spaces-app-language/index.ts +4 -2
  114. package/templates/podcast-creator-owner/config.ts +1 -1
  115. package/templates/podcast-creator-owner/dev/index.ts +247 -9
  116. package/templates/podcast-creator-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  117. package/templates/podcast-creator-owner/tier5-src/_shared/aria-chat.ts +405 -20
  118. package/templates/podcast-creator-owner/tier5-src/_shared/collection-contract.ts +4 -1
  119. package/templates/podcast-creator-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  120. package/templates/podcast-creator-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  121. package/templates/podcast-creator-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  122. package/templates/podcast-creator-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  123. package/templates/podcast-creator-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  124. package/templates/portfolio-creative/dev/index.ts +575 -214
  125. package/templates/portfolio-creative/tier5-src/_shared/collection-contract.ts +4 -1
  126. package/templates/portfolio-creative/tier5-src/_shared/owner-load-error.ts +7 -1
  127. package/templates/portfolio-creative/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  128. package/templates/portfolio-creative/tier5-src/himi-store-product/index.ts +36 -5
  129. package/templates/portfolio-creative/tier5-src/wix-spaces-app-language/index.ts +4 -2
  130. package/templates/portfolio-creative-owner/config.ts +1 -1
  131. package/templates/portfolio-creative-owner/dev/index.ts +247 -9
  132. package/templates/portfolio-creative-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  133. package/templates/portfolio-creative-owner/tier5-src/_shared/aria-chat.ts +405 -20
  134. package/templates/portfolio-creative-owner/tier5-src/_shared/collection-contract.ts +4 -1
  135. package/templates/portfolio-creative-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  136. package/templates/portfolio-creative-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  137. package/templates/portfolio-creative-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  138. package/templates/portfolio-creative-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  139. package/templates/portfolio-creative-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  140. package/templates/restaurant/dev/index.ts +451 -204
  141. package/templates/restaurant/tier5-src/_shared/collection-contract.ts +4 -1
  142. package/templates/restaurant/tier5-src/_shared/owner-load-error.ts +7 -1
  143. package/templates/restaurant/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  144. package/templates/restaurant/tier5-src/wix-spaces-app-language/index.ts +4 -2
  145. package/templates/restaurant-owner/config.ts +1 -1
  146. package/templates/restaurant-owner/dev/index.ts +247 -9
  147. package/templates/restaurant-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  148. package/templates/restaurant-owner/tier5-src/_shared/aria-chat.ts +405 -20
  149. package/templates/restaurant-owner/tier5-src/_shared/collection-contract.ts +4 -1
  150. package/templates/restaurant-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  151. package/templates/restaurant-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  152. package/templates/restaurant-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  153. package/templates/restaurant-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  154. package/templates/restaurant-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  155. package/templates/retail-store/dev/index.ts +575 -214
  156. package/templates/retail-store/tier5-src/_shared/collection-contract.ts +4 -1
  157. package/templates/retail-store/tier5-src/_shared/owner-load-error.ts +7 -1
  158. package/templates/retail-store/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  159. package/templates/retail-store/tier5-src/himi-store-product/index.ts +36 -5
  160. package/templates/retail-store/tier5-src/wix-spaces-app-language/index.ts +4 -2
  161. package/templates/retail-store-owner/config.ts +1 -1
  162. package/templates/retail-store-owner/dev/index.ts +247 -9
  163. package/templates/retail-store-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  164. package/templates/retail-store-owner/tier5-src/_shared/aria-chat.ts +405 -20
  165. package/templates/retail-store-owner/tier5-src/_shared/collection-contract.ts +4 -1
  166. package/templates/retail-store-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  167. package/templates/retail-store-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  168. package/templates/retail-store-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  169. package/templates/retail-store-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  170. package/templates/retail-store-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
  171. package/templates/yoga-studio/dev/index.ts +451 -204
  172. package/templates/yoga-studio/tier5-src/_shared/collection-contract.ts +4 -1
  173. package/templates/yoga-studio/tier5-src/_shared/owner-load-error.ts +7 -1
  174. package/templates/yoga-studio/tier5-src/himi-branded-lite-appearance/index.ts +12 -1
  175. package/templates/yoga-studio/tier5-src/wix-spaces-app-language/index.ts +4 -2
  176. package/templates/yoga-studio-owner/config.ts +1 -1
  177. package/templates/yoga-studio-owner/dev/index.ts +247 -9
  178. package/templates/yoga-studio-owner/tier5-src/_shared/aria-attachments.ts +179 -0
  179. package/templates/yoga-studio-owner/tier5-src/_shared/aria-chat.ts +405 -20
  180. package/templates/yoga-studio-owner/tier5-src/_shared/collection-contract.ts +4 -1
  181. package/templates/yoga-studio-owner/tier5-src/_shared/owner-bookings.ts +20 -0
  182. package/templates/yoga-studio-owner/tier5-src/_shared/owner-load-error.ts +7 -1
  183. package/templates/yoga-studio-owner/tier5-src/himi-owner-lite-aria/index.ts +40 -1
  184. package/templates/yoga-studio-owner/tier5-src/himi-owner-lite-home/index.ts +2 -12
  185. package/templates/yoga-studio-owner/tier5-src/himi-owner-lite-manage/index.ts +10 -4
@@ -14,6 +14,9 @@ export interface CollectionConfig {
14
14
  searchPlaceholder?: string;
15
15
  sortLabels?: { default: string; az: string; za: string };
16
16
  metadata?: string[];
17
+ /** Numeric 0–5 row field rendered as a Rating (accessible "N out of 5") instead of
18
+ * folding a "★★★★☆" glyph string into the metadata line, so screen readers get a value. */
19
+ rating?: string;
17
20
  sectioned?: boolean;
18
21
  view: 'list' | 'grid';
19
22
  backendQuery?: boolean;
@@ -58,7 +61,7 @@ export const COLLECTIONS: Record<string, CollectionConfig> = {
58
61
  himiBrandedCoupons: { rows: 'coupons', title: 'name', subtitle: 'subtitle', view: 'list', primaryVerb: { label: 'Get code' } },
59
62
  himiBrandedNotifications: { rows: 'items', title: 'name', subtitle: 'subtitle', image: 'photo', metadata: ['unreadDot'], view: 'list' },
60
63
  himiBrandedLoyalty: { rows: 'rewards', title: 'name', subtitle: 'description', view: 'grid', primaryVerb: { label: 'Redeem' } },
61
- himiBrandedReviews: { rows: 'reviews', title: 'title', subtitle: 'body', metadata: ['author', 'stars'], view: 'list' },
64
+ himiBrandedReviews: { rows: 'reviews', title: 'title', subtitle: 'body', metadata: ['author'], rating: 'rating', view: 'list' },
62
65
  himiBrandedPortfolio: { rows: 'projects', title: 'title', subtitle: 'subtitle', image: 'image', view: 'grid', gridImageHeight: 180 },
63
66
  himiBrandedInvoices: { rows: 'invoices', title: 'title', subtitle: 'subtitle', view: 'list' },
64
67
  himiBrandedBadges: { rows: 'badges', title: 'name', subtitle: 'description', view: 'grid' },
@@ -1,6 +1,12 @@
1
1
  import { copyParam } from "./himi-copy.js";
2
2
 
3
- /** Host-owned preview input. Absent on native and older hosts. */
3
+ /** Host-owned preview input. Absent on native and older hosts.
4
+ *
5
+ * `"sample"` — the built-in demo records; `"live"` — the viewer's own business over the
6
+ * owner rung; `"fixtures"` — a DEV web host over a sealed hermetic gateway, where
7
+ * the dev fixtures are the sample data. `"fixtures"` is neither live nor demo, so a
8
+ * worker READS through the bridge as it does on a device; it is still a preview host
9
+ * (`isOwnerPreviewHost`), so failure copy may name the web preview. */
4
10
  function ownerPreviewMode(): unknown {
5
11
  return (globalThis as unknown as { himalaya?: { input?: Record<string, unknown> } }).himalaya?.input?.__himiOwnerPreview;
6
12
  }
@@ -1,5 +1,6 @@
1
1
  import { defineService } from "@himalaya/state";
2
2
  import {
3
+ ACCENT_IDS,
3
4
  ACCENT_KEY,
4
5
  ACCENT_META,
5
6
  DEFAULT_ACCENT,
@@ -29,6 +30,10 @@ interface State {
29
30
  accentHex_sage: string;
30
31
  accentHex_plum: string;
31
32
  accentHex_ocean: string;
33
+ // Per-accent selection flags for the radio group (`selected_<id>`) and the
34
+ // check mark on the swatch (`notSelected_<id>`, hiddenWhen hides on TRUE). Flat
35
+ // fields for the same reason as the hex ones: the swatches are static nodes.
36
+ [flag: `selected_${string}` | `notSelected_${string}`]: boolean | string;
32
37
  }
33
38
 
34
39
  interface StorageLike {
@@ -50,7 +55,13 @@ function paramValue(arg: unknown, key: string): string {
50
55
  }
51
56
 
52
57
  function build(pendingAccent: string, brandAccent: string): State {
58
+ const flags: Record<string, boolean> = {};
59
+ for (const id of ACCENT_IDS) {
60
+ flags[`selected_${id}`] = id === pendingAccent;
61
+ flags[`notSelected_${id}`] = id !== pendingAccent;
62
+ }
53
63
  return {
64
+ ...flags,
54
65
  pendingAccent,
55
66
  brandAccent,
56
67
  accentHex_brand: brandAccent || ACCENT_META.amber.hex,
@@ -85,7 +96,7 @@ const svc = defineService<State, {
85
96
  selectAccent: (state, arg) => {
86
97
  const id = paramValue(arg, "id");
87
98
  if (!isAccentId(id)) return state;
88
- return { ...state, pendingAccent: id };
99
+ return build(id, state.brandAccent);
89
100
  },
90
101
  // Apply: persist the accent; the home worker re-reads it on launch.
91
102
  apply: (state) => {
@@ -5,11 +5,12 @@
5
5
  import { defineService } from "@himalaya/state";
6
6
  import { dispatch } from "@himalaya/dispatch";
7
7
 
8
- interface Row { id: string; name: string; subtitle: string }
8
+ /** `selected` drives the row's radio; `subtitle` stays for older descriptors. */
9
+ interface Row { id: string; name: string; subtitle: string; selected: boolean }
9
10
  interface S { status: "ready"; options: Row[] }
10
11
 
11
12
  /** Locales with catalogs (`tools/l10n/catalog.<tag>.json`) + LocaleStore support. */
12
- const LOCALE_OPTIONS: Omit<Row, "subtitle">[] = [
13
+ const LOCALE_OPTIONS: Omit<Row, "subtitle" | "selected">[] = [
13
14
  { id: "en", name: "English" },
14
15
  { id: "es", name: "Español" },
15
16
  { id: "he", name: "עברית" },
@@ -19,6 +20,7 @@ function withSelected(selected: string): Row[] {
19
20
  return LOCALE_OPTIONS.map((o) => ({
20
21
  ...o,
21
22
  subtitle: o.id === selected ? "Selected" : "",
23
+ selected: o.id === selected,
22
24
  }));
23
25
  }
24
26
 
@@ -37,7 +37,7 @@ export default defineApp({
37
37
  actions: "http://localhost:8190/v1/actions",
38
38
  sync: "http://localhost:8190/v1/sync",
39
39
  },
40
- capabilities: ["live_activity","push","share","secure_storage","open_url","local_database","clipboard","ui"],
40
+ capabilities: ["live_activity","push","share","secure_storage","open_url","local_database","clipboard","ui","camera","presigned_upload"],
41
41
  designTokensPath: "./tokens.json",
42
42
  navigation: {
43
43
  "navKind": "responsive",
@@ -50019,7 +50019,7 @@ const SCREENS = runtimeSetting({
50019
50019
  "itemsPath": "$service:himiOwnerLiteManage.recents",
50020
50020
  "items": [
50021
50021
  {
50022
- "id": "",
50022
+ "id": "himi_owner_lite.manage.recent.$item.id",
50023
50023
  "body": {
50024
50024
  "package": "himalaya",
50025
50025
  "type": "VStack",
@@ -50164,7 +50164,7 @@ const SCREENS = runtimeSetting({
50164
50164
  "spacing": 14,
50165
50165
  "children": [
50166
50166
  {
50167
- "id": "",
50167
+ "id": "himi_owner_lite.manage.recent.create.$item.id",
50168
50168
  "body": {
50169
50169
  "package": "himalaya",
50170
50170
  "type": "Text",
@@ -50189,7 +50189,7 @@ const SCREENS = runtimeSetting({
50189
50189
  }
50190
50190
  },
50191
50191
  {
50192
- "id": "",
50192
+ "id": "himi_owner_lite.manage.recent.handoff.$item.id",
50193
50193
  "body": {
50194
50194
  "package": "himalaya",
50195
50195
  "type": "Text",
@@ -50325,7 +50325,7 @@ const SCREENS = runtimeSetting({
50325
50325
  "itemsPath": "$item.areas",
50326
50326
  "items": [
50327
50327
  {
50328
- "id": "",
50328
+ "id": "himi_owner_lite.manage.area.$item.id",
50329
50329
  "body": {
50330
50330
  "package": "himalaya",
50331
50331
  "type": "VStack",
@@ -50470,7 +50470,7 @@ const SCREENS = runtimeSetting({
50470
50470
  "spacing": 14,
50471
50471
  "children": [
50472
50472
  {
50473
- "id": "",
50473
+ "id": "himi_owner_lite.manage.area.create.$item.id",
50474
50474
  "body": {
50475
50475
  "package": "himalaya",
50476
50476
  "type": "Text",
@@ -50495,7 +50495,7 @@ const SCREENS = runtimeSetting({
50495
50495
  }
50496
50496
  },
50497
50497
  {
50498
- "id": "",
50498
+ "id": "himi_owner_lite.manage.area.handoff.$item.id",
50499
50499
  "body": {
50500
50500
  "package": "himalaya",
50501
50501
  "type": "Text",
@@ -51275,7 +51275,7 @@ const SCREENS = runtimeSetting({
51275
51275
  "props": {
51276
51276
  "items": [
51277
51277
  {
51278
- "id": "",
51278
+ "id": "ol_drawer_nav.$item.id",
51279
51279
  "body": {
51280
51280
  "package": "himalaya",
51281
51281
  "type": "ListItem",
@@ -51327,7 +51327,7 @@ const SCREENS = runtimeSetting({
51327
51327
  "props": {
51328
51328
  "items": [
51329
51329
  {
51330
- "id": "",
51330
+ "id": "ol_drawer_attention.$item.id",
51331
51331
  "body": {
51332
51332
  "package": "himalaya",
51333
51333
  "type": "ListItem",
@@ -54888,6 +54888,45 @@ const SCREENS = runtimeSetting({
54888
54888
  }
54889
54889
  }
54890
54890
  },
54891
+ {
54892
+ "id": "himi_owner_lite_aria.msg_attach_$item.id",
54893
+ "body": {
54894
+ "package": "himalaya",
54895
+ "type": "HStack",
54896
+ "props": {
54897
+ "spacing": 0,
54898
+ "children": [
54899
+ {
54900
+ "id": "",
54901
+ "body": {
54902
+ "package": "himalaya",
54903
+ "type": "Spacer",
54904
+ "props": {}
54905
+ },
54906
+ "modifiers": {
54907
+ "hiddenPath": "$item.notUser"
54908
+ }
54909
+ },
54910
+ {
54911
+ "id": "",
54912
+ "body": {
54913
+ "package": "himalaya",
54914
+ "type": "Text",
54915
+ "props": {
54916
+ "text": "$item.attachText",
54917
+ "style": "footnote",
54918
+ "color": "textSecondary",
54919
+ "maxLines": 3
54920
+ }
54921
+ }
54922
+ }
54923
+ ]
54924
+ }
54925
+ },
54926
+ "modifiers": {
54927
+ "hiddenPath": "$item.attachHidden"
54928
+ }
54929
+ },
54891
54930
  {
54892
54931
  "id": "himi_owner_lite_aria.msg_$item.id.link1",
54893
54932
  "body": {
@@ -58468,6 +58507,203 @@ const SCREENS = runtimeSetting({
58468
58507
  }
58469
58508
  }
58470
58509
  },
58510
+ {
58511
+ "id": "himi_owner_lite_aria.attachments.bound",
58512
+ "body": {
58513
+ "package": "himalaya",
58514
+ "type": "LazyList",
58515
+ "props": {
58516
+ "itemsPath": "$service:himiOwnerLiteAria.attachments",
58517
+ "horizontal": true,
58518
+ "spacing": 8,
58519
+ "items": [
58520
+ {
58521
+ "id": "himi_owner_lite_aria.attachment_$item.id",
58522
+ "body": {
58523
+ "package": "himalaya",
58524
+ "type": "VStack",
58525
+ "props": {
58526
+ "spacing": 4,
58527
+ "children": [
58528
+ {
58529
+ "id": "himi_owner_lite_aria.attachment_thumb_$item.id",
58530
+ "body": {
58531
+ "package": "himalaya",
58532
+ "type": "Image",
58533
+ "props": {
58534
+ "url": "$item.thumbUrl",
58535
+ "width": 72,
58536
+ "height": 72,
58537
+ "contentMode": "fill",
58538
+ "shape": "rounded",
58539
+ "contentDescription": "$item.name"
58540
+ }
58541
+ },
58542
+ "modifiers": {
58543
+ "hiddenPath": "$item.thumbHidden"
58544
+ }
58545
+ },
58546
+ {
58547
+ "id": "",
58548
+ "body": {
58549
+ "package": "himalaya",
58550
+ "type": "Text",
58551
+ "props": {
58552
+ "text": "$item.statusText",
58553
+ "style": "caption",
58554
+ "color": "textSecondary",
58555
+ "maxLines": 2
58556
+ }
58557
+ },
58558
+ "modifiers": {
58559
+ "hiddenPath": "$item.statusHidden"
58560
+ }
58561
+ },
58562
+ {
58563
+ "id": "",
58564
+ "body": {
58565
+ "package": "himalaya",
58566
+ "type": "HStack",
58567
+ "props": {
58568
+ "spacing": 8,
58569
+ "children": [
58570
+ {
58571
+ "id": "himi_owner_lite_aria.attachment_retry_$item.id",
58572
+ "body": {
58573
+ "package": "himalaya",
58574
+ "type": "Text",
58575
+ "props": {
58576
+ "text": "Retry",
58577
+ "style": "caption",
58578
+ "color": "accentPrimary",
58579
+ "maxLines": 1
58580
+ }
58581
+ },
58582
+ "modifiers": {
58583
+ "onTap": {
58584
+ "actionId": "tier5.himiOwnerLiteAria.retryAttachment",
58585
+ "params": {
58586
+ "id": "$item.id"
58587
+ }
58588
+ },
58589
+ "hiddenPath": "$item.retryHidden"
58590
+ }
58591
+ },
58592
+ {
58593
+ "id": "himi_owner_lite_aria.attachment_remove_$item.id",
58594
+ "body": {
58595
+ "package": "himalaya",
58596
+ "type": "Icon",
58597
+ "props": {
58598
+ "name": "close",
58599
+ "size": 14,
58600
+ "tint": "textSecondary"
58601
+ }
58602
+ },
58603
+ "modifiers": {
58604
+ "onTap": {
58605
+ "actionId": "tier5.himiOwnerLiteAria.removeAttachment",
58606
+ "params": {
58607
+ "id": "$item.id"
58608
+ }
58609
+ },
58610
+ "accessibilityLabel": "Remove photo"
58611
+ }
58612
+ }
58613
+ ]
58614
+ }
58615
+ }
58616
+ }
58617
+ ]
58618
+ }
58619
+ },
58620
+ "modifiers": {
58621
+ "width": 72
58622
+ }
58623
+ }
58624
+ ]
58625
+ }
58626
+ },
58627
+ "modifiers": {
58628
+ "hiddenPath": "$service:himiOwnerLiteAria.attachmentsHidden",
58629
+ "padding": {
58630
+ "leading": 0,
58631
+ "trailing": 0,
58632
+ "top": 8,
58633
+ "bottom": 0
58634
+ }
58635
+ }
58636
+ },
58637
+ {
58638
+ "id": "",
58639
+ "body": {
58640
+ "package": "himalaya",
58641
+ "type": "HStack",
58642
+ "props": {
58643
+ "spacing": 16,
58644
+ "children": [
58645
+ {
58646
+ "id": "himi_owner_lite_aria.attach.library",
58647
+ "body": {
58648
+ "package": "himalaya",
58649
+ "type": "Icon",
58650
+ "props": {
58651
+ "name": "image",
58652
+ "size": 22,
58653
+ "tint": "accentPrimary"
58654
+ }
58655
+ },
58656
+ "modifiers": {
58657
+ "onTap": {
58658
+ "actionId": "tier5.himiOwnerLiteAria.attach",
58659
+ "params": {
58660
+ "source": "library"
58661
+ }
58662
+ },
58663
+ "accessibilityLabel": "Add a photo"
58664
+ }
58665
+ },
58666
+ {
58667
+ "id": "himi_owner_lite_aria.attach.camera",
58668
+ "body": {
58669
+ "package": "himalaya",
58670
+ "type": "Icon",
58671
+ "props": {
58672
+ "name": "camera",
58673
+ "size": 22,
58674
+ "tint": "accentPrimary"
58675
+ }
58676
+ },
58677
+ "modifiers": {
58678
+ "onTap": {
58679
+ "actionId": "tier5.himiOwnerLiteAria.attach",
58680
+ "params": {
58681
+ "source": "camera"
58682
+ }
58683
+ },
58684
+ "accessibilityLabel": "Take a photo"
58685
+ }
58686
+ },
58687
+ {
58688
+ "id": "",
58689
+ "body": {
58690
+ "package": "himalaya",
58691
+ "type": "Spacer",
58692
+ "props": {}
58693
+ }
58694
+ }
58695
+ ]
58696
+ }
58697
+ },
58698
+ "modifiers": {
58699
+ "padding": {
58700
+ "leading": 0,
58701
+ "trailing": 0,
58702
+ "top": 8,
58703
+ "bottom": 0
58704
+ }
58705
+ }
58706
+ },
58471
58707
  {
58472
58708
  "id": "form_aria",
58473
58709
  "body": {
@@ -58553,7 +58789,9 @@ const SCREENS = runtimeSetting({
58553
58789
  "wix_api",
58554
58790
  "open_url",
58555
58791
  "clipboard",
58556
- "ui"
58792
+ "ui",
58793
+ "camera",
58794
+ "presigned_upload"
58557
58795
  ],
58558
58796
  "minBinaryVersion": "0.1.0",
58559
58797
  "bundleVersion": "0.0.1"
@@ -0,0 +1,179 @@
1
+ // Photo attachments for the Aria composer — the pure half.
2
+ //
3
+ // Everything here is a decision that can be made without touching the device
4
+ // or the network: which files may be attached, how many, how large, what a chip
5
+ // in the composer says in each of its three states, and how a picked image is
6
+ // turned into the bytes an upload sends. The half that DOES touch the world —
7
+ // minting the upload, sending the bytes, picking — lives in `aria-chat.ts`
8
+ // (the mint, through `@himalaya/wix-genie-chat`) and in each app's adapter (the
9
+ // picker and the byte transfer, which are device capabilities the adapter's
10
+ // screen has to declare).
11
+ //
12
+ // This file is copied verbatim into every generated starter app, so it explains
13
+ // itself without pointing at anything only this repo has.
14
+
15
+ /** Image types the composer accepts. The first-party clients' own allowlist
16
+ * for images: png, jpeg (and the non-standard `image/jpg` some pickers still
17
+ * report), webp, gif and heic. Anything else is REFUSED with a line saying so,
18
+ * never silently dropped — the native Aria app drops unsupported files without a
19
+ * word, and an owner who picked something and sees nothing happen assumes the
20
+ * button is broken. */
21
+ export const ARIA_IMAGE_TYPES: readonly string[] = [
22
+ "image/png",
23
+ "image/jpeg",
24
+ "image/jpg",
25
+ "image/webp",
26
+ "image/gif",
27
+ "image/heic",
28
+ ];
29
+
30
+ /** At most this many attachments ride one message. The native Aria app caps at
31
+ * 10; nothing on the wire says otherwise. */
32
+ export const ARIA_MAX_ATTACHMENTS = 10;
33
+
34
+ /** The largest image the composer will try to send, in bytes.
35
+ *
36
+ * Not a product choice: it is the ceiling of the transfer this slice uses. A
37
+ * picked photo crosses the worker bridge as a base64 string and is sent inline,
38
+ * and the inline upload refuses anything over 8 MiB (the `MAX_INLINE_BASE64_BYTES`
39
+ * bound of the pre-signed upload capability, which it enforces on every arm).
40
+ * Checking it HERE is what turns that refusal into a sentence the owner can act
41
+ * on, instead of a chip that fails for no stated reason. */
42
+ export const ARIA_MAX_IMAGE_BYTES = 8 * 1024 * 1024;
43
+
44
+ /** A chip in the composer. Every field is always present — a `$item.` path that
45
+ * is missing on some rows does not substitute — and each `…Hidden` flag
46
+ * collapses the part it names. */
47
+ export interface AriaAttachmentChip {
48
+ /** Minted by the worker, never derived from the file. The native Aria app keyed
49
+ * concurrent uploads by file NAME and collided on the second `IMG_0001.jpg`. */
50
+ id: string;
51
+ name: string;
52
+ mimeType: string;
53
+ state: "uploading" | "ready" | "failed";
54
+ /** The chip's thumbnail as a `data:` URI, set only when the picked image is
55
+ * small; "" otherwise, which collapses the preview. The full bytes an upload
56
+ * and a retry send are held by the worker, never in the chip, because the chip
57
+ * rides the service state and a large photo there would exceed the web
58
+ * runtime's frame limit. */
59
+ thumbUrl: string;
60
+ thumbHidden: boolean;
61
+ /** "Uploading…" / "Couldn't upload" / "" — collapses when empty. */
62
+ statusText: string;
63
+ statusHidden: boolean;
64
+ /** The retry control shows ONLY on a failed chip. */
65
+ retryHidden: boolean;
66
+ /** `genie-upload://<id>` once the bytes have landed; "" until then. The send
67
+ * carries a chip only when this is set. */
68
+ ref: string;
69
+ }
70
+
71
+ /** What an upload reports back, delivered as a fresh action so it lands on the
72
+ * CURRENT state rather than on the snapshot the upload started from. */
73
+ export interface AriaAttachmentOutcome {
74
+ id: string;
75
+ ok: boolean;
76
+ /** Set when `ok`. */
77
+ ref?: string;
78
+ }
79
+
80
+ export interface ParsedDataUri { mimeType: string; base64: string; bytes: number }
81
+
82
+ /** `data:<mime>;base64,<payload>` → its parts, or null for anything else.
83
+ *
84
+ * Only the base64 form: every picker this composer is wired to returns it, and
85
+ * a percent-encoded `data:` URI would need decoding the bridge cannot do. The
86
+ * byte count is computed from the payload length, so a multi-megabyte photo is
87
+ * sized without being decoded. */
88
+ export function parseDataUri(uri: string): ParsedDataUri | null {
89
+ const m = /^data:([^;,]*)((?:;[^;,]*)*?);base64,/i.exec(uri ?? "");
90
+ if (!m) return null;
91
+ const base64 = uri.slice(m[0].length).replace(/\s+/g, "");
92
+ const pad = base64.endsWith("==") ? 2 : base64.endsWith("=") ? 1 : 0;
93
+ const bytes = Math.max(0, Math.floor((base64.length * 3) / 4) - pad);
94
+ return { mimeType: (m[1] || "").trim().toLowerCase(), base64, bytes };
95
+ }
96
+
97
+ /** Normalize a MIME type a picker reported.
98
+ *
99
+ * Some pickers hand back a platform type identifier where a MIME type belongs
100
+ * (`public.jpeg`, `public.heic`), and the service validates the field as a MIME
101
+ * type. Mapped for the image identifiers this composer accepts; anything else
102
+ * is returned lowercased and left for the allowlist to judge. */
103
+ export function normalizeMime(mime: string): string {
104
+ const v = (mime ?? "").trim().toLowerCase();
105
+ switch (v) {
106
+ case "public.jpeg": return "image/jpeg";
107
+ case "public.png": return "image/png";
108
+ case "public.heic": return "image/heic";
109
+ case "com.compuserve.gif": return "image/gif";
110
+ case "org.webmproject.webp": return "image/webp";
111
+ case "image/jpg": return "image/jpeg";
112
+ default: return v;
113
+ }
114
+ }
115
+
116
+ /** A file name for an image the picker did not name, by type. The service
117
+ * requires one (1–255 characters), and it is what the transcript shows. */
118
+ export function imageFileName(mimeType: string, n: number, given?: string): string {
119
+ const name = (given ?? "").trim();
120
+ if (name) return name.slice(0, 255);
121
+ const ext = mimeType === "image/png" ? "png"
122
+ : mimeType === "image/webp" ? "webp"
123
+ : mimeType === "image/gif" ? "gif"
124
+ : mimeType === "image/heic" ? "heic"
125
+ : "jpg";
126
+ return `photo-${n}.${ext}`;
127
+ }
128
+
129
+ /** Why a picked file cannot be attached, or "" when it can. */
130
+ export type AttachRefusal = "" | "type" | "size" | "count";
131
+
132
+ export function refusalFor(parsed: ParsedDataUri | null, mimeType: string, attached: number): AttachRefusal {
133
+ if (attached >= ARIA_MAX_ATTACHMENTS) return "count";
134
+ if (!parsed || !ARIA_IMAGE_TYPES.includes(mimeType)) return "type";
135
+ if (parsed.bytes > ARIA_MAX_IMAGE_BYTES) return "size";
136
+ return "";
137
+ }
138
+
139
+ /** A chip in a given state. One constructor so the flags can never disagree
140
+ * with the state they describe — a failed chip without its retry control is
141
+ * the shape of bug this rules out. */
142
+ export function chipIn(
143
+ base: Pick<AriaAttachmentChip, "id" | "name" | "mimeType" | "thumbUrl">,
144
+ state: AriaAttachmentChip["state"],
145
+ labels: { uploading: string; failed: string },
146
+ ref = "",
147
+ ): AriaAttachmentChip {
148
+ const statusText = state === "uploading" ? labels.uploading : state === "failed" ? labels.failed : "";
149
+ return {
150
+ ...base,
151
+ state,
152
+ thumbHidden: !base.thumbUrl,
153
+ statusText,
154
+ statusHidden: !statusText,
155
+ retryHidden: state !== "failed",
156
+ ref: state === "ready" ? ref : "",
157
+ };
158
+ }
159
+
160
+ /** Why Send is refused while attachments are pending, or "" when it is not.
161
+ *
162
+ * An upload still running would be dropped from the message, and a failed one
163
+ * would be sent as if the owner had never picked it — in both cases the
164
+ * assistant answers about a photo it never received. So the send waits, and
165
+ * says what it is waiting for. */
166
+ export function sendBlocker(chips: readonly AriaAttachmentChip[]): "" | "uploading" | "failed" {
167
+ if (chips.some((c) => c.state === "uploading")) return "uploading";
168
+ if (chips.some((c) => c.state === "failed")) return "failed";
169
+ return "";
170
+ }
171
+
172
+ /** The one line a bubble shows for its attachments: a paperclip and the file
173
+ * names. Text, not thumbnails, and not by choice: a `genie-upload://`
174
+ * reference has no published download url, so a sent photo cannot be shown
175
+ * again from the server's copy — and a resumed conversation has nothing else. */
176
+ export function attachmentLine(names: readonly string[]): string {
177
+ const shown = names.map((n) => n.trim()).filter(Boolean);
178
+ return shown.length ? `📎 ${shown.join(", ")}` : "";
179
+ }