@ai4b-team/fsaos-gateway-sdk 3.1.0 → 3.2.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.
package/dist/index.d.cts CHANGED
@@ -717,6 +717,10 @@ declare function fetchChannelMessagesWithCards(channelPath: string, parentMessag
717
717
  /** Response shape from fetchChannelMessagesPage. */
718
718
  interface ChannelMessagesPage {
719
719
  messages: ChannelMessage[];
720
+ /** Cards grouped by parent message path (child cards of messages in this page). */
721
+ messageCards: Map<string, ChannelCard[]>;
722
+ /** Cards that are direct siblings of the channel (not nested under a message). */
723
+ siblingCards: ChannelCard[];
720
724
  /** Mode returned by kernel: 'top_level' or 'thread'. */
721
725
  mode: 'top_level' | 'thread';
722
726
  }
@@ -1571,6 +1575,10 @@ interface InfiniteChannelMessagesOptions {
1571
1575
  */
1572
1576
  declare function useInfiniteChannelMessages(options: InfiniteChannelMessagesOptions): {
1573
1577
  messages: ChannelMessage[];
1578
+ /** Cards grouped by parent message path (child cards of messages). */
1579
+ messageCards: Map<string, ChannelCard[]>;
1580
+ /** Cards that are direct siblings of the channel (not nested under a message). */
1581
+ siblingCards: ChannelCard[];
1574
1582
  threads: ChannelMessage[];
1575
1583
  isLoading: boolean;
1576
1584
  isFetching: boolean;
package/dist/index.d.ts CHANGED
@@ -717,6 +717,10 @@ declare function fetchChannelMessagesWithCards(channelPath: string, parentMessag
717
717
  /** Response shape from fetchChannelMessagesPage. */
718
718
  interface ChannelMessagesPage {
719
719
  messages: ChannelMessage[];
720
+ /** Cards grouped by parent message path (child cards of messages in this page). */
721
+ messageCards: Map<string, ChannelCard[]>;
722
+ /** Cards that are direct siblings of the channel (not nested under a message). */
723
+ siblingCards: ChannelCard[];
720
724
  /** Mode returned by kernel: 'top_level' or 'thread'. */
721
725
  mode: 'top_level' | 'thread';
722
726
  }
@@ -1571,6 +1575,10 @@ interface InfiniteChannelMessagesOptions {
1571
1575
  */
1572
1576
  declare function useInfiniteChannelMessages(options: InfiniteChannelMessagesOptions): {
1573
1577
  messages: ChannelMessage[];
1578
+ /** Cards grouped by parent message path (child cards of messages). */
1579
+ messageCards: Map<string, ChannelCard[]>;
1580
+ /** Cards that are direct siblings of the channel (not nested under a message). */
1581
+ siblingCards: ChannelCard[];
1574
1582
  threads: ChannelMessage[];
1575
1583
  isLoading: boolean;
1576
1584
  isFetching: boolean;
package/dist/index.js CHANGED
@@ -868,8 +868,22 @@ async function fetchChannelMessagesPage(channelPath, options) {
868
868
  const response = await gatewayCall("get-channel-messages", params);
869
869
  const raw = response;
870
870
  const items = raw.messages || [];
871
+ const cards = parseChannelCards(items);
872
+ const messageCards = /* @__PURE__ */ new Map();
873
+ const siblingCards = [];
874
+ for (const card of cards) {
875
+ if (card.parentMessagePath) {
876
+ const existing = messageCards.get(card.parentMessagePath) || [];
877
+ existing.push(card);
878
+ messageCards.set(card.parentMessagePath, existing);
879
+ } else {
880
+ siblingCards.push(card);
881
+ }
882
+ }
871
883
  return {
872
884
  messages: parseChannelMessages(items),
885
+ messageCards,
886
+ siblingCards,
873
887
  mode: raw.mode || "top_level"
874
888
  };
875
889
  } catch (err) {
@@ -877,7 +891,7 @@ async function fetchChannelMessagesPage(channelPath, options) {
877
891
  `[gateway] Failed to fetch channel messages page for ${channelPath}:`,
878
892
  err
879
893
  );
880
- return { messages: [], mode: "top_level" };
894
+ return { messages: [], messageCards: /* @__PURE__ */ new Map(), siblingCards: [], mode: "top_level" };
881
895
  }
882
896
  }
883
897
  function invalidateChildren(path) {
@@ -2400,17 +2414,60 @@ function useInfiniteChannelMessages(options) {
2400
2414
  }
2401
2415
  return flat.sort((a, b) => a.seq - b.seq);
2402
2416
  }, [query.data?.pages]);
2417
+ const { messageCards, siblingCards } = useMemo(() => {
2418
+ const mc = /* @__PURE__ */ new Map();
2419
+ const sc = [];
2420
+ if (!query.data?.pages) return { messageCards: mc, siblingCards: sc };
2421
+ const seenCards = /* @__PURE__ */ new Set();
2422
+ for (const page of query.data.pages) {
2423
+ for (const [path, cards] of page.messageCards) {
2424
+ for (const card of cards) {
2425
+ if (seenCards.has(card.id)) continue;
2426
+ seenCards.add(card.id);
2427
+ const existing = mc.get(path) || [];
2428
+ existing.push(card);
2429
+ mc.set(path, existing);
2430
+ }
2431
+ }
2432
+ for (const card of page.siblingCards) {
2433
+ if (seenCards.has(card.id)) continue;
2434
+ seenCards.add(card.id);
2435
+ sc.push(card);
2436
+ }
2437
+ }
2438
+ return { messageCards: mc, siblingCards: sc };
2439
+ }, [query.data?.pages]);
2440
+ const qc = useQueryClient();
2441
+ const debounceRef = useRef(null);
2442
+ const stableKey = useMemo(
2443
+ () => [...vfsKeys.channelMessages(channelPath || "", parentMessageId), "infinite", limit],
2444
+ [channelPath, parentMessageId, limit]
2445
+ );
2403
2446
  useEffect(() => {
2404
2447
  if (!realtime || !channelPath || !queryEnabled) return;
2405
- const unsub = subscribeToEvents(channelPath, (event) => {
2406
- if (event.event_type === "vfs_change") {
2407
- query.refetch();
2448
+ const unsub = subscribeToEvents(
2449
+ "vfs_change",
2450
+ () => {
2451
+ if (debounceRef.current) clearTimeout(debounceRef.current);
2452
+ debounceRef.current = setTimeout(() => {
2453
+ qc.invalidateQueries({ queryKey: stableKey });
2454
+ }, 500);
2455
+ },
2456
+ (data) => {
2457
+ return (data.item_type === "message" || data.item_type === "card") && typeof data.path === "string" && data.path.startsWith(channelPath);
2408
2458
  }
2409
- });
2410
- return unsub;
2411
- }, [realtime, channelPath, queryEnabled]);
2459
+ );
2460
+ return () => {
2461
+ unsub();
2462
+ if (debounceRef.current) clearTimeout(debounceRef.current);
2463
+ };
2464
+ }, [realtime, channelPath, queryEnabled, stableKey, qc]);
2412
2465
  return {
2413
2466
  messages,
2467
+ /** Cards grouped by parent message path (child cards of messages). */
2468
+ messageCards,
2469
+ /** Cards that are direct siblings of the channel (not nested under a message). */
2470
+ siblingCards,
2414
2471
  threads: messages.filter((m) => m.reply_count > 0),
2415
2472
  isLoading: query.isLoading,
2416
2473
  isFetching: query.isFetching,