azure-signalr icon indicating copy to clipboard operation
azure-signalr copied to clipboard

Angular client is not receiveing group message from azure function

Open shyambabu-kolipaka opened this issue 3 years ago • 3 comments

Describe the bug

Angular client is not receiveing group message from azure function

To Reproduce

Azure function

[FunctionName("negotiate")]
        public static SignalRConnectionInfo GetSignalRInfo(
            [HttpTrigger(AuthorizationLevel.Anonymous, "post")] HttpRequest req,
            [SignalRConnectionInfo(HubName = "reservationNotification")] SignalRConnectionInfo connectionInfo)
        {
            return connectionInfo;
        }

        // Used by a group admin or the user themselves to join a group
        //
        // Example assumes both groupName and userId are passed
        [FunctionName("JoinGroup")]
        public static Task JoinGroup(
        [HttpTrigger(AuthorizationLevel.Anonymous, "post", Route = "{groupName}/add/{connectionId}")] HttpRequest req,
        string groupName,
        string userId,
        [SignalR(HubName = "reservationNotification")] IAsyncCollector<SignalRGroupAction> signalRGroupActions,
        ILogger Log)
        {
            //Log.LogInformation("group name :" + groupName + " | userId : " + userId, new int[] { });
            return signalRGroupActions.AddAsync(
                new SignalRGroupAction
                {
                    UserId = userId,
                    GroupName = groupName,
                    Action = GroupAction.Add
                });
        }

        class Notification
        {
            public int siteId { get; set; }
        }

        [FunctionName("SendNotification")]
        public static Task SendMessage(
            [QueueTrigger("notification", Connection = "AzureWebJobsStorage")] string notification,
            [SignalR(HubName = "reservationNotification")] IAsyncCollector<SignalRMessage> signalRMessages,
            ILogger Log)
        {
            Notification obj = JsonConvert.DeserializeObject<Notification>(notification);
            Log.LogInformation("siteId : " + obj.siteId.ToString(), new int[] { });
            return signalRMessages.AddAsync(
                new SignalRMessage
                {
                    Target = "newMessage",
                    GroupName = obj.siteId.ToString(),
                    Arguments = new[] { notification }
                });
        }

Angular service

import { EventEmitter, Injectable } from '@angular/core';
import { HubConnection, HubConnectionBuilder, LogLevel } from '@aspnet/signalr';
import { Notification } from '../Models/notification.model';
import { environment } from '../../environments/environment';
import { HttpClient, HttpHeaders } from '@angular/common/http';
import { ConnectionInfo } from '../models/connectionInfo';

@Injectable()
export class SignalRService {
  messageReceived = new EventEmitter<Notification>();
  connectionEstablished = new EventEmitter<Boolean>();

  private connectionIsEstablished = false;
  private _hubConnection: HubConnection;

  constructor(private http: HttpClient) {
    this.createConnection();
    this.registerOnServerEvents();
    this.startConnection();
  }

  private createConnection() {
		this._hubConnection = new HubConnectionBuilder()
									.configureLogging(LogLevel.Information)
									.withUrl(environment.API_URL)
									.build();
  }

  private startConnection(): void {
    this._hubConnection
      .start()
      .then(() => {
        this.http.post(environment.API_URL + '164/add/123', {}).subscribe(() => {});
        console.log('Hub connection started');
      });
  }

  private registerOnServerEvents(): void {
    this._hubConnection.on('newMessage', (data: any) => {
      console.log(data);
    });
  }
}

Further technical details

  • I am using azure function template
  • ASPNET CORE version => 3.1
  • Angular @aspnet/signalr version 1.1.4

explanation of the problem

I implemented the negotiate, group join functions. which are called from Angular application. And, the there is a thrid function which is triggered based storage queue.

negotiation, and group joining is working perfect. But, Sending messages frim Queue triggered function is not working. Client is not receiving messages. There following 2 scenarios where client receives messages,

  1. If I remove the GroupName while sending messages. That means sending message to all the connected clients.
  2. If I assign ConnectionId property when adding to Group.

So, Is ConnectionId property mandatory while adding to a group?

shyambabu-kolipaka avatar Nov 08 '20 09:11 shyambabu-kolipaka

ConnectionId is not mandatory and adding user to group should work. However, the differences between adding user to group and adding connection to group is the previous one is async operation which means when REST call returns, you cannot guarantee the user has been added to group while the later can guarantee that. So, we recommend to use add connection to group if you can get connectionId

zackliu avatar Nov 09 '20 06:11 zackliu

We are using same method signalRGroupActions.AddAsync to add user or connectionId to group. Is there difference between adding connectionId and user to group internally in the library?

shyambabu-kolipaka avatar Nov 09 '20 09:11 shyambabu-kolipaka

No difference in the library but in the SignalR Service side.

zackliu avatar Nov 13 '20 02:11 zackliu