How do i map user connection and user id in signalr so that i can send a message to a specific user

放肆的年华 提交于 2021-01-29 02:26:00

问题


I want to send a private message to a user, i have created a hub but unfortunately i have no idea how to do it in signalr core, the documentation also doesn't have any article in it.


回答1:


How do i map user connection and user id in signalr so that i can send a message to a specific user

To achieve above requirement, please refer to the following example.

ChatHub class:

public class ChatHub : Hub
{
    public static List<KeyValuePair<string, string>> ConnectedIds = new List<KeyValuePair<string, string>>();

    public async Task SendMessage(string user, string message)
    {
        await Clients.Others.SendAsync("NoteUpdateNotification", user, message);

        await Clients.All.SendAsync("ReceiveMessage", user, message);
    }

    public async Task SendPrivateMessage(string user, string message, string conid)
    {
        await Clients.Client(conid).SendAsync("ReceiveMessage", user, message + " (private message)");
    }

    public override async Task OnConnectedAsync()
    {
        var connId = Context.ConnectionId;

        var name = Context.GetHttpContext().Request.Query["user"].ToString();

        ConnectedIds.Add(new KeyValuePair<string, string>(connId, name));

        await Clients.All.SendAsync("updateList", ConnectedIds);

        await base.OnConnectedAsync();
    }
}

SignalR JavaScript Client:

<h1>PrivateChat</h1>

<div class="container">
    <div class="row">&nbsp;</div>
    <div class="row">
        <div class="col-6">&nbsp;</div>
        <div class="col-6">
            User..........
    <span id="uname"></span>
    @*<input type="text" id="userInput" />*@
            <br />
            Message...<input type="text" id="messageInput" />
            <input type="button" id="sendButton" value="Send Message" />
        </div>
    </div>
    <div class="row">
        <div class="col-12">
            <hr />
        </div>
    </div>
    <div class="row">
        <div class="col-6">&nbsp;</div>
        <div class="col-6">
            <ul id="messagesList"></ul>
        </div>
    </div>

    <div class="row">
        <div class="col-12">
            <hr />
        </div>
    </div>
    <div class="row">
        <div class="col-6">&nbsp;</div>
        <div class="col-6">
            <h2>Online Users</h2>
            <div>
                <!--<ul id="user_list"></ul>-->
                <div id="online"></div>
            </div>
        </div>
        <div class="col-12">
            <hr />
        </div>
        <div class="col-6">&nbsp;</div>
        <div class="col-6">
            <h2>Private Message</h2>
            <div id="user_id"></div>
            <input type="text" id="txtPrivateMessage" />
            <input type="button" id="sendprivatemessage" value="Send Private Message" />
            <input type="hidden" id="pconnId" value="" />
            <ul id="privatemessagelogs"></ul>
        </div>
    </div>
</div>


<script>
    var user = prompt('Enter your name:', '');
    $("#uname").text(user);
    var connection = new signalR.HubConnectionBuilder().withUrl("/chatHub?user=" + user).build();

    //Disable send button until connection is established
    $("#sendButton").disabled = true;

    connection.on("ReceiveMessage", function (user, message) {
        var msg = message.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;");
        var encodedMsg = user + " says " + msg;

        var li = "<li>" + encodedMsg + "</li>";
        $("#messagesList").append(li);
    });

    connection.on("updateList", function (ids) {
        $('#online').empty();
        console.log(ids);

        $.each(ids, function (k, v) {
            console.log(v["key"] + "/" + v["value"]);

            if (v["value"].toString() != user) {
                $('#online').append("<span onclick=getValue('" + v["key"] + "','" + v["value"] + "')>" + v["value"] + "</span><br/>");
            }
        });
    });


    connection.start().then(function () {
        $("#sendButton").disabled = false;

    }).catch(function (err) {
        return console.error(err.toString());
    });

    $("#sendButton").on("click", function (event) {
        var message = $("#messageInput").val();

        connection.invoke("SendMessage", user, message).catch(function (err) {
            return console.error(err.toString());
        });
        event.preventDefault();
    });

    $("#sendprivatemessage").on("click", function (event) {
        var message = $("#txtPrivateMessage").val();
        var conid = $("#pconnId").val();
        connection.invoke("SendPrivateMessage", user, message, conid).catch(function (err) {
            return console.error(err.toString());
        });

        $('#privatemessagelogs').append('<li><strong>You sent: </strong>:&nbsp;&nbsp;' + $("#txtPrivateMessage").val() + '</li>');

        event.preventDefault();
    });

    function getValue(userId, name) {
        $("#user_id").text("Name: " + name + "Connection Id: " + userId);

        $("#pconnId").val(userId);

        $("#txtPrivateMessage").val("");

        $('#privatemessagelogs').empty();
    }
</script>

Test Result:

Note: The above example just for testing purpose, if you'd like to mapping user to connections on production environment, you can use permanent external storage, such as a database or Azure table storage for storing connection information.



来源:https://stackoverflow.com/questions/56721522/how-do-i-map-user-connection-and-user-id-in-signalr-so-that-i-can-send-a-message

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!