@banta/sdk 5.6.5 → 5.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -7950,8 +7950,6 @@ class CommentViewComponent {
7950
7950
  // Load more from backend if needed
7951
7951
  // Note: Backend only supports fetching more content in one direction.
7952
7952
  let lastMessage = this.previousMessages[0] ?? this.messages[0];
7953
- if (!lastMessage)
7954
- this.hasMore = false;
7955
7953
  if (nextPageSize > 0 && this.newestLast && lastMessage) {
7956
7954
  this.isLoadingMore = true;
7957
7955
  let messages = await this.source.loadAfter(lastMessage, nextPageSize);
@@ -8018,8 +8016,6 @@ class CommentViewComponent {
8018
8016
  nextPageSize -= storedMessages.length;
8019
8017
  }
8020
8018
  const lastMessage = this.olderMessages[this.olderMessages.length - 1] ?? this.messages[this.messages.length - 1];
8021
- if (!lastMessage)
8022
- this.hasMore = false;
8023
8019
  if (nextPageSize > 0 && !this.newestLast && lastMessage) {
8024
8020
  // Load more from backend
8025
8021
  this.isLoadingMore = true;
@@ -8060,16 +8056,16 @@ class CommentViewComponent {
8060
8056
  nextPageSize -= storedMessages.length;
8061
8057
  this.hasMore = this.olderMessages.length > 0;
8062
8058
  }
8063
- if (nextPageSize > 0) {
8059
+ let lastMessage;
8060
+ if (this.newestLast) {
8061
+ lastMessage = this.olderMessages[0] ?? this.messages[0];
8062
+ }
8063
+ else {
8064
+ lastMessage = this.olderMessages[this.olderMessages.length - 1] ?? this.messages[this.messages.length - 1];
8065
+ }
8066
+ if (nextPageSize > 0 && lastMessage) {
8064
8067
  // Load more from backend
8065
8068
  this.isLoadingMore = true;
8066
- let lastMessage;
8067
- if (this.newestLast) {
8068
- lastMessage = this.olderMessages[0] ?? this.messages[0];
8069
- }
8070
- else {
8071
- lastMessage = this.olderMessages[this.olderMessages.length - 1] ?? this.messages[this.messages.length - 1];
8072
- }
8073
8069
  if (!lastMessage) {
8074
8070
  this.isLoadingMore = false;
8075
8071
  this.hasMore = false;
@@ -8094,15 +8090,17 @@ class CommentViewComponent {
8094
8090
  this.isLoadingMore = false;
8095
8091
  }
8096
8092
  // Extract the messages that do not fit in the maxVisibleMessages buffer.
8097
- let overflow;
8098
- if (this.newestLast)
8099
- overflow = this.messages.splice(this.maxVisibleMessages, this.messages.length);
8100
- else
8101
- overflow = this.messages.splice(0, this.maxVisibleMessages);
8102
- // Regardless of the order (newestLast), newMessages represents the direction that is being pushed, since it's definition
8103
- // depends on that order. Move overflowing messages into newMessages.
8104
- this.newMessages = overflow.concat(this.newMessages);
8105
- this.newMessages.splice(this.maxMessages - this.maxVisibleMessages, this.newMessages.length);
8093
+ if (this.messages.length > this.maxVisibleMessages) {
8094
+ let overflow = [];
8095
+ if (this.newestLast)
8096
+ overflow = this.messages.splice(this.maxVisibleMessages, this.messages.length);
8097
+ else
8098
+ overflow = this.messages.splice(0, this.messages.length - this.maxVisibleMessages);
8099
+ // Regardless of the order (newestLast), newMessages represents the direction that is being pushed, since it's definition
8100
+ // depends on that order. Move overflowing messages into newMessages.
8101
+ this.newMessages = overflow.concat(this.newMessages);
8102
+ this.newMessages.splice(this.maxMessages - this.maxVisibleMessages, this.newMessages.length);
8103
+ }
8106
8104
  }
8107
8105
  addMessage(message) {
8108
8106
  if (!message.transientState)
@@ -9048,6 +9046,12 @@ class BantaCommentsComponent {
9048
9046
  return;
9049
9047
  setTimeout(async () => {
9050
9048
  console.log(`[Banta/Comments] Subscribing to topic source '${topicID}'`);
9049
+ // If we are loading a shared comment, we must override the mode to be Newest/All
9050
+ // to ensure we can find the comment.
9051
+ if (this.sharedCommentID) {
9052
+ this._sortOrder = CommentsOrder.NEWEST;
9053
+ this._filterMode = FilterMode.ALL;
9054
+ }
9051
9055
  this.source = await this.backend.getSourceForTopic(topicID, {
9052
9056
  sortOrder: this.sortOrder,
9053
9057
  filterMode: this.filterMode,
@@ -9318,16 +9322,21 @@ class BantaCommentsComponent {
9318
9322
  await this.waitForThreadView();
9319
9323
  await this.threadView.loadMessageInContext(message);
9320
9324
  message = await thread.get(message.id);
9321
- message.transientState ??= {};
9322
- message.transientState.highlighted = true;
9323
- console.dir(message);
9324
- await new Promise(resolve => setTimeout(() => resolve(), 500));
9325
+ if (message) {
9326
+ message.transientState ??= {};
9327
+ message.transientState.highlighted = true;
9328
+ console.dir(message);
9329
+ await new Promise(r => setTimeout(r, 500));
9330
+ }
9325
9331
  }
9326
9332
  else {
9327
9333
  // Make sure that this message is loaded and visible to the user
9328
9334
  await this.commentView.loadMessageInContext(message);
9329
- message.transientState ??= {};
9330
- message.transientState.highlighted = true;
9335
+ message = await source.get(message.id);
9336
+ if (message) {
9337
+ message.transientState ??= {};
9338
+ message.transientState.highlighted = true;
9339
+ }
9331
9340
  }
9332
9341
  this.loadingSharedComment = false;
9333
9342
  await this.scrollToComment(id);
@@ -10688,6 +10697,32 @@ class ChatSource extends SocketRPC {
10688
10697
  }
10689
10698
  return message;
10690
10699
  }
10700
+ /**
10701
+ * Ask server for messages that have occurred since the message with the given ID.
10702
+ * This is used during brief reconnects to avoid dropping messages, while also not
10703
+ * causing mobbing as everyone reconnects after an issue. The backend can choose to
10704
+ * not service this request, instead returning undefined. In that case, the client
10705
+ * is expected to fetch the existing messages and start state anew.
10706
+ *
10707
+ * TODO: this is not yet used
10708
+ *
10709
+ * @param id
10710
+ * @returns
10711
+ */
10712
+ async loadSince(id) {
10713
+ try {
10714
+ let messages = await this.idempotentPeer.loadSince(id);
10715
+ if (messages) {
10716
+ messages = this.mapOrUpdateMessages(messages);
10717
+ }
10718
+ return messages;
10719
+ }
10720
+ catch (e) {
10721
+ console.error(`[Banta/${this.identifier}] Error occurred while trying to get existing messages:`);
10722
+ console.error(e);
10723
+ return [];
10724
+ }
10725
+ }
10691
10726
  async getExistingMessages() {
10692
10727
  try {
10693
10728
  let messages = await this.idempotentPeer.getExistingMessages(this.options.initialMessageCount ?? 20);
@@ -10788,7 +10823,10 @@ class ChatSource extends SocketRPC {
10788
10823
  async send(message) {
10789
10824
  await this.ensureConnection();
10790
10825
  message.id ??= v4();
10791
- return await this.idempotentPeer.sendMessage(message);
10826
+ let finishedMessage = await this.idempotentPeer.sendMessage(message);
10827
+ this.messageMap.set(finishedMessage.id, finishedMessage);
10828
+ this._messageReceived.next(finishedMessage);
10829
+ return finishedMessage;
10792
10830
  }
10793
10831
  async loadAfter(message, count) {
10794
10832
  if (!message)
@@ -10873,6 +10911,9 @@ class StaticChatSource {
10873
10911
  }
10874
10912
  this.backend.getSourceCountForTopic(this.identifier);
10875
10913
  }
10914
+ async loadSince(id) {
10915
+ return undefined;
10916
+ }
10876
10917
  async getExistingMessages() {
10877
10918
  if (this.parentIdentifier) {
10878
10919
  return await this.backend.getReplies(this.parentIdentifier, this.sortOrder, this.filterMode, 0, this.initialMessageCount);
@@ -10909,12 +10950,22 @@ class ChatBackend extends ChatBackendBase {
10909
10950
  super(...arguments);
10910
10951
  this.options = inject(BANTA_SDK_OPTIONS);
10911
10952
  this.platformId = inject(PLATFORM_ID);
10953
+ this.runId = v4();
10912
10954
  }
10913
10955
  get serviceUrl() {
10914
10956
  return `${this.options?.serviceUrl ?? 'http://localhost:3422'}`;
10915
10957
  }
10916
10958
  async connectToService() {
10917
- let socket = new DurableSocket(`${this.serviceUrl.replace(/^http/, 'ws')}/socket`);
10959
+ let deviceId = v4();
10960
+ if (typeof localStorage !== 'undefined') {
10961
+ if (localStorage['banta-chat:deviceId']) {
10962
+ deviceId = localStorage['banta-chat:deviceId'];
10963
+ }
10964
+ else {
10965
+ localStorage['banta-chat:deviceId'] = deviceId;
10966
+ }
10967
+ }
10968
+ let socket = new DurableSocket(`${this.serviceUrl.replace(/^http/, 'ws')}/socket`, undefined, `${deviceId},${this.runId}`);
10918
10969
  await new Promise((resolve, reject) => {
10919
10970
  socket.onopen = () => {
10920
10971
  resolve();