@cossistant/react 0.0.29 → 0.0.31

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 (305) hide show
  1. package/README.md +3 -1
  2. package/_virtual/rolldown_runtime.js +9 -23
  3. package/hooks/index.d.ts +2 -2
  4. package/hooks/private/store/use-conversations-store.d.ts +2 -0
  5. package/hooks/private/store/use-conversations-store.d.ts.map +1 -1
  6. package/hooks/private/store/use-conversations-store.js +15 -8
  7. package/hooks/private/store/use-conversations-store.js.map +1 -1
  8. package/hooks/private/store/use-store-selector.d.ts +3 -0
  9. package/hooks/private/store/use-store-selector.d.ts.map +1 -1
  10. package/hooks/private/store/use-store-selector.js +4 -8
  11. package/hooks/private/store/use-store-selector.js.map +1 -1
  12. package/hooks/private/store/use-website-store.d.ts +3 -1
  13. package/hooks/private/store/use-website-store.d.ts.map +1 -1
  14. package/hooks/private/store/use-website-store.js +14 -6
  15. package/hooks/private/store/use-website-store.js.map +1 -1
  16. package/hooks/private/use-client-query.d.ts +1 -1
  17. package/hooks/private/use-client-query.d.ts.map +1 -1
  18. package/hooks/private/use-client-query.js +1 -0
  19. package/hooks/private/use-client-query.js.map +1 -1
  20. package/hooks/private/use-default-messages.d.ts +1 -1
  21. package/hooks/private/use-grouped-messages.d.ts +2 -2
  22. package/hooks/private/use-grouped-messages.d.ts.map +1 -1
  23. package/hooks/private/use-grouped-messages.js +34 -10
  24. package/hooks/private/use-grouped-messages.js.map +1 -1
  25. package/hooks/private/use-rest-client.d.ts +13 -3
  26. package/hooks/private/use-rest-client.d.ts.map +1 -1
  27. package/hooks/private/use-rest-client.js +49 -22
  28. package/hooks/private/use-rest-client.js.map +1 -1
  29. package/hooks/private/use-visitor-typing-reporter.d.ts +1 -1
  30. package/hooks/use-conversation-auto-seen.d.ts +1 -1
  31. package/hooks/use-conversation-page.d.ts +1 -1
  32. package/hooks/use-conversation-page.d.ts.map +1 -1
  33. package/hooks/use-conversation-page.js +13 -4
  34. package/hooks/use-conversation-page.js.map +1 -1
  35. package/hooks/use-conversation-preview.d.ts +3 -1
  36. package/hooks/use-conversation-preview.d.ts.map +1 -1
  37. package/hooks/use-conversation-preview.js +8 -4
  38. package/hooks/use-conversation-preview.js.map +1 -1
  39. package/hooks/use-conversation-seen.d.ts +1 -1
  40. package/hooks/use-conversation-timeline-items.d.ts +1 -1
  41. package/hooks/use-conversation-timeline-items.js +2 -3
  42. package/hooks/use-conversation-timeline-items.js.map +1 -1
  43. package/hooks/use-conversation-timeline.d.ts +1 -1
  44. package/hooks/use-conversation.d.ts +1 -1
  45. package/hooks/use-conversation.js +2 -3
  46. package/hooks/use-conversation.js.map +1 -1
  47. package/hooks/use-conversations.d.ts +1 -1
  48. package/hooks/use-conversations.js +5 -3
  49. package/hooks/use-conversations.js.map +1 -1
  50. package/hooks/use-create-conversation.d.ts +3 -3
  51. package/hooks/use-create-conversation.js +1 -0
  52. package/hooks/use-create-conversation.js.map +1 -1
  53. package/hooks/use-file-upload.d.ts +1 -1
  54. package/hooks/use-file-upload.js +3 -3
  55. package/hooks/use-file-upload.js.map +1 -1
  56. package/hooks/use-home-page.js +3 -3
  57. package/hooks/use-home-page.js.map +1 -1
  58. package/hooks/use-message-composer.d.ts +10 -3
  59. package/hooks/use-message-composer.d.ts.map +1 -1
  60. package/hooks/use-message-composer.js +5 -2
  61. package/hooks/use-message-composer.js.map +1 -1
  62. package/hooks/use-realtime-support.d.ts +1 -1
  63. package/hooks/use-send-message.d.ts +8 -2
  64. package/hooks/use-send-message.d.ts.map +1 -1
  65. package/hooks/use-send-message.js +5 -3
  66. package/hooks/use-send-message.js.map +1 -1
  67. package/hooks/use-visitor.js +2 -2
  68. package/hooks/use-visitor.js.map +1 -1
  69. package/identify-visitor.d.ts.map +1 -1
  70. package/identify-visitor.js +15 -1
  71. package/identify-visitor.js.map +1 -1
  72. package/index.d.ts +2 -2
  73. package/index.js +1 -1
  74. package/package.json +6 -3
  75. package/{conversation.d.ts → packages/types/src/api/conversation.d.ts} +374 -64
  76. package/packages/types/src/api/conversation.d.ts.map +1 -0
  77. package/packages/types/src/api/timeline-item.d.ts +460 -0
  78. package/packages/types/src/api/timeline-item.d.ts.map +1 -0
  79. package/{realtime-events.d.ts → packages/types/src/realtime-events.d.ts} +449 -47
  80. package/packages/types/src/realtime-events.d.ts.map +1 -0
  81. package/{schemas3.d.ts → packages/types/src/schemas.d.ts} +97 -19
  82. package/packages/types/src/schemas.d.ts.map +1 -0
  83. package/primitives/avatar/avatar.js +1 -1
  84. package/primitives/avatar/avatar.js.map +1 -1
  85. package/primitives/avatar/fallback.js +1 -1
  86. package/primitives/avatar/fallback.js.map +1 -1
  87. package/primitives/avatar/image.js +1 -1
  88. package/primitives/avatar/image.js.map +1 -1
  89. package/primitives/button.js +1 -1
  90. package/primitives/button.js.map +1 -1
  91. package/primitives/conversation-timeline.d.ts +1 -1
  92. package/primitives/conversation-timeline.js +4 -4
  93. package/primitives/conversation-timeline.js.map +1 -1
  94. package/primitives/day-separator.js +3 -3
  95. package/primitives/day-separator.js.map +1 -1
  96. package/primitives/multimodal-input.d.ts +2 -2
  97. package/primitives/multimodal-input.d.ts.map +1 -1
  98. package/primitives/multimodal-input.js +2 -2
  99. package/primitives/multimodal-input.js.map +1 -1
  100. package/primitives/timeline-item-attachments.d.ts +1 -1
  101. package/primitives/timeline-item-attachments.js +6 -7
  102. package/primitives/timeline-item-attachments.js.map +1 -1
  103. package/primitives/timeline-item-group.d.ts +1 -1
  104. package/primitives/timeline-item-group.js +7 -7
  105. package/primitives/timeline-item-group.js.map +1 -1
  106. package/primitives/timeline-item.d.ts +1 -1
  107. package/primitives/timeline-item.d.ts.map +1 -1
  108. package/primitives/timeline-item.js +54 -14
  109. package/primitives/timeline-item.js.map +1 -1
  110. package/primitives/trigger.js +1 -1
  111. package/primitives/trigger.js.map +1 -1
  112. package/primitives/window.js +1 -1
  113. package/primitives/window.js.map +1 -1
  114. package/provider.d.ts +4 -2
  115. package/provider.d.ts.map +1 -1
  116. package/provider.js +56 -8
  117. package/provider.js.map +1 -1
  118. package/realtime/event-filter.d.ts +4 -1
  119. package/realtime/event-filter.d.ts.map +1 -1
  120. package/realtime/event-filter.js +14 -0
  121. package/realtime/event-filter.js.map +1 -1
  122. package/realtime/provider.d.ts +1 -1
  123. package/realtime/provider.d.ts.map +1 -1
  124. package/realtime/provider.js +1 -2
  125. package/realtime/provider.js.map +1 -1
  126. package/realtime/seen-store.d.ts +2 -2
  127. package/realtime/support-provider.js +3 -2
  128. package/realtime/support-provider.js.map +1 -1
  129. package/realtime/typing-store.d.ts +1 -1
  130. package/realtime/use-realtime.d.ts +1 -1
  131. package/support/components/avatar-stack.d.ts.map +1 -1
  132. package/support/components/avatar-stack.js +32 -12
  133. package/support/components/avatar-stack.js.map +1 -1
  134. package/support/components/avatar.d.ts +34 -3
  135. package/support/components/avatar.d.ts.map +1 -1
  136. package/support/components/avatar.js +61 -8
  137. package/support/components/avatar.js.map +1 -1
  138. package/support/components/button.d.ts +4 -2
  139. package/support/components/button.d.ts.map +1 -1
  140. package/support/components/button.js +3 -3
  141. package/support/components/button.js.map +1 -1
  142. package/support/components/configuration-error.d.ts +16 -0
  143. package/support/components/configuration-error.d.ts.map +1 -0
  144. package/support/components/configuration-error.js +162 -0
  145. package/support/components/configuration-error.js.map +1 -0
  146. package/support/components/content.js +1 -2
  147. package/support/components/content.js.map +1 -1
  148. package/support/components/conversation-button-link.js +18 -23
  149. package/support/components/conversation-button-link.js.map +1 -1
  150. package/support/components/conversation-event.d.ts.map +1 -1
  151. package/support/components/conversation-event.js +7 -5
  152. package/support/components/conversation-event.js.map +1 -1
  153. package/support/components/conversation-resolved-feedback.d.ts +21 -0
  154. package/support/components/conversation-resolved-feedback.d.ts.map +1 -0
  155. package/support/components/conversation-resolved-feedback.js +59 -0
  156. package/support/components/conversation-resolved-feedback.js.map +1 -0
  157. package/support/components/conversation-timeline-utils.d.ts +5 -0
  158. package/support/components/conversation-timeline-utils.d.ts.map +1 -0
  159. package/support/components/conversation-timeline-utils.js +10 -0
  160. package/support/components/conversation-timeline-utils.js.map +1 -0
  161. package/support/components/conversation-timeline.d.ts +1 -1
  162. package/support/components/conversation-timeline.d.ts.map +1 -1
  163. package/support/components/conversation-timeline.js +5 -4
  164. package/support/components/conversation-timeline.js.map +1 -1
  165. package/support/components/header.js +1 -1
  166. package/support/components/icons.d.ts +1 -1
  167. package/support/components/icons.d.ts.map +1 -1
  168. package/support/components/icons.js +6 -2
  169. package/support/components/icons.js.map +1 -1
  170. package/support/components/image-lightbox.d.ts +1 -1
  171. package/support/components/image-lightbox.js +1 -2
  172. package/support/components/image-lightbox.js.map +1 -1
  173. package/support/components/index.d.ts +2 -1
  174. package/support/components/index.js +3 -2
  175. package/support/components/multimodal-input.js +0 -1
  176. package/support/components/multimodal-input.js.map +1 -1
  177. package/support/components/navigation-tab.js +1 -1
  178. package/support/components/online-indicator.d.ts +50 -0
  179. package/support/components/online-indicator.d.ts.map +1 -0
  180. package/support/components/online-indicator.js +65 -0
  181. package/support/components/online-indicator.js.map +1 -0
  182. package/support/components/root.js +0 -1
  183. package/support/components/root.js.map +1 -1
  184. package/support/components/timeline-identification-tool.js +4 -4
  185. package/support/components/timeline-identification-tool.js.map +1 -1
  186. package/support/components/timeline-message-group.d.ts +1 -1
  187. package/support/components/timeline-message-group.d.ts.map +1 -1
  188. package/support/components/timeline-message-group.js +6 -4
  189. package/support/components/timeline-message-group.js.map +1 -1
  190. package/support/components/timeline-message-item.d.ts +1 -1
  191. package/support/components/timeline-message-item.js +4 -4
  192. package/support/components/timeline-message-item.js.map +1 -1
  193. package/support/components/trigger.js +1 -2
  194. package/support/components/trigger.js.map +1 -1
  195. package/support/components/typing-indicator.js +1 -1
  196. package/support/components/typing-indicator.js.map +1 -1
  197. package/support/context/controlled-state.js +0 -1
  198. package/support/context/controlled-state.js.map +1 -1
  199. package/support/context/events.d.ts +1 -1
  200. package/support/context/events.js +0 -1
  201. package/support/context/events.js.map +1 -1
  202. package/support/context/handle.js +0 -1
  203. package/support/context/handle.js.map +1 -1
  204. package/support/context/identification.d.ts +33 -0
  205. package/support/context/identification.d.ts.map +1 -0
  206. package/support/context/identification.js +34 -0
  207. package/support/context/identification.js.map +1 -0
  208. package/support/context/positioning.js +0 -1
  209. package/support/context/positioning.js.map +1 -1
  210. package/support/context/slots.js +0 -1
  211. package/support/context/slots.js.map +1 -1
  212. package/support/context/websocket.d.ts +1 -1
  213. package/support/context/websocket.js +0 -1
  214. package/support/context/websocket.js.map +1 -1
  215. package/support/index.d.ts.map +1 -1
  216. package/support/index.js +51 -18
  217. package/support/index.js.map +1 -1
  218. package/support/pages/conversation-history.js +2 -1
  219. package/support/pages/conversation-history.js.map +1 -1
  220. package/support/pages/conversation.d.ts +1 -1
  221. package/support/pages/conversation.d.ts.map +1 -1
  222. package/support/pages/conversation.js +34 -8
  223. package/support/pages/conversation.js.map +1 -1
  224. package/support/pages/home.js +5 -3
  225. package/support/pages/home.js.map +1 -1
  226. package/support/router.d.ts.map +1 -1
  227. package/support/router.js +4 -0
  228. package/support/router.js.map +1 -1
  229. package/support/store/support-store.js +0 -1
  230. package/support/store/support-store.js.map +1 -1
  231. package/support/{support-C7Xaw-N6.css → support-DmViRaga.css} +2 -2
  232. package/support/{support-C7Xaw-N6.css.map → support-DmViRaga.css.map} +1 -1
  233. package/support/text/index.js +1 -1
  234. package/support/text/index.js.map +1 -1
  235. package/support/text/locales/en.js +10 -1
  236. package/support/text/locales/en.js.map +1 -1
  237. package/support/text/locales/es.js +10 -1
  238. package/support/text/locales/es.js.map +1 -1
  239. package/support/text/locales/fr.js +10 -1
  240. package/support/text/locales/fr.js.map +1 -1
  241. package/support/text/locales/keys.d.ts +11 -0
  242. package/support/text/locales/keys.d.ts.map +1 -1
  243. package/support/text/locales/keys.js +3 -0
  244. package/support/text/locales/keys.js.map +1 -1
  245. package/support/utils/index.d.ts +1 -1
  246. package/support-config.js +0 -1
  247. package/support-config.js.map +1 -1
  248. package/support.css +1 -1
  249. package/tailwind.css +1 -1
  250. package/utils/conversation.d.ts.map +1 -1
  251. package/utils/conversation.js +1 -3
  252. package/utils/conversation.js.map +1 -1
  253. package/utils/use-render-element.js +2 -2
  254. package/utils/use-render-element.js.map +1 -1
  255. package/api.d.ts +0 -71
  256. package/api.d.ts.map +0 -1
  257. package/checks.d.ts +0 -189
  258. package/checks.d.ts.map +0 -1
  259. package/clsx.d.ts +0 -7
  260. package/clsx.d.ts.map +0 -1
  261. package/coerce.d.ts +0 -9
  262. package/coerce.d.ts.map +0 -1
  263. package/conversation.d.ts.map +0 -1
  264. package/core.d.ts +0 -35
  265. package/core.d.ts.map +0 -1
  266. package/errors.d.ts +0 -130
  267. package/errors.d.ts.map +0 -1
  268. package/errors2.d.ts +0 -24
  269. package/errors2.d.ts.map +0 -1
  270. package/index2.d.ts +0 -4
  271. package/index3.d.ts +0 -1
  272. package/json-schema.d.ts +0 -70
  273. package/json-schema.d.ts.map +0 -1
  274. package/metadata.d.ts +0 -1
  275. package/openapi-generator.d.ts +0 -1
  276. package/openapi-generator2.d.ts +0 -1
  277. package/openapi-generator3.d.ts +0 -1
  278. package/openapi30.d.ts +0 -125
  279. package/openapi30.d.ts.map +0 -1
  280. package/openapi31.d.ts +0 -131
  281. package/openapi31.d.ts.map +0 -1
  282. package/parse.d.ts +0 -17
  283. package/parse.d.ts.map +0 -1
  284. package/realtime-events.d.ts.map +0 -1
  285. package/registries.d.ts +0 -32
  286. package/registries.d.ts.map +0 -1
  287. package/schemas.d.ts +0 -971
  288. package/schemas.d.ts.map +0 -1
  289. package/schemas2.d.ts +0 -345
  290. package/schemas2.d.ts.map +0 -1
  291. package/schemas3.d.ts.map +0 -1
  292. package/specification-extension.d.ts +0 -9
  293. package/specification-extension.d.ts.map +0 -1
  294. package/standard-schema.d.ts +0 -121
  295. package/standard-schema.d.ts.map +0 -1
  296. package/timeline-item.d.ts +0 -227
  297. package/timeline-item.d.ts.map +0 -1
  298. package/to-json-schema.d.ts +0 -96
  299. package/to-json-schema.d.ts.map +0 -1
  300. package/util.d.ts +0 -45
  301. package/util.d.ts.map +0 -1
  302. package/versions.d.ts +0 -9
  303. package/versions.d.ts.map +0 -1
  304. package/zod-extensions.d.ts +0 -39
  305. package/zod-extensions.d.ts.map +0 -1
@@ -1,23 +1,39 @@
1
1
  import { cn } from "../utils/index.js";
2
2
  import { useRenderElement } from "../../utils/use-render-element.js";
3
3
  import { Avatar } from "./avatar.js";
4
- import { CossistantLogo } from "./cossistant-branding.js";
5
4
  import { jsx, jsxs } from "react/jsx-runtime";
6
5
 
7
6
  //#region src/support/components/avatar-stack.tsx
8
- const AvatarStackItem = ({ children, index, size = 44, spacing = 28, gapWidth = 2, className }) => {
7
+ /**
8
+ * Creates an SVG mask with a rounded rectangle cutout on the left side.
9
+ * This respects the border radius of the avatars.
10
+ */
11
+ function createRoundedCutoutMask(size, cutoutWidth, borderRadius) {
12
+ const extension = borderRadius * .15;
13
+ const svg = `
14
+ <svg xmlns="http://www.w3.org/2000/svg" width="${size}" height="${size}">
15
+ <defs>
16
+ <mask id="m">
17
+ <rect width="${size}" height="${size}" fill="white"/>
18
+ <rect x="${-size + cutoutWidth}" y="${-extension}" width="${size}" height="${size + extension * 2}" rx="${borderRadius}" ry="${borderRadius}" fill="black"/>
19
+ </mask>
20
+ </defs>
21
+ <rect width="${size}" height="${size}" fill="white" mask="url(#m)"/>
22
+ </svg>
23
+ `.replace(/\s+/g, " ");
24
+ return `url("data:image/svg+xml,${encodeURIComponent(svg)}")`;
25
+ }
26
+ const AvatarStackItem = ({ children, index, size = 44, spacing = 32, gapWidth = 1, className }) => {
9
27
  const isFirst = index === 0;
10
- const circleRadius = size * .5;
11
- const cutoutRadius = circleRadius + gapWidth;
12
- const cutoutPosition = `${circleRadius - spacing}px`;
28
+ const maskImage = createRoundedCutoutMask(size, size - spacing + gapWidth, 4);
13
29
  return useRenderElement("div", { className }, { props: {
14
30
  className: cn("relative grid place-items-center", !isFirst && "[mask-repeat:no-repeat] [mask-size:100%_100%]"),
15
31
  style: {
16
32
  width: `${size}px`,
17
33
  height: `${size}px`,
18
34
  ...isFirst ? {} : {
19
- mask: `radial-gradient(${cutoutRadius}px ${cutoutRadius}px at ${cutoutPosition} 50%, transparent ${cutoutRadius}px, white ${cutoutRadius}px)`,
20
- WebkitMask: `radial-gradient(${cutoutRadius}px ${cutoutRadius}px at ${cutoutPosition} 50%, transparent ${cutoutRadius}px, white ${cutoutRadius}px)`
35
+ maskImage,
36
+ WebkitMaskImage: maskImage
21
37
  }
22
38
  },
23
39
  children
@@ -27,7 +43,7 @@ const AvatarStackItem = ({ children, index, size = 44, spacing = 28, gapWidth =
27
43
  * Displays a compact row of agent avatars with optional branding and overflow
28
44
  * counts.
29
45
  */
30
- function AvatarStack({ humanAgents, aiAgents, hideBranding = false, hideDefaultAIAgent = true, className, size = 44, spacing = 28, gapWidth = 3 }) {
46
+ function AvatarStack({ humanAgents, aiAgents, hideBranding = false, hideDefaultAIAgent = true, className, size = 44, spacing = 36, gapWidth = 3 }) {
31
47
  const displayedHumanAgents = humanAgents.slice(0, 2);
32
48
  const remainingHumanAgentsCount = Math.max(0, humanAgents.length - 2);
33
49
  const items = [
@@ -56,15 +72,19 @@ function AvatarStack({ humanAgents, aiAgents, hideBranding = false, hideDefaultA
56
72
  item.type === "human" && /* @__PURE__ */ jsx(Avatar, {
57
73
  className: cn("size-full"),
58
74
  image: item.agent.image,
75
+ lastSeenAt: item.agent.lastSeenAt,
59
76
  name: item.agent.name
60
77
  }),
61
78
  item.type === "count" && /* @__PURE__ */ jsxs("div", {
62
- className: "flex size-full items-center justify-center rounded-full bg-co-background-200 font-medium text-co-primary text-sm dark:bg-co-background-500",
79
+ className: "flex size-full items-center justify-center rounded bg-co-background-200 font-medium text-co-primary text-sm ring-1 ring-co-border/30 dark:bg-co-background-500",
63
80
  children: ["+", item.count]
64
81
  }),
65
- item.type === "ai" && /* @__PURE__ */ jsx("div", {
66
- className: "flex size-full items-center justify-center rounded-full bg-co-background-200 dark:bg-co-background-600",
67
- children: /* @__PURE__ */ jsx(CossistantLogo, { className: "h-[50%] min-h-4 w-[50%] min-w-4" })
82
+ item.type === "ai" && /* @__PURE__ */ jsx(Avatar, {
83
+ className: "z-0 size-full",
84
+ image: item.agent?.image,
85
+ isAI: true,
86
+ name: item.agent?.name || "AI",
87
+ showBackground: !!item.agent?.image
68
88
  })
69
89
  ]
70
90
  }, `avatar-${index}`))
@@ -1 +1 @@
1
- {"version":3,"file":"avatar-stack.js","names":[],"sources":["../../../src/support/components/avatar-stack.tsx"],"sourcesContent":["import type { AvailableAIAgent, AvailableHumanAgent } from \"@cossistant/types\";\nimport type { ReactElement, ReactNode } from \"react\";\nimport { useRenderElement } from \"../../utils/use-render-element\";\nimport { cn } from \"../utils\";\nimport { Avatar } from \"./avatar\";\nimport { CossistantLogo } from \"./cossistant-branding\";\n\ntype AvatarStackProps = {\n\thumanAgents: AvailableHumanAgent[];\n\taiAgents: AvailableAIAgent[];\n\thideBranding?: boolean;\n\thideDefaultAIAgent?: boolean;\n\tclassName?: string;\n\t/** Size of avatars (default: 44px) */\n\tsize?: number;\n\t/** Space between avatars (default: 28px) */\n\tspacing?: number;\n\t/** Gap width between avatars (default: 2px) */\n\tgapWidth?: number;\n};\n\nexport const AvatarStackItem = ({\n\tchildren,\n\tindex,\n\tsize = 44,\n\tspacing = 28,\n\tgapWidth = 2,\n\tclassName,\n}: {\n\tchildren: ReactNode;\n\tindex: number;\n\tsize?: number;\n\tspacing?: number;\n\tgapWidth?: number;\n\tclassName?: string;\n}): ReactElement | null => {\n\tconst isFirst = index === 0;\n\n\t// Calculate the circle radius for the mask cutout\n\tconst circleRadius = size * 0.5;\n\tconst cutoutRadius = circleRadius + gapWidth; // Add gap width to create visible border\n\tconst cutoutPosition = `${circleRadius - spacing}px`;\n\n\treturn useRenderElement(\n\t\t\"div\",\n\t\t{ className },\n\t\t{\n\t\t\tprops: {\n\t\t\t\tclassName: cn(\n\t\t\t\t\t\"relative grid place-items-center\",\n\t\t\t\t\t!isFirst && \"[mask-repeat:no-repeat] [mask-size:100%_100%]\"\n\t\t\t\t),\n\t\t\t\tstyle: {\n\t\t\t\t\twidth: `${size}px`,\n\t\t\t\t\theight: `${size}px`,\n\t\t\t\t\t// Apply mask only to non-first items\n\t\t\t\t\t...(isFirst\n\t\t\t\t\t\t? {}\n\t\t\t\t\t\t: {\n\t\t\t\t\t\t\t\tmask: `radial-gradient(${cutoutRadius}px ${cutoutRadius}px at ${cutoutPosition} 50%, transparent ${cutoutRadius}px, white ${cutoutRadius}px)`,\n\t\t\t\t\t\t\t\tWebkitMask: `radial-gradient(${cutoutRadius}px ${cutoutRadius}px at ${cutoutPosition} 50%, transparent ${cutoutRadius}px, white ${cutoutRadius}px)`,\n\t\t\t\t\t\t\t}),\n\t\t\t\t},\n\t\t\t\tchildren,\n\t\t\t},\n\t\t}\n\t);\n};\n\n/**\n * Displays a compact row of agent avatars with optional branding and overflow\n * counts.\n */\nexport function AvatarStack({\n\thumanAgents,\n\taiAgents,\n\thideBranding = false,\n\thideDefaultAIAgent = true,\n\tclassName,\n\tsize = 44,\n\tspacing = 28,\n\tgapWidth = 3,\n}: AvatarStackProps): ReactElement | null {\n\tconst displayedHumanAgents = humanAgents.slice(0, 2);\n\tconst remainingHumanAgentsCount = Math.max(0, humanAgents.length - 2);\n\n\t// Create array of all items to display\n\tconst items = [\n\t\t...displayedHumanAgents.map((agent) => ({\n\t\t\ttype: \"human\" as const,\n\t\t\tagent,\n\t\t})),\n\t\t...(remainingHumanAgentsCount > 0\n\t\t\t? [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"count\" as const,\n\t\t\t\t\t\tcount: remainingHumanAgentsCount,\n\t\t\t\t\t},\n\t\t\t\t]\n\t\t\t: []),\n\t\t...(hideDefaultAIAgent\n\t\t\t? []\n\t\t\t: [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"ai\" as const,\n\t\t\t\t\t\tagent: aiAgents[0],\n\t\t\t\t\t},\n\t\t\t\t]),\n\t];\n\n\treturn useRenderElement(\n\t\t\"div\",\n\t\t{ className },\n\t\t{\n\t\t\tprops: {\n\t\t\t\tclassName: \"inline-grid items-center\",\n\t\t\t\tstyle: {\n\t\t\t\t\tgridTemplateColumns: `repeat(${items.length}, ${spacing}px)`,\n\t\t\t\t},\n\t\t\t\tchildren: items.map((item, index) => (\n\t\t\t\t\t<AvatarStackItem\n\t\t\t\t\t\tgapWidth={gapWidth}\n\t\t\t\t\t\tindex={index}\n\t\t\t\t\t\tkey={`avatar-${index}`}\n\t\t\t\t\t\tsize={size}\n\t\t\t\t\t\tspacing={spacing}\n\t\t\t\t\t>\n\t\t\t\t\t\t{item.type === \"human\" && (\n\t\t\t\t\t\t\t<Avatar\n\t\t\t\t\t\t\t\tclassName={cn(\"size-full\")}\n\t\t\t\t\t\t\t\timage={item.agent.image}\n\t\t\t\t\t\t\t\tname={item.agent.name}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{item.type === \"count\" && (\n\t\t\t\t\t\t\t<div className=\"flex size-full items-center justify-center rounded-full bg-co-background-200 font-medium text-co-primary text-sm dark:bg-co-background-500\">\n\t\t\t\t\t\t\t\t+{item.count}\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{item.type === \"ai\" && (\n\t\t\t\t\t\t\t<div className=\"flex size-full items-center justify-center rounded-full bg-co-background-200 dark:bg-co-background-600\">\n\t\t\t\t\t\t\t\t<CossistantLogo className=\"h-[50%] min-h-4 w-[50%] min-w-4\" />\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t)}\n\t\t\t\t\t</AvatarStackItem>\n\t\t\t\t)),\n\t\t\t},\n\t\t}\n\t);\n}\n"],"mappings":";;;;;;;AAqBA,MAAa,mBAAmB,EAC/B,UACA,OACA,OAAO,IACP,UAAU,IACV,WAAW,GACX,gBAQ0B;CAC1B,MAAM,UAAU,UAAU;CAG1B,MAAM,eAAe,OAAO;CAC5B,MAAM,eAAe,eAAe;CACpC,MAAM,iBAAiB,GAAG,eAAe,QAAQ;AAEjD,QAAO,iBACN,OACA,EAAE,WAAW,EACb,EACC,OAAO;EACN,WAAW,GACV,oCACA,CAAC,WAAW,gDACZ;EACD,OAAO;GACN,OAAO,GAAG,KAAK;GACf,QAAQ,GAAG,KAAK;GAEhB,GAAI,UACD,EAAE,GACF;IACA,MAAM,mBAAmB,aAAa,KAAK,aAAa,QAAQ,eAAe,oBAAoB,aAAa,YAAY,aAAa;IACzI,YAAY,mBAAmB,aAAa,KAAK,aAAa,QAAQ,eAAe,oBAAoB,aAAa,YAAY,aAAa;IAC/I;GACH;EACD;EACA,EACD,CACD;;;;;;AAOF,SAAgB,YAAY,EAC3B,aACA,UACA,eAAe,OACf,qBAAqB,MACrB,WACA,OAAO,IACP,UAAU,IACV,WAAW,KAC8B;CACzC,MAAM,uBAAuB,YAAY,MAAM,GAAG,EAAE;CACpD,MAAM,4BAA4B,KAAK,IAAI,GAAG,YAAY,SAAS,EAAE;CAGrE,MAAM,QAAQ;EACb,GAAG,qBAAqB,KAAK,WAAW;GACvC,MAAM;GACN;GACA,EAAE;EACH,GAAI,4BAA4B,IAC7B,CACA;GACC,MAAM;GACN,OAAO;GACP,CACD,GACA,EAAE;EACL,GAAI,qBACD,EAAE,GACF,CACA;GACC,MAAM;GACN,OAAO,SAAS;GAChB,CACD;EACH;AAED,QAAO,iBACN,OACA,EAAE,WAAW,EACb,EACC,OAAO;EACN,WAAW;EACX,OAAO,EACN,qBAAqB,UAAU,MAAM,OAAO,IAAI,QAAQ,MACxD;EACD,UAAU,MAAM,KAAK,MAAM,UAC1B,qBAAC;GACU;GACH;GAED;GACG;;IAER,KAAK,SAAS,WACd,oBAAC;KACA,WAAW,GAAG,YAAY;KAC1B,OAAO,KAAK,MAAM;KAClB,MAAM,KAAK,MAAM;MAChB;IAEF,KAAK,SAAS,WACd,qBAAC;KAAI,WAAU;gBAA6I,KACzJ,KAAK;MACF;IAEN,KAAK,SAAS,QACd,oBAAC;KAAI,WAAU;eACd,oBAAC,kBAAe,WAAU,oCAAoC;MACzD;;KAnBF,UAAU,QAqBE,CACjB;EACF,EACD,CACD"}
1
+ {"version":3,"file":"avatar-stack.js","names":[],"sources":["../../../src/support/components/avatar-stack.tsx"],"sourcesContent":["import type { AvailableAIAgent, AvailableHumanAgent } from \"@cossistant/types\";\nimport type { ReactElement, ReactNode } from \"react\";\nimport { useRenderElement } from \"../../utils/use-render-element\";\nimport { cn } from \"../utils\";\nimport { Avatar } from \"./avatar\";\n\ntype AvatarStackProps = {\n\thumanAgents: AvailableHumanAgent[];\n\taiAgents: AvailableAIAgent[];\n\thideBranding?: boolean;\n\thideDefaultAIAgent?: boolean;\n\tclassName?: string;\n\t/** Size of avatars (default: 44px) */\n\tsize?: number;\n\t/** Space between avatars (default: 28px) */\n\tspacing?: number;\n\t/** Gap width between avatars (default: 2px) */\n\tgapWidth?: number;\n};\n\n/**\n * Creates an SVG mask with a rounded rectangle cutout on the left side.\n * This respects the border radius of the avatars.\n */\nfunction createRoundedCutoutMask(\n\tsize: number,\n\tcutoutWidth: number,\n\tborderRadius: number\n): string {\n\t// SVG mask: white = visible, black = hidden\n\t// We create a white rectangle (full size) and subtract a rounded rect on the left\n\t// The cutout rect is extended beyond top/bottom bounds so only the right-side curve is visible\n\tconst extension = borderRadius * 0.15;\n\tconst svg = `\n\t\t<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"${size}\" height=\"${size}\">\n\t\t\t<defs>\n\t\t\t\t<mask id=\"m\">\n\t\t\t\t\t<rect width=\"${size}\" height=\"${size}\" fill=\"white\"/>\n\t\t\t\t\t<rect x=\"${-size + cutoutWidth}\" y=\"${-extension}\" width=\"${size}\" height=\"${size + extension * 2}\" rx=\"${borderRadius}\" ry=\"${borderRadius}\" fill=\"black\"/>\n\t\t\t\t</mask>\n\t\t\t</defs>\n\t\t\t<rect width=\"${size}\" height=\"${size}\" fill=\"white\" mask=\"url(#m)\"/>\n\t\t</svg>\n\t`.replace(/\\s+/g, \" \");\n\n\treturn `url(\"data:image/svg+xml,${encodeURIComponent(svg)}\")`;\n}\n\nexport const AvatarStackItem = ({\n\tchildren,\n\tindex,\n\tsize = 44,\n\tspacing = 32,\n\tgapWidth = 1,\n\tclassName,\n}: {\n\tchildren: ReactNode;\n\tindex: number;\n\tsize?: number;\n\tspacing?: number;\n\tgapWidth?: number;\n\tclassName?: string;\n}): ReactElement | null => {\n\tconst isFirst = index === 0;\n\n\t// Calculate mask for squared avatars with rounded corners\n\t// The mask creates a cutout on the left side where the previous avatar overlaps\n\tconst cutoutWidth = size - spacing + gapWidth;\n\tconst borderRadius = 4; // Match the 4px border radius used on avatars\n\n\tconst maskImage = createRoundedCutoutMask(size, cutoutWidth, borderRadius);\n\n\treturn useRenderElement(\n\t\t\"div\",\n\t\t{ className },\n\t\t{\n\t\t\tprops: {\n\t\t\t\tclassName: cn(\n\t\t\t\t\t\"relative grid place-items-center\",\n\t\t\t\t\t!isFirst && \"[mask-repeat:no-repeat] [mask-size:100%_100%]\"\n\t\t\t\t),\n\t\t\t\tstyle: {\n\t\t\t\t\twidth: `${size}px`,\n\t\t\t\t\theight: `${size}px`,\n\t\t\t\t\t// Apply mask only to non-first items - uses SVG for rounded cutout\n\t\t\t\t\t...(isFirst\n\t\t\t\t\t\t? {}\n\t\t\t\t\t\t: {\n\t\t\t\t\t\t\t\tmaskImage,\n\t\t\t\t\t\t\t\tWebkitMaskImage: maskImage,\n\t\t\t\t\t\t\t}),\n\t\t\t\t},\n\t\t\t\tchildren,\n\t\t\t},\n\t\t}\n\t);\n};\n\n/**\n * Displays a compact row of agent avatars with optional branding and overflow\n * counts.\n */\nexport function AvatarStack({\n\thumanAgents,\n\taiAgents,\n\thideBranding = false,\n\thideDefaultAIAgent = true,\n\tclassName,\n\tsize = 44,\n\tspacing = 36,\n\tgapWidth = 3,\n}: AvatarStackProps): ReactElement | null {\n\tconst displayedHumanAgents = humanAgents.slice(0, 2);\n\tconst remainingHumanAgentsCount = Math.max(0, humanAgents.length - 2);\n\n\t// Create array of all items to display\n\tconst items = [\n\t\t...displayedHumanAgents.map((agent) => ({\n\t\t\ttype: \"human\" as const,\n\t\t\tagent,\n\t\t})),\n\t\t...(remainingHumanAgentsCount > 0\n\t\t\t? [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"count\" as const,\n\t\t\t\t\t\tcount: remainingHumanAgentsCount,\n\t\t\t\t\t},\n\t\t\t\t]\n\t\t\t: []),\n\t\t...(hideDefaultAIAgent\n\t\t\t? []\n\t\t\t: [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"ai\" as const,\n\t\t\t\t\t\tagent: aiAgents[0],\n\t\t\t\t\t},\n\t\t\t\t]),\n\t];\n\n\treturn useRenderElement(\n\t\t\"div\",\n\t\t{ className },\n\t\t{\n\t\t\tprops: {\n\t\t\t\tclassName: \"inline-grid items-center\",\n\t\t\t\tstyle: {\n\t\t\t\t\tgridTemplateColumns: `repeat(${items.length}, ${spacing}px)`,\n\t\t\t\t},\n\t\t\t\tchildren: items.map((item, index) => (\n\t\t\t\t\t<AvatarStackItem\n\t\t\t\t\t\tgapWidth={gapWidth}\n\t\t\t\t\t\tindex={index}\n\t\t\t\t\t\tkey={`avatar-${index}`}\n\t\t\t\t\t\tsize={size}\n\t\t\t\t\t\tspacing={spacing}\n\t\t\t\t\t>\n\t\t\t\t\t\t{item.type === \"human\" && (\n\t\t\t\t\t\t\t<Avatar\n\t\t\t\t\t\t\t\tclassName={cn(\"size-full\")}\n\t\t\t\t\t\t\t\timage={item.agent.image}\n\t\t\t\t\t\t\t\tlastSeenAt={item.agent.lastSeenAt}\n\t\t\t\t\t\t\t\tname={item.agent.name}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{item.type === \"count\" && (\n\t\t\t\t\t\t\t<div className=\"flex size-full items-center justify-center rounded bg-co-background-200 font-medium text-co-primary text-sm ring-1 ring-co-border/30 dark:bg-co-background-500\">\n\t\t\t\t\t\t\t\t+{item.count}\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{item.type === \"ai\" && (\n\t\t\t\t\t\t\t<Avatar\n\t\t\t\t\t\t\t\tclassName=\"z-0 size-full\"\n\t\t\t\t\t\t\t\timage={item.agent?.image}\n\t\t\t\t\t\t\t\tisAI\n\t\t\t\t\t\t\t\tname={item.agent?.name || \"AI\"}\n\t\t\t\t\t\t\t\tshowBackground={!!item.agent?.image}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t)}\n\t\t\t\t\t</AvatarStackItem>\n\t\t\t\t)),\n\t\t\t},\n\t\t}\n\t);\n}\n"],"mappings":";;;;;;;;;;AAwBA,SAAS,wBACR,MACA,aACA,cACS;CAIT,MAAM,YAAY,eAAe;CACjC,MAAM,MAAM;mDACsC,KAAK,YAAY,KAAK;;;oBAGrD,KAAK,YAAY,KAAK;gBAC1B,CAAC,OAAO,YAAY,OAAO,CAAC,UAAU,WAAW,KAAK,YAAY,OAAO,YAAY,EAAE,QAAQ,aAAa,QAAQ,aAAa;;;kBAG/H,KAAK,YAAY,KAAK;;GAErC,QAAQ,QAAQ,IAAI;AAEtB,QAAO,2BAA2B,mBAAmB,IAAI,CAAC;;AAG3D,MAAa,mBAAmB,EAC/B,UACA,OACA,OAAO,IACP,UAAU,IACV,WAAW,GACX,gBAQ0B;CAC1B,MAAM,UAAU,UAAU;CAO1B,MAAM,YAAY,wBAAwB,MAHtB,OAAO,UAAU,UAChB,EAEqD;AAE1E,QAAO,iBACN,OACA,EAAE,WAAW,EACb,EACC,OAAO;EACN,WAAW,GACV,oCACA,CAAC,WAAW,gDACZ;EACD,OAAO;GACN,OAAO,GAAG,KAAK;GACf,QAAQ,GAAG,KAAK;GAEhB,GAAI,UACD,EAAE,GACF;IACA;IACA,iBAAiB;IACjB;GACH;EACD;EACA,EACD,CACD;;;;;;AAOF,SAAgB,YAAY,EAC3B,aACA,UACA,eAAe,OACf,qBAAqB,MACrB,WACA,OAAO,IACP,UAAU,IACV,WAAW,KAC8B;CACzC,MAAM,uBAAuB,YAAY,MAAM,GAAG,EAAE;CACpD,MAAM,4BAA4B,KAAK,IAAI,GAAG,YAAY,SAAS,EAAE;CAGrE,MAAM,QAAQ;EACb,GAAG,qBAAqB,KAAK,WAAW;GACvC,MAAM;GACN;GACA,EAAE;EACH,GAAI,4BAA4B,IAC7B,CACA;GACC,MAAM;GACN,OAAO;GACP,CACD,GACA,EAAE;EACL,GAAI,qBACD,EAAE,GACF,CACA;GACC,MAAM;GACN,OAAO,SAAS;GAChB,CACD;EACH;AAED,QAAO,iBACN,OACA,EAAE,WAAW,EACb,EACC,OAAO;EACN,WAAW;EACX,OAAO,EACN,qBAAqB,UAAU,MAAM,OAAO,IAAI,QAAQ,MACxD;EACD,UAAU,MAAM,KAAK,MAAM,UAC1B,qBAAC;GACU;GACH;GAED;GACG;;IAER,KAAK,SAAS,WACd,oBAAC;KACA,WAAW,GAAG,YAAY;KAC1B,OAAO,KAAK,MAAM;KAClB,YAAY,KAAK,MAAM;KACvB,MAAM,KAAK,MAAM;MAChB;IAEF,KAAK,SAAS,WACd,qBAAC;KAAI,WAAU;gBAAiK,KAC7K,KAAK;MACF;IAEN,KAAK,SAAS,QACd,oBAAC;KACA,WAAU;KACV,OAAO,KAAK,OAAO;KACnB;KACA,MAAM,KAAK,OAAO,QAAQ;KAC1B,gBAAgB,CAAC,CAAC,KAAK,OAAO;MAC7B;;KAxBE,UAAU,QA0BE,CACjB;EACF,EACD,CACD"}
@@ -5,15 +5,46 @@ type AvatarProps = {
5
5
  className?: string;
6
6
  image?: string | null;
7
7
  name: string;
8
+ /** Whether this avatar is for an AI agent */
9
+ isAI?: boolean;
10
+ /** Whether to show the background circle (default: true) */
11
+ showBackground?: boolean;
12
+ /**
13
+ * Tailwind class array for Facehash background colors.
14
+ * Defaults to Cossistant theme colors (pink, blue, yellow, orange).
15
+ * @example ["bg-pink-500", "bg-blue-500", "bg-green-500"]
16
+ */
17
+ colorClasses?: string[];
18
+ /**
19
+ * Last seen timestamp for the agent. When provided, shows a status indicator:
20
+ * - Green (online): seen within last 15 minutes
21
+ * - Orange (away): seen within last hour
22
+ * Only shown for non-AI agents.
23
+ */
24
+ lastSeenAt?: string | null;
25
+ /**
26
+ * Size of the online indicator in pixels.
27
+ * Defaults to 6px.
28
+ */
29
+ indicatorSize?: number;
8
30
  };
9
31
  /**
10
- * Renders a circular avatar with graceful fallbacks when no image is
11
- * available.
32
+ * Renders a squared avatar with graceful fallbacks using Facehash when no
33
+ * image is available. Features squircle corners when supported by the browser
34
+ * and a subtle ring border.
35
+ *
36
+ * For AI agents without an image, displays the Cossistant logo without
37
+ * a background.
12
38
  */
13
39
  declare function Avatar({
14
40
  className,
15
41
  image,
16
- name
42
+ name,
43
+ isAI,
44
+ showBackground,
45
+ colorClasses,
46
+ lastSeenAt,
47
+ indicatorSize
17
48
  }: AvatarProps): ReactElement;
18
49
  //#endregion
19
50
  export { Avatar };
@@ -1 +1 @@
1
- {"version":3,"file":"avatar.d.ts","names":[],"sources":["../../../src/support/components/avatar.tsx"],"sourcesContent":[],"mappings":";;;KASK,WAAA;;EAAA,KAAA,CAAA,EAAA,MAAW,GAAA,IAAA;EAUA,IAAA,EAAA,MAAM;CAAG;;;;;AAAoD,iBAA7D,MAAA,CAA6D;EAAA,SAAA;EAAA,KAAA;EAAA;AAAA,CAAA,EAA1B,WAA0B,CAAA,EAAZ,YAAY"}
1
+ {"version":3,"file":"avatar.d.ts","names":[],"sources":["../../../src/support/components/avatar.tsx"],"sourcesContent":[],"mappings":";;;KAuBK,WAAA;;EAAA,KAAA,CAAA,EAAA,MAAW,GAAA,IAAA;EAoCA,IAAA,EAAA,MAAM;EACrB;EACA,IAAA,CAAA,EAAA,OAAA;EACA;EACA,cAAA,CAAA,EAAA,OAAA;EACA;;;;;EAIgB,YAAA,CAAA,EAAA,MAAA,EAAA;EAAY;;;;;;;;;;;;;;;;;;;;;iBATb,MAAA;;;;;;;;;GASb,cAAc"}
@@ -2,22 +2,75 @@ import { cn } from "../utils/index.js";
2
2
  import { Avatar as Avatar$1 } from "../../primitives/avatar/avatar.js";
3
3
  import { AvatarFallback } from "../../primitives/avatar/fallback.js";
4
4
  import { AvatarImage } from "../../primitives/avatar/image.js";
5
+ import { CossistantLogo } from "./cossistant-branding.js";
6
+ import { OnlineIndicator, getAgentStatus } from "./online-indicator.js";
5
7
  import { jsx, jsxs } from "react/jsx-runtime";
8
+ import { Facehash } from "facehash";
6
9
 
7
10
  //#region src/support/components/avatar.tsx
8
11
  /**
9
- * Renders a circular avatar with graceful fallbacks when no image is
10
- * available.
12
+ * Default Cossistant theme colors for avatar fallbacks.
13
+ * These use the Tailwind classes defined in support.css.
11
14
  */
12
- function Avatar({ className, image, name }) {
13
- return /* @__PURE__ */ jsxs(Avatar$1, {
14
- className: cn("flex size-9 items-center justify-center overflow-clip rounded-full bg-co-background-200 dark:bg-co-background-500", className),
15
- children: [image && /* @__PURE__ */ jsx(AvatarImage, {
15
+ const DEFAULT_AVATAR_COLORS = [
16
+ "bg-co-pink",
17
+ "bg-co-blue",
18
+ "bg-co-yellow",
19
+ "bg-co-orange"
20
+ ];
21
+ /**
22
+ * Renders a squared avatar with graceful fallbacks using Facehash when no
23
+ * image is available. Features squircle corners when supported by the browser
24
+ * and a subtle ring border.
25
+ *
26
+ * For AI agents without an image, displays the Cossistant logo without
27
+ * a background.
28
+ */
29
+ function Avatar({ className, image, name, isAI = false, showBackground = true, colorClasses = DEFAULT_AVATAR_COLORS, lastSeenAt, indicatorSize = 6 }) {
30
+ const agentStatus = isAI ? "offline" : getAgentStatus(lastSeenAt);
31
+ if (isAI && !image) return /* @__PURE__ */ jsx("div", {
32
+ className: cn("flex items-center justify-center rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500", className),
33
+ children: /* @__PURE__ */ jsx(CossistantLogo, { className: "h-1/2 w-1/2" })
34
+ });
35
+ if (isAI && image) return /* @__PURE__ */ jsxs(Avatar$1, {
36
+ className: cn("flex size-9 items-center justify-center overflow-clip rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500", className),
37
+ children: [/* @__PURE__ */ jsx(AvatarImage, {
16
38
  alt: name,
17
39
  src: image
18
40
  }), /* @__PURE__ */ jsx(AvatarFallback, {
19
- className: "font-medium text-xs",
20
- name
41
+ className: "size-full",
42
+ children: /* @__PURE__ */ jsx(Facehash, {
43
+ className: "size-full",
44
+ colorClasses,
45
+ interactive: false,
46
+ name,
47
+ showInitial: false,
48
+ size: "100%"
49
+ })
50
+ })]
51
+ });
52
+ return /* @__PURE__ */ jsxs("div", {
53
+ className: cn("relative", className),
54
+ children: [/* @__PURE__ */ jsxs(Avatar$1, {
55
+ className: cn("flex size-full items-center justify-center overflow-clip rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500"),
56
+ children: [image && /* @__PURE__ */ jsx(AvatarImage, {
57
+ alt: name,
58
+ src: image
59
+ }), /* @__PURE__ */ jsx(AvatarFallback, {
60
+ className: "size-full",
61
+ children: /* @__PURE__ */ jsx(Facehash, {
62
+ className: "size-full",
63
+ colorClasses,
64
+ interactive: false,
65
+ name,
66
+ showInitial: false,
67
+ size: "100%"
68
+ })
69
+ })]
70
+ }), /* @__PURE__ */ jsx(OnlineIndicator, {
71
+ className: "-bottom-0.5 -right-0.5 z-10",
72
+ size: indicatorSize,
73
+ status: agentStatus
21
74
  })]
22
75
  });
23
76
  }
@@ -1 +1 @@
1
- {"version":3,"file":"avatar.js","names":["AvatarPrimitive"],"sources":["../../../src/support/components/avatar.tsx"],"sourcesContent":["import type { ReactElement } from \"react\";\n\nimport {\n\tAvatarFallback,\n\tAvatarImage,\n\tAvatar as AvatarPrimitive,\n} from \"../../primitives/avatar\";\nimport { cn } from \"../utils\";\n\ntype AvatarProps = {\n\tclassName?: string;\n\timage?: string | null;\n\tname: string;\n};\n\n/**\n * Renders a circular avatar with graceful fallbacks when no image is\n * available.\n */\nexport function Avatar({ className, image, name }: AvatarProps): ReactElement {\n\treturn (\n\t\t<AvatarPrimitive\n\t\t\tclassName={cn(\n\t\t\t\t\"flex size-9 items-center justify-center overflow-clip rounded-full bg-co-background-200 dark:bg-co-background-500\",\n\t\t\t\tclassName\n\t\t\t)}\n\t\t>\n\t\t\t{image && <AvatarImage alt={name} src={image} />}\n\t\t\t<AvatarFallback className=\"font-medium text-xs\" name={name} />\n\t\t</AvatarPrimitive>\n\t);\n}\n"],"mappings":";;;;;;;;;;;AAmBA,SAAgB,OAAO,EAAE,WAAW,OAAO,QAAmC;AAC7E,QACC,qBAACA;EACA,WAAW,GACV,qHACA,UACA;aAEA,SAAS,oBAAC;GAAY,KAAK;GAAM,KAAK;IAAS,EAChD,oBAAC;GAAe,WAAU;GAA4B;IAAQ;GAC7C"}
1
+ {"version":3,"file":"avatar.js","names":["AvatarPrimitive"],"sources":["../../../src/support/components/avatar.tsx"],"sourcesContent":["import { Facehash } from \"facehash\";\nimport type { ReactElement } from \"react\";\n\nimport {\n\tAvatarFallback,\n\tAvatarImage,\n\tAvatar as AvatarPrimitive,\n} from \"../../primitives/avatar\";\nimport { cn } from \"../utils\";\nimport { CossistantLogo } from \"./cossistant-branding\";\nimport { getAgentStatus, OnlineIndicator } from \"./online-indicator\";\n\n/**\n * Default Cossistant theme colors for avatar fallbacks.\n * These use the Tailwind classes defined in support.css.\n */\nconst DEFAULT_AVATAR_COLORS = [\n\t\"bg-co-pink\",\n\t\"bg-co-blue\",\n\t\"bg-co-yellow\",\n\t\"bg-co-orange\",\n];\n\ntype AvatarProps = {\n\tclassName?: string;\n\timage?: string | null;\n\tname: string;\n\t/** Whether this avatar is for an AI agent */\n\tisAI?: boolean;\n\t/** Whether to show the background circle (default: true) */\n\tshowBackground?: boolean;\n\t/**\n\t * Tailwind class array for Facehash background colors.\n\t * Defaults to Cossistant theme colors (pink, blue, yellow, orange).\n\t * @example [\"bg-pink-500\", \"bg-blue-500\", \"bg-green-500\"]\n\t */\n\tcolorClasses?: string[];\n\t/**\n\t * Last seen timestamp for the agent. When provided, shows a status indicator:\n\t * - Green (online): seen within last 15 minutes\n\t * - Orange (away): seen within last hour\n\t * Only shown for non-AI agents.\n\t */\n\tlastSeenAt?: string | null;\n\t/**\n\t * Size of the online indicator in pixels.\n\t * Defaults to 6px.\n\t */\n\tindicatorSize?: number;\n};\n\n/**\n * Renders a squared avatar with graceful fallbacks using Facehash when no\n * image is available. Features squircle corners when supported by the browser\n * and a subtle ring border.\n *\n * For AI agents without an image, displays the Cossistant logo without\n * a background.\n */\nexport function Avatar({\n\tclassName,\n\timage,\n\tname,\n\tisAI = false,\n\tshowBackground = true,\n\tcolorClasses = DEFAULT_AVATAR_COLORS,\n\tlastSeenAt,\n\tindicatorSize = 6,\n}: AvatarProps): ReactElement {\n\tconst agentStatus = isAI ? \"offline\" : getAgentStatus(lastSeenAt);\n\n\t// AI agent without image: show logo in avatar box (only in avatar-stack context)\n\t// or at full size when used standalone\n\tif (isAI && !image) {\n\t\treturn (\n\t\t\t<div\n\t\t\t\tclassName={cn(\n\t\t\t\t\t\"flex items-center justify-center rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500\",\n\t\t\t\t\tclassName\n\t\t\t\t)}\n\t\t\t>\n\t\t\t\t<CossistantLogo className=\"h-1/2 w-1/2\" />\n\t\t\t</div>\n\t\t);\n\t}\n\n\t// AI agent with image: show image in a square\n\tif (isAI && image) {\n\t\treturn (\n\t\t\t<AvatarPrimitive\n\t\t\t\tclassName={cn(\n\t\t\t\t\t\"flex size-9 items-center justify-center overflow-clip rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500\",\n\t\t\t\t\tclassName\n\t\t\t\t)}\n\t\t\t>\n\t\t\t\t<AvatarImage alt={name} src={image} />\n\t\t\t\t<AvatarFallback className=\"size-full\">\n\t\t\t\t\t<Facehash\n\t\t\t\t\t\tclassName=\"size-full\"\n\t\t\t\t\t\tcolorClasses={colorClasses}\n\t\t\t\t\t\tinteractive={false}\n\t\t\t\t\t\tname={name}\n\t\t\t\t\t\tshowInitial={false}\n\t\t\t\t\t\tsize=\"100%\"\n\t\t\t\t\t/>\n\t\t\t\t</AvatarFallback>\n\t\t\t</AvatarPrimitive>\n\t\t);\n\t}\n\n\treturn (\n\t\t<div className={cn(\"relative\", className)}>\n\t\t\t<AvatarPrimitive\n\t\t\t\tclassName={cn(\n\t\t\t\t\t\"flex size-full items-center justify-center overflow-clip rounded bg-co-background-200 ring-1 ring-co-border/30 dark:bg-co-background-500\"\n\t\t\t\t)}\n\t\t\t>\n\t\t\t\t{image && <AvatarImage alt={name} src={image} />}\n\t\t\t\t<AvatarFallback className=\"size-full\">\n\t\t\t\t\t<Facehash\n\t\t\t\t\t\tclassName=\"size-full\"\n\t\t\t\t\t\tcolorClasses={colorClasses}\n\t\t\t\t\t\tinteractive={false}\n\t\t\t\t\t\tname={name}\n\t\t\t\t\t\tshowInitial={false}\n\t\t\t\t\t\tsize=\"100%\"\n\t\t\t\t\t/>\n\t\t\t\t</AvatarFallback>\n\t\t\t</AvatarPrimitive>\n\t\t\t<OnlineIndicator\n\t\t\t\tclassName=\"-bottom-0.5 -right-0.5 z-10\"\n\t\t\t\tsize={indicatorSize}\n\t\t\t\tstatus={agentStatus}\n\t\t\t/>\n\t\t</div>\n\t);\n}\n"],"mappings":";;;;;;;;;;;;;;AAgBA,MAAM,wBAAwB;CAC7B;CACA;CACA;CACA;CACA;;;;;;;;;AAsCD,SAAgB,OAAO,EACtB,WACA,OACA,MACA,OAAO,OACP,iBAAiB,MACjB,eAAe,uBACf,YACA,gBAAgB,KACa;CAC7B,MAAM,cAAc,OAAO,YAAY,eAAe,WAAW;AAIjE,KAAI,QAAQ,CAAC,MACZ,QACC,oBAAC;EACA,WAAW,GACV,oHACA,UACA;YAED,oBAAC,kBAAe,WAAU,gBAAgB;GACrC;AAKR,KAAI,QAAQ,MACX,QACC,qBAACA;EACA,WAAW,GACV,yIACA,UACA;aAED,oBAAC;GAAY,KAAK;GAAM,KAAK;IAAS,EACtC,oBAAC;GAAe,WAAU;aACzB,oBAAC;IACA,WAAU;IACI;IACd,aAAa;IACP;IACN,aAAa;IACb,MAAK;KACJ;IACc;GACA;AAIpB,QACC,qBAAC;EAAI,WAAW,GAAG,YAAY,UAAU;aACxC,qBAACA;GACA,WAAW,GACV,2IACA;cAEA,SAAS,oBAAC;IAAY,KAAK;IAAM,KAAK;KAAS,EAChD,oBAAC;IAAe,WAAU;cACzB,oBAAC;KACA,WAAU;KACI;KACd,aAAa;KACP;KACN,aAAa;KACb,MAAK;MACJ;KACc;IACA,EAClB,oBAAC;GACA,WAAU;GACV,MAAM;GACN,QAAQ;IACP;GACG"}
@@ -4,10 +4,12 @@ import * as class_variance_authority_dist_types0 from "class-variance-authority/
4
4
 
5
5
  //#region src/support/components/button.d.ts
6
6
  declare const coButtonVariants: (props?: ({
7
- variant?: "tab" | "default" | "secondary" | "ghost" | "outline" | "tab-selected" | null | undefined;
7
+ variant?: "default" | "tab" | "secondary" | "ghost" | "outline" | "tab-selected" | null | undefined;
8
8
  size?: "default" | "large" | "icon" | null | undefined;
9
9
  } & class_variance_authority_dist_types0.ClassProp) | undefined) => string;
10
- type CossistantButtonProps = React$1.ComponentProps<"button"> & VariantProps<typeof coButtonVariants>;
10
+ type CossistantButtonProps = React$1.ComponentProps<"button"> & {
11
+ asChild?: boolean;
12
+ } & VariantProps<typeof coButtonVariants>;
11
13
  /**
12
14
  * Styled button primitive that forwards variant and size props to the shared
13
15
  * design tokens.
@@ -1 +1 @@
1
- {"version":3,"file":"button.d.ts","names":[],"sources":["../../../src/support/components/button.tsx"],"sourcesContent":[],"mappings":";;;;;cAKa,wBA4BZ;;;AA5BD,CAAA,GA4BC,oCAAA,CAAA,SAAA,CAAA,GAAA,SAAA,EAAA,GAAA,MAAA;AAEW,KAAA,qBAAA,GAAwB,OAAA,CAAM,cAAT,CAAA,QAAA,CAAA,GAChC,YADgC,CAAA,OACZ,gBADY,CAAA;;;;;AAOjB,iBAAA,QAAA,CAAQ;EAAA,SAAA;EAAA,OAAA;EAAA,IAAA;EAAA,GAAA;AAAA,CAAA,EAKrB,qBALqB,CAAA,EAKG,OAAA,CAAM,YALT"}
1
+ {"version":3,"file":"button.d.ts","names":[],"sources":["../../../src/support/components/button.tsx"],"sourcesContent":[],"mappings":";;;;;cAKa,wBA4BZ;;;AA5BD,CAAA,GA4BC,oCAAA,CAAA,SAAA,CAAA,GAAA,SAAA,EAAA,GAAA,MAAA;AAEW,KAAA,qBAAA,GAAwB,OAAA,CAAM,cAAT,CAAA,QAAA,CAAA,GAAA;EAAG,OAAM,CAAA,EAAA,OAAA;CAElB,GAApB,YAAoB,CAAA,OAAA,gBAAA,CAAA;;;AAMxB;;AAEC,iBAFe,QAAA,CAEf;EAAA,SAAA;EAAA,OAAA;EAAA,IAAA;EAAA,GAAA;AAAA,CAAA,EAGE,qBAHF,CAAA,EAG0B,OAAA,CAAM,YAHhC"}
@@ -4,11 +4,11 @@ import { jsx } from "react/jsx-runtime";
4
4
  import { cva } from "class-variance-authority";
5
5
 
6
6
  //#region src/support/components/button.tsx
7
- const coButtonVariants = cva("group/btn inline-flex shrink-0 items-center justify-center gap-2 whitespace-nowrap rounded-md border font-medium text-sm outline-none transition-all hover:cursor-pointer focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 [&_svg:not([class*='size-'])]:size-4 [&_svg]:pointer-events-none [&_svg]:shrink-0", {
7
+ const coButtonVariants = cva("group/btn inline-flex shrink-0 items-center justify-center gap-2 whitespace-nowrap rounded border font-medium text-sm outline-none transition-all hover:cursor-pointer focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 [&_svg:not([class*='size-'])]:size-4 [&_svg]:pointer-events-none [&_svg]:shrink-0", {
8
8
  variants: {
9
9
  variant: {
10
10
  default: "bg-co-primary text-co-primary-foreground hover:bg-co-primary/90",
11
- secondary: "border-co-border bg-co-background-50 text-co-primary hover:bg-co-background-100 hover:text-co-foreground dark:bg-co-background-300 dark:hover:bg-co-background-400",
11
+ secondary: "border-co-border bg-co-background-50/50 text-co-primary hover:bg-co-background-100 hover:text-co-foreground dark:bg-co-background-300 dark:hover:bg-co-background-400",
12
12
  ghost: "border-transparent text-co-primary hover:bg-co-background-200 hover:text-co-foreground dark:hover:bg-co-background-300",
13
13
  outline: "border border-co-border bg-co-background text-co-primary hover:bg-co-background-100 dark:bg-co-background-200 dark:hover:bg-co-background-300",
14
14
  tab: "opacity-40 hover:bg-co-background-100 hover:text-co-foreground hover:opacity-90 dark:hover:bg-co-background-200",
@@ -29,7 +29,7 @@ const coButtonVariants = cva("group/btn inline-flex shrink-0 items-center justif
29
29
  * Styled button primitive that forwards variant and size props to the shared
30
30
  * design tokens.
31
31
  */
32
- function CoButton({ className, variant, size,...props }) {
32
+ function CoButton({ className, variant, size, ...props }) {
33
33
  return /* @__PURE__ */ jsx(Button, {
34
34
  className: cn(coButtonVariants({
35
35
  variant,
@@ -1 +1 @@
1
- {"version":3,"file":"button.js","names":["ButtonPrimitive"],"sources":["../../../src/support/components/button.tsx"],"sourcesContent":["import { cva, type VariantProps } from \"class-variance-authority\";\nimport type * as React from \"react\";\nimport { Button as ButtonPrimitive } from \"../../primitives/button\";\nimport { cn } from \"../utils\";\n\nexport const coButtonVariants = cva(\n\t\"group/btn inline-flex shrink-0 items-center justify-center gap-2 whitespace-nowrap rounded-md border font-medium text-sm outline-none transition-all hover:cursor-pointer focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 [&_svg:not([class*='size-'])]:size-4 [&_svg]:pointer-events-none [&_svg]:shrink-0\",\n\t{\n\t\tvariants: {\n\t\t\tvariant: {\n\t\t\t\tdefault:\n\t\t\t\t\t\"bg-co-primary text-co-primary-foreground hover:bg-co-primary/90\",\n\t\t\t\tsecondary:\n\t\t\t\t\t\"border-co-border bg-co-background-50 text-co-primary hover:bg-co-background-100 hover:text-co-foreground dark:bg-co-background-300 dark:hover:bg-co-background-400\",\n\t\t\t\tghost:\n\t\t\t\t\t\"border-transparent text-co-primary hover:bg-co-background-200 hover:text-co-foreground dark:hover:bg-co-background-300\",\n\t\t\t\toutline:\n\t\t\t\t\t\"border border-co-border bg-co-background text-co-primary hover:bg-co-background-100 dark:bg-co-background-200 dark:hover:bg-co-background-300\",\n\t\t\t\ttab: \"opacity-40 hover:bg-co-background-100 hover:text-co-foreground hover:opacity-90 dark:hover:bg-co-background-200\",\n\t\t\t\t\"tab-selected\":\n\t\t\t\t\t\"hover:bg-co-background-100 hover:text-co-foreground dark:hover:bg-co-background-200\",\n\t\t\t},\n\t\t\tsize: {\n\t\t\t\tdefault: \"h-8 px-4 py-2 has-[>svg]:px-3\",\n\t\t\t\tlarge: \"h-14 px-6 has-[>svg]:px-4\",\n\t\t\t\ticon: \"size-6\",\n\t\t\t},\n\t\t},\n\t\tdefaultVariants: {\n\t\t\tvariant: \"default\",\n\t\t\tsize: \"default\",\n\t\t},\n\t}\n);\n\nexport type CossistantButtonProps = React.ComponentProps<\"button\"> &\n\tVariantProps<typeof coButtonVariants>;\n\n/**\n * Styled button primitive that forwards variant and size props to the shared\n * design tokens.\n */\nexport function CoButton({\n\tclassName,\n\tvariant,\n\tsize,\n\t...props\n}: CossistantButtonProps): React.ReactElement {\n\treturn (\n\t\t<ButtonPrimitive\n\t\t\tclassName={cn(coButtonVariants({ variant, size, className }))}\n\t\t\t{...props}\n\t\t/>\n\t);\n}\n"],"mappings":";;;;;;AAKA,MAAa,mBAAmB,IAC/B,qeACA;CACC,UAAU;EACT,SAAS;GACR,SACC;GACD,WACC;GACD,OACC;GACD,SACC;GACD,KAAK;GACL,gBACC;GACD;EACD,MAAM;GACL,SAAS;GACT,OAAO;GACP,MAAM;GACN;EACD;CACD,iBAAiB;EAChB,SAAS;EACT,MAAM;EACN;CACD,CACD;;;;;AASD,SAAgB,SAAS,EACxB,WACA,SACA,KACA,GAAG,SAC0C;AAC7C,QACC,oBAACA;EACA,WAAW,GAAG,iBAAiB;GAAE;GAAS;GAAM;GAAW,CAAC,CAAC;EAC7D,GAAI;GACH"}
1
+ {"version":3,"file":"button.js","names":["ButtonPrimitive"],"sources":["../../../src/support/components/button.tsx"],"sourcesContent":["import { cva, type VariantProps } from \"class-variance-authority\";\nimport type * as React from \"react\";\nimport { Button as ButtonPrimitive } from \"../../primitives/button\";\nimport { cn } from \"../utils\";\n\nexport const coButtonVariants = cva(\n\t\"group/btn inline-flex shrink-0 items-center justify-center gap-2 whitespace-nowrap rounded border font-medium text-sm outline-none transition-all hover:cursor-pointer focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 [&_svg:not([class*='size-'])]:size-4 [&_svg]:pointer-events-none [&_svg]:shrink-0\",\n\t{\n\t\tvariants: {\n\t\t\tvariant: {\n\t\t\t\tdefault:\n\t\t\t\t\t\"bg-co-primary text-co-primary-foreground hover:bg-co-primary/90\",\n\t\t\t\tsecondary:\n\t\t\t\t\t\"border-co-border bg-co-background-50/50 text-co-primary hover:bg-co-background-100 hover:text-co-foreground dark:bg-co-background-300 dark:hover:bg-co-background-400\",\n\t\t\t\tghost:\n\t\t\t\t\t\"border-transparent text-co-primary hover:bg-co-background-200 hover:text-co-foreground dark:hover:bg-co-background-300\",\n\t\t\t\toutline:\n\t\t\t\t\t\"border border-co-border bg-co-background text-co-primary hover:bg-co-background-100 dark:bg-co-background-200 dark:hover:bg-co-background-300\",\n\t\t\t\ttab: \"opacity-40 hover:bg-co-background-100 hover:text-co-foreground hover:opacity-90 dark:hover:bg-co-background-200\",\n\t\t\t\t\"tab-selected\":\n\t\t\t\t\t\"hover:bg-co-background-100 hover:text-co-foreground dark:hover:bg-co-background-200\",\n\t\t\t},\n\t\t\tsize: {\n\t\t\t\tdefault: \"h-8 px-4 py-2 has-[>svg]:px-3\",\n\t\t\t\tlarge: \"h-14 px-6 has-[>svg]:px-4\",\n\t\t\t\ticon: \"size-6\",\n\t\t\t},\n\t\t},\n\t\tdefaultVariants: {\n\t\t\tvariant: \"default\",\n\t\t\tsize: \"default\",\n\t\t},\n\t}\n);\n\nexport type CossistantButtonProps = React.ComponentProps<\"button\"> & {\n\tasChild?: boolean;\n} & VariantProps<typeof coButtonVariants>;\n\n/**\n * Styled button primitive that forwards variant and size props to the shared\n * design tokens.\n */\nexport function CoButton({\n\tclassName,\n\tvariant,\n\tsize,\n\t...props\n}: CossistantButtonProps): React.ReactElement {\n\treturn (\n\t\t<ButtonPrimitive\n\t\t\tclassName={cn(coButtonVariants({ variant, size, className }))}\n\t\t\t{...props}\n\t\t/>\n\t);\n}\n"],"mappings":";;;;;;AAKA,MAAa,mBAAmB,IAC/B,keACA;CACC,UAAU;EACT,SAAS;GACR,SACC;GACD,WACC;GACD,OACC;GACD,SACC;GACD,KAAK;GACL,gBACC;GACD;EACD,MAAM;GACL,SAAS;GACT,OAAO;GACP,MAAM;GACN;EACD;CACD,iBAAiB;EAChB,SAAS;EACT,MAAM;EACN;CACD,CACD;;;;;AAUD,SAAgB,SAAS,EACxB,WACA,SACA,MACA,GAAG,SAC0C;AAC7C,QACC,oBAACA;EACA,WAAW,GAAG,iBAAiB;GAAE;GAAS;GAAM;GAAW,CAAC,CAAC;EAC7D,GAAI;GACH"}
@@ -0,0 +1,16 @@
1
+ import { ConfigurationError } from "../../hooks/private/use-rest-client.js";
2
+ import React from "react";
3
+
4
+ //#region src/support/components/configuration-error.d.ts
5
+ type ConfigurationErrorDisplayProps = {
6
+ error: ConfigurationError;
7
+ className?: string;
8
+ };
9
+ /**
10
+ * Full-page fallback component displayed inside the widget when misconfigured.
11
+ * Shows a helpful message with instructions on how to configure the API key.
12
+ */
13
+ declare const ConfigurationErrorDisplay: React.FC<ConfigurationErrorDisplayProps>;
14
+ //#endregion
15
+ export { ConfigurationErrorDisplay };
16
+ //# sourceMappingURL=configuration-error.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"configuration-error.d.ts","names":[],"sources":["../../../src/support/components/configuration-error.tsx"],"sourcesContent":[],"mappings":";;;;KAUK,8BAAA;SACG;EADH,SAAA,CAAA,EAAA,MAAA;AASL,CAAA;;;;;cAAa,2BAA2B,KAAA,CAAM,GAC7C"}
@@ -0,0 +1,162 @@
1
+ "use client";
2
+
3
+ import { cn } from "../utils/index.js";
4
+ import { CossistantLogo } from "./cossistant-branding.js";
5
+ import { CoButton } from "./button.js";
6
+ import { Icon } from "./icons.js";
7
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
8
+
9
+ //#region src/support/components/configuration-error.tsx
10
+ /**
11
+ * Full-page fallback component displayed inside the widget when misconfigured.
12
+ * Shows a helpful message with instructions on how to configure the API key.
13
+ */
14
+ const ConfigurationErrorDisplay = ({ error, className }) => {
15
+ const docsUrl = "https://cossistant.com/docs/quickstart/api-keys";
16
+ const isInvalidKey = error.type === "invalid_api_key";
17
+ return /* @__PURE__ */ jsxs("div", {
18
+ className: cn("flex h-full flex-col bg-co-background text-co-foreground", className),
19
+ children: [
20
+ /* @__PURE__ */ jsxs("div", {
21
+ className: cn("flex flex-col items-center justify-center px-6 pb-10"),
22
+ children: [
23
+ /* @__PURE__ */ jsx("div", {
24
+ className: cn("mb-4 flex h-20 w-20 items-center justify-center rounded-2xl", isInvalidKey ? "bg-co-orange/10 text-co-orange" : "bg-co-blue/10 text-co-blue"),
25
+ children: /* @__PURE__ */ jsx(CossistantLogo, { className: "h-10 w-10" })
26
+ }),
27
+ /* @__PURE__ */ jsx("h2", {
28
+ className: "font-semibold text-lg",
29
+ children: isInvalidKey ? "Invalid API Key" : "Setup Required"
30
+ }),
31
+ /* @__PURE__ */ jsx("p", {
32
+ className: "mt-1 text-center text-co-muted-foreground text-sm",
33
+ children: isInvalidKey ? "Your API key couldn't be verified" : "Almost there! Just add your API key"
34
+ })
35
+ ]
36
+ }),
37
+ /* @__PURE__ */ jsx("div", {
38
+ className: "flex flex-1 flex-col gap-8 overflow-y-auto px-5 pb-4",
39
+ children: isInvalidKey ? /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsxs("div", {
40
+ className: "rounded-lg border border-co-orange/20 bg-co-orange/5 p-4",
41
+ children: [/* @__PURE__ */ jsx("h4", {
42
+ className: "mb-2 font-medium text-co-foreground text-sm",
43
+ children: "Common causes:"
44
+ }), /* @__PURE__ */ jsxs("ul", {
45
+ className: "space-y-1.5 text-co-muted-foreground text-sm",
46
+ children: [
47
+ /* @__PURE__ */ jsxs("li", {
48
+ className: "flex items-start gap-2",
49
+ children: [/* @__PURE__ */ jsx("span", { className: "mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60" }), "API key has been revoked or deleted"]
50
+ }),
51
+ /* @__PURE__ */ jsxs("li", {
52
+ className: "flex items-start gap-2",
53
+ children: [/* @__PURE__ */ jsx("span", { className: "mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60" }), "Key has expired"]
54
+ }),
55
+ /* @__PURE__ */ jsxs("li", {
56
+ className: "flex items-start gap-2",
57
+ children: [/* @__PURE__ */ jsx("span", { className: "mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60" }), "Domain not in the allowed list"]
58
+ }),
59
+ /* @__PURE__ */ jsxs("li", {
60
+ className: "flex items-start gap-2",
61
+ children: [/* @__PURE__ */ jsx("span", { className: "mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60" }), "Using a test key on production"]
62
+ })
63
+ ]
64
+ })]
65
+ }) }) : /* @__PURE__ */ jsxs(Fragment, { children: [
66
+ /* @__PURE__ */ jsxs("div", {
67
+ className: "flex gap-3",
68
+ children: [/* @__PURE__ */ jsx("div", {
69
+ className: "flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-yellow/10 font-semibold text-co-yellow text-xs",
70
+ children: "1"
71
+ }), /* @__PURE__ */ jsxs("div", {
72
+ className: "flex flex-1 flex-col gap-3",
73
+ children: [/* @__PURE__ */ jsx("h4", {
74
+ className: "mt-1 font-medium text-sm",
75
+ children: "Create an account"
76
+ }), /* @__PURE__ */ jsx(CoButton, {
77
+ asChild: true,
78
+ variant: "secondary",
79
+ children: /* @__PURE__ */ jsx("a", {
80
+ href: "https://cossistant.com/sign-up",
81
+ rel: "noopener noreferrer",
82
+ target: "_blank",
83
+ children: "Create an account"
84
+ })
85
+ })]
86
+ })]
87
+ }),
88
+ /* @__PURE__ */ jsxs("div", {
89
+ className: "flex gap-3",
90
+ children: [/* @__PURE__ */ jsx("div", {
91
+ className: "flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-blue/10 font-semibold text-co-blue text-xs",
92
+ children: "2"
93
+ }), /* @__PURE__ */ jsxs("div", {
94
+ className: "mt-1 flex flex-1 flex-col gap-2",
95
+ children: [/* @__PURE__ */ jsx("h4", {
96
+ className: "font-medium text-sm",
97
+ children: "Get your public API key"
98
+ }), /* @__PURE__ */ jsxs("p", {
99
+ className: "mt-0.5 text-co-primary/60 text-xs",
100
+ children: [
101
+ "(Go to",
102
+ " ",
103
+ /* @__PURE__ */ jsx("span", {
104
+ className: "font-medium text-co-primary/60",
105
+ children: "Settings / Developers"
106
+ }),
107
+ " ",
108
+ "in your dashboard)"
109
+ ]
110
+ })]
111
+ })]
112
+ }),
113
+ /* @__PURE__ */ jsxs("div", {
114
+ className: "flex gap-3",
115
+ children: [/* @__PURE__ */ jsx("div", {
116
+ className: "flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-pink/10 font-semibold text-co-pink text-xs",
117
+ children: "3"
118
+ }), /* @__PURE__ */ jsxs("div", {
119
+ className: "flex flex-1 flex-col gap-3",
120
+ children: [/* @__PURE__ */ jsx("h4", {
121
+ className: "mt-1 font-medium text-sm",
122
+ children: "Add to your environment"
123
+ }), /* @__PURE__ */ jsxs("div", {
124
+ className: "mt-2 overflow-hidden rounded-lg border border-co-border bg-co-background-100",
125
+ children: [/* @__PURE__ */ jsx("div", {
126
+ className: "border-co-border border-b bg-co-background-50 px-3 py-1",
127
+ children: /* @__PURE__ */ jsx("span", {
128
+ className: "font-mono text-co-muted-foreground text-xs",
129
+ children: ".env"
130
+ })
131
+ }), /* @__PURE__ */ jsxs("div", {
132
+ className: "p-3 font-mono text-xs",
133
+ children: [/* @__PURE__ */ jsx("span", {
134
+ className: "text-co-foreground",
135
+ children: error.envVarName
136
+ }), /* @__PURE__ */ jsx("span", {
137
+ className: "text-co-muted-foreground",
138
+ children: "=pk_live_..."
139
+ })]
140
+ })]
141
+ })]
142
+ })]
143
+ })
144
+ ] })
145
+ }),
146
+ /* @__PURE__ */ jsx("div", {
147
+ className: "border-co-border border-t p-4",
148
+ children: /* @__PURE__ */ jsxs("a", {
149
+ className: cn("flex w-full items-center justify-center gap-2 rounded-lg px-4 py-2.5", "bg-co-primary text-co-primary-foreground", "font-medium text-sm", "transition-all hover:opacity-90 active:scale-[0.98]"),
150
+ href: docsUrl,
151
+ rel: "noopener noreferrer",
152
+ target: "_blank",
153
+ children: ["View our docs", /* @__PURE__ */ jsx(Icon, { name: "arrow-right" })]
154
+ })
155
+ })
156
+ ]
157
+ });
158
+ };
159
+
160
+ //#endregion
161
+ export { ConfigurationErrorDisplay };
162
+ //# sourceMappingURL=configuration-error.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"configuration-error.js","names":["ConfigurationErrorDisplay: React.FC<\n\tConfigurationErrorDisplayProps\n>"],"sources":["../../../src/support/components/configuration-error.tsx"],"sourcesContent":["\"use client\";\n\nimport { Button } from \"@cossistant/react\";\nimport type React from \"react\";\nimport type { ConfigurationError } from \"../../hooks/private/use-rest-client\";\nimport { cn } from \"../utils\";\nimport { CoButton } from \"./button\";\nimport { CossistantLogo } from \"./cossistant-branding\";\nimport { Icon } from \"./icons\";\n\ntype ConfigurationErrorDisplayProps = {\n\terror: ConfigurationError;\n\tclassName?: string;\n};\n\n/**\n * Full-page fallback component displayed inside the widget when misconfigured.\n * Shows a helpful message with instructions on how to configure the API key.\n */\nexport const ConfigurationErrorDisplay: React.FC<\n\tConfigurationErrorDisplayProps\n> = ({ error, className }) => {\n\tconst docsUrl = \"https://cossistant.com/docs/quickstart/api-keys\";\n\tconst isInvalidKey = error.type === \"invalid_api_key\";\n\n\treturn (\n\t\t<div\n\t\t\tclassName={cn(\n\t\t\t\t\"flex h-full flex-col bg-co-background text-co-foreground\",\n\t\t\t\tclassName\n\t\t\t)}\n\t\t>\n\t\t\t{/* Hero section with logo */}\n\t\t\t<div\n\t\t\t\tclassName={cn(\"flex flex-col items-center justify-center px-6 pb-10\")}\n\t\t\t>\n\t\t\t\t<div\n\t\t\t\t\tclassName={cn(\n\t\t\t\t\t\t\"mb-4 flex h-20 w-20 items-center justify-center rounded-2xl\",\n\t\t\t\t\t\tisInvalidKey\n\t\t\t\t\t\t\t? \"bg-co-orange/10 text-co-orange\"\n\t\t\t\t\t\t\t: \"bg-co-blue/10 text-co-blue\"\n\t\t\t\t\t)}\n\t\t\t\t>\n\t\t\t\t\t<CossistantLogo className=\"h-10 w-10\" />\n\t\t\t\t</div>\n\t\t\t\t<h2 className=\"font-semibold text-lg\">\n\t\t\t\t\t{isInvalidKey ? \"Invalid API Key\" : \"Setup Required\"}\n\t\t\t\t</h2>\n\t\t\t\t<p className=\"mt-1 text-center text-co-muted-foreground text-sm\">\n\t\t\t\t\t{isInvalidKey\n\t\t\t\t\t\t? \"Your API key couldn't be verified\"\n\t\t\t\t\t\t: \"Almost there! Just add your API key\"}\n\t\t\t\t</p>\n\t\t\t</div>\n\n\t\t\t{/* Content */}\n\t\t\t<div className=\"flex flex-1 flex-col gap-8 overflow-y-auto px-5 pb-4\">\n\t\t\t\t{isInvalidKey ? (\n\t\t\t\t\t<>\n\t\t\t\t\t\t{/* Error details card */}\n\t\t\t\t\t\t<div className=\"rounded-lg border border-co-orange/20 bg-co-orange/5 p-4\">\n\t\t\t\t\t\t\t<h4 className=\"mb-2 font-medium text-co-foreground text-sm\">\n\t\t\t\t\t\t\t\tCommon causes:\n\t\t\t\t\t\t\t</h4>\n\t\t\t\t\t\t\t<ul className=\"space-y-1.5 text-co-muted-foreground text-sm\">\n\t\t\t\t\t\t\t\t<li className=\"flex items-start gap-2\">\n\t\t\t\t\t\t\t\t\t<span className=\"mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60\" />\n\t\t\t\t\t\t\t\t\tAPI key has been revoked or deleted\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t\t<li className=\"flex items-start gap-2\">\n\t\t\t\t\t\t\t\t\t<span className=\"mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60\" />\n\t\t\t\t\t\t\t\t\tKey has expired\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t\t<li className=\"flex items-start gap-2\">\n\t\t\t\t\t\t\t\t\t<span className=\"mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60\" />\n\t\t\t\t\t\t\t\t\tDomain not in the allowed list\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t\t<li className=\"flex items-start gap-2\">\n\t\t\t\t\t\t\t\t\t<span className=\"mt-1.5 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-co-orange/60\" />\n\t\t\t\t\t\t\t\t\tUsing a test key on production\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t</ul>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</>\n\t\t\t\t) : (\n\t\t\t\t\t<>\n\t\t\t\t\t\t<div className=\"flex gap-3\">\n\t\t\t\t\t\t\t<div className=\"flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-yellow/10 font-semibold text-co-yellow text-xs\">\n\t\t\t\t\t\t\t\t1\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t<div className=\"flex flex-1 flex-col gap-3\">\n\t\t\t\t\t\t\t\t<h4 className=\"mt-1 font-medium text-sm\">Create an account</h4>\n\t\t\t\t\t\t\t\t<CoButton asChild variant=\"secondary\">\n\t\t\t\t\t\t\t\t\t<a\n\t\t\t\t\t\t\t\t\t\thref=\"https://cossistant.com/sign-up\"\n\t\t\t\t\t\t\t\t\t\trel=\"noopener noreferrer\"\n\t\t\t\t\t\t\t\t\t\ttarget=\"_blank\"\n\t\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t\tCreate an account\n\t\t\t\t\t\t\t\t\t</a>\n\t\t\t\t\t\t\t\t</CoButton>\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<div className=\"flex gap-3\">\n\t\t\t\t\t\t\t<div className=\"flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-blue/10 font-semibold text-co-blue text-xs\">\n\t\t\t\t\t\t\t\t2\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t<div className=\"mt-1 flex flex-1 flex-col gap-2\">\n\t\t\t\t\t\t\t\t<h4 className=\"font-medium text-sm\">Get your public API key</h4>\n\t\t\t\t\t\t\t\t<p className=\"mt-0.5 text-co-primary/60 text-xs\">\n\t\t\t\t\t\t\t\t\t(Go to{\" \"}\n\t\t\t\t\t\t\t\t\t<span className=\"font-medium text-co-primary/60\">\n\t\t\t\t\t\t\t\t\t\tSettings / Developers\n\t\t\t\t\t\t\t\t\t</span>{\" \"}\n\t\t\t\t\t\t\t\t\tin your dashboard)\n\t\t\t\t\t\t\t\t</p>\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t</div>\n\n\t\t\t\t\t\t<div className=\"flex gap-3\">\n\t\t\t\t\t\t\t<div className=\"flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full bg-co-pink/10 font-semibold text-co-pink text-xs\">\n\t\t\t\t\t\t\t\t3\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t<div className=\"flex flex-1 flex-col gap-3\">\n\t\t\t\t\t\t\t\t<h4 className=\"mt-1 font-medium text-sm\">\n\t\t\t\t\t\t\t\t\tAdd to your environment\n\t\t\t\t\t\t\t\t</h4>\n\t\t\t\t\t\t\t\t<div className=\"mt-2 overflow-hidden rounded-lg border border-co-border bg-co-background-100\">\n\t\t\t\t\t\t\t\t\t<div className=\"border-co-border border-b bg-co-background-50 px-3 py-1\">\n\t\t\t\t\t\t\t\t\t\t<span className=\"font-mono text-co-muted-foreground text-xs\">\n\t\t\t\t\t\t\t\t\t\t\t.env\n\t\t\t\t\t\t\t\t\t\t</span>\n\t\t\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t\t\t<div className=\"p-3 font-mono text-xs\">\n\t\t\t\t\t\t\t\t\t\t<span className=\"text-co-foreground\">\n\t\t\t\t\t\t\t\t\t\t\t{error.envVarName}\n\t\t\t\t\t\t\t\t\t\t</span>\n\t\t\t\t\t\t\t\t\t\t<span className=\"text-co-muted-foreground\">\n\t\t\t\t\t\t\t\t\t\t\t=pk_live_...\n\t\t\t\t\t\t\t\t\t\t</span>\n\t\t\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t</>\n\t\t\t\t)}\n\t\t\t</div>\n\n\t\t\t{/* Footer with CTA */}\n\t\t\t<div className=\"border-co-border border-t p-4\">\n\t\t\t\t<a\n\t\t\t\t\tclassName={cn(\n\t\t\t\t\t\t\"flex w-full items-center justify-center gap-2 rounded-lg px-4 py-2.5\",\n\t\t\t\t\t\t\"bg-co-primary text-co-primary-foreground\",\n\t\t\t\t\t\t\"font-medium text-sm\",\n\t\t\t\t\t\t\"transition-all hover:opacity-90 active:scale-[0.98]\"\n\t\t\t\t\t)}\n\t\t\t\t\thref={docsUrl}\n\t\t\t\t\trel=\"noopener noreferrer\"\n\t\t\t\t\ttarget=\"_blank\"\n\t\t\t\t>\n\t\t\t\t\tView our docs\n\t\t\t\t\t<Icon name=\"arrow-right\" />\n\t\t\t\t</a>\n\t\t\t</div>\n\t\t</div>\n\t);\n};\n"],"mappings":";;;;;;;;;;;;;AAmBA,MAAaA,6BAER,EAAE,OAAO,gBAAgB;CAC7B,MAAM,UAAU;CAChB,MAAM,eAAe,MAAM,SAAS;AAEpC,QACC,qBAAC;EACA,WAAW,GACV,4DACA,UACA;;GAGD,qBAAC;IACA,WAAW,GAAG,uDAAuD;;KAErE,oBAAC;MACA,WAAW,GACV,+DACA,eACG,mCACA,6BACH;gBAED,oBAAC,kBAAe,WAAU,cAAc;OACnC;KACN,oBAAC;MAAG,WAAU;gBACZ,eAAe,oBAAoB;OAChC;KACL,oBAAC;MAAE,WAAU;gBACX,eACE,sCACA;OACA;;KACC;GAGN,oBAAC;IAAI,WAAU;cACb,eACA,0CAEC,qBAAC;KAAI,WAAU;gBACd,oBAAC;MAAG,WAAU;gBAA8C;OAEvD,EACL,qBAAC;MAAG,WAAU;;OACb,qBAAC;QAAG,WAAU;mBACb,oBAAC,UAAK,WAAU,kEAAkE;SAE9E;OACL,qBAAC;QAAG,WAAU;mBACb,oBAAC,UAAK,WAAU,kEAAkE;SAE9E;OACL,qBAAC;QAAG,WAAU;mBACb,oBAAC,UAAK,WAAU,kEAAkE;SAE9E;OACL,qBAAC;QAAG,WAAU;mBACb,oBAAC,UAAK,WAAU,kEAAkE;SAE9E;;OACD;MACA,GACJ,GAEH;KACC,qBAAC;MAAI,WAAU;iBACd,oBAAC;OAAI,WAAU;iBAA2H;QAEpI,EACN,qBAAC;OAAI,WAAU;kBACd,oBAAC;QAAG,WAAU;kBAA2B;SAAsB,EAC/D,oBAAC;QAAS;QAAQ,SAAQ;kBACzB,oBAAC;SACA,MAAK;SACL,KAAI;SACJ,QAAO;mBACP;UAEG;SACM;QACN;OACD;KACN,qBAAC;MAAI,WAAU;iBACd,oBAAC;OAAI,WAAU;iBAAuH;QAEhI,EACN,qBAAC;OAAI,WAAU;kBACd,oBAAC;QAAG,WAAU;kBAAsB;SAA4B,EAChE,qBAAC;QAAE,WAAU;;SAAoC;SACzC;SACP,oBAAC;UAAK,WAAU;oBAAiC;WAE1C;SAAC;SAAI;;SAET;QACC;OACD;KAEN,qBAAC;MAAI,WAAU;iBACd,oBAAC;OAAI,WAAU;iBAAuH;QAEhI,EACN,qBAAC;OAAI,WAAU;kBACd,oBAAC;QAAG,WAAU;kBAA2B;SAEpC,EACL,qBAAC;QAAI,WAAU;mBACd,oBAAC;SAAI,WAAU;mBACd,oBAAC;UAAK,WAAU;oBAA6C;WAEtD;UACF,EACN,qBAAC;SAAI,WAAU;oBACd,oBAAC;UAAK,WAAU;oBACd,MAAM;WACD,EACP,oBAAC;UAAK,WAAU;oBAA2B;WAEpC;UACF;SACD;QACD;OACD;QACJ;KAEC;GAGN,oBAAC;IAAI,WAAU;cACd,qBAAC;KACA,WAAW,GACV,wEACA,4CACA,uBACA,sDACA;KACD,MAAM;KACN,KAAI;KACJ,QAAO;gBACP,iBAEA,oBAAC,QAAK,MAAK,gBAAgB;MACxB;KACC;;GACD"}
@@ -1,6 +1,5 @@
1
1
  "use client";
2
2
 
3
-
4
3
  import { cn } from "../utils/index.js";
5
4
  import { useTriggerRef } from "../context/positioning.js";
6
5
  import { useSupportConfig } from "../store/support-store.js";
@@ -245,7 +244,7 @@ const ContentInner = ({ children, containerRef, showScrollIndicator }) => {
245
244
  children: header
246
245
  }),
247
246
  /* @__PURE__ */ jsx("div", {
248
- className: cn("flex flex-1 flex-col overflow-y-auto", !hasCustomHeader && "pt-18"),
247
+ className: cn("flex flex-1 flex-col overflow-y-auto", !hasCustomHeader && "pt-16"),
249
248
  ref: containerRef,
250
249
  children
251
250
  }),