microsoft / BotFramework-DirectLineJS

JavaScript client library for Microsoft Bot Framework's Direct Line protocol
MIT License
196 stars 123 forks source link

Multiple Continuous API Requests Issue #424

Open pachamuthu5142 opened 2 months ago

pachamuthu5142 commented 2 months ago

I have created a WebChat UI in React using the botframework-directlinejs package. While subscribing to messages, the application is continuously sending multiple API requests. This is leading to performance issues and unnecessary load on the server.

Expected Behavior: The application should only send API requests when necessary, such as when new messages are received.

Actual Behavior: The application is continuously sending multiple API requests, as shown in the attached screenshot.

Screenshot 2024-06-26   @@165840

my code : const subscribeToBotMessages = useCallback(() => { if (!directLine) return;

directLine.connectionStatus$.subscribe((status) => {
  if (status === 2 && !conversationId) {
    localStorage.setItem("conversationId", directLine.conversationId);
    localStorage.setItem("token", directLine.token);
    localStorage.setItem("watermark", directLine.watermark);
  }
});

directLine.activity$
  .filter(
    (activity) =>
      activity.type === "message" && activity.from.id !== "myUserId"
  )
  .subscribe((message) => {
    const timestamp = new Date().toLocaleTimeString([], {
      hour: "2-digit",
      minute: "2-digit",
    });

    const newBotMessage = {
      from: "bot",
      botMessage: message,
      timestamp,
      liked: false,
      disliked: false,
      attachment:
        message.attachments && message.attachments.length > 0
          ? message.attachments.length === 1 && message.attachments[0]
          : null,
      carousel:
        message.attachments && message.attachments.length > 0
          ? message.attachments.length > 1 && message.attachments
          : null,
    };
    setLoading(false);
    if (message.text) {
      try {
        receiveAudioRef.current.play();
      } catch (error) {
        console.log("failed to play", error);
      }
    }
    setMessages((prevMessages) => [...prevMessages, newBotMessage]);
  });

directLine.activity$
  .filter(
    (activity) =>
      activity.type === "message" && activity.from.id === "myUserId"
  )
  .subscribe((message) => {
    const timestamp = new Date().toLocaleTimeString([], {
      hour: "2-digit",
      minute: "2-digit",
    });

    const newUserMessage = {
      from: "user",
      userMessage: message,
      timestamp,
      attachment: filePreview,
    };
    setMessages((prevMessages) => {
      // Check if the user message already exists
      if (
        prevMessages.some(
          (msg) => msg.timestamp === timestamp && msg.from === "user"
        )
      ) {
        return prevMessages;
      }
      return [...prevMessages, newUserMessage];
    });
  });

}, [directLine, conversationId]);

@billba

billba commented 2 months ago

OK so please keep in mind when reading the following that I haven't looked at this code in about seven years 😅

First of all, you don't need to, and probably shouldn't, subscribe twice to the same activity stream. I would instead do something like:

directLine.activity$
  .filter(({type}) => type === "message")
  .subscribe(message => {
    if (message.from.id === "myUserId") {
      ...
    } else {
      ...
    }
  }

As for all those activity requests, by default DirectLine receives activities via WebSocket, so you actually shouldn't see any. Is it possible you set your options do not use WebSocket?

pachamuthu5142 commented 2 months ago

thanks you reply @billba when set webSocket: true those activity requests are stopped but the previous conversations not resuming

billba commented 1 month ago

I'm not quite sure what that means. Can you spell out your scenario in more detail? Also, did you move to a single subscription as I recommended?