SignalR在Asp.NetCore的使用入门

news2025/1/17 6:08:22

SignalR在ASP.NET CORE下的使用

SignalR是微软提供的实时Web通信的库

它会自己根据情况使用不同的链接方式,主要有

  • WebSocket
  • long polling
  • Forever frame
  • Sever Events Sent

等方式,故可以不管其具体的实现方式,差不多等于开箱即用了。

一.StartUp中的起始配置

在StartUp中添加配置

public void ConfigureServices(IServiceCollection services)
{
    services.AddRazorPages();
    services.AddSignalR();     //只需要添加AddSignalR
    services.AddControllers();
    
    services.AddCors(options =>
    options.AddPolicy("lingluAllCors",
    p => 	p.AllowAnyOrigin().
              AllowAnyHeader().
              AllowAnyMethod()));
    #endregion
}

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }
    else
    {
        app.UseExceptionHandler("/Error");
    }

    app.UseStaticFiles();

    app.UseRouting();

    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapControllers();
        endpoints.MapRazorPages();
        //添加/注册对应的Hub类,并添加路由
        //请注意:在不同的.Net Core版本中,MapHub方法也可能在app中
        //如果找不到MapHub请两个地方都试一试
        endpoints.MapHub<ChatHub>("/chatHub");
    });

    app.UseCors("lingluAllCors");
}

二.配置Hub中心类和服务器推送信息

Hub类是SignalR的核心工具类

它主要有两个功能

1. 向Client(浏览器)的监听处主动推送消息【服务器主动推送数据】

2.接受Client的发起的信息(请求),【普通的请求----->响应模式】

例:Hub类的简单解释

public class ChatHub : Hub
{
	//继承Hub类可以复写
    //Task OnDisconnectedAsync(Exception exception)
    //Task OnConnectedAsync()
    //以上方法在Client链接/断开时被触发,而推送/接受信息的方法则需要你自定义
    
    //Hub里的方法不在后台调用,而是通过函数名和参数在前端进行js调用
    public async Task SendMessage(string user, string message)
    {
        //这里和普通的 请求---->响应 的方式很像
        //在这里拿到参数,写一些逻辑
		Console.WriteLine("User is" + user + " | Message is"+message);
        
        //但区别在于,你可以选择是否响应
        //这个SendAsync在下一小节细讲
        //Clients.All.SendAsync("ReceiveMessage2", user, message);
    }

	
    //如果请求需要返回,也可以多次返回(或是一些有条件的返回)
    public async Task SendMessage2(string user, string message)
    {

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

        for (int i = 0; i < 10; i++)
        {
            Thread.Sleep(2000);
            await Clients.All.SendAsync("ReceiveMessage2","van you see","luckshit");
        }
    }


   
}

例:服务器主动推送消息给前端

当你完成自定义Hub类,并把它注册到StartUp中,

你就能通过ASP.NET CORE自带的DI(依赖注入)

获取该类型(你自定义的Hub)泛型的IHubContext对象,

然后后台就可以在链接存在时随时的推送数据了

以一个Controller为例:

[Route("api/[controller]/[action]")]
[ApiController]
public class SendController : ControllerBase
{
    //可以通过DI来获取指定的自定义中心泛型的IHubContext工具
    private readonly IHubContext<ChatHub> _hubContext;

    public SendController(IHubContext<ChatHub> hubContext)
    {
        _hubContext = hubContext;
    }

    
    [HttpGet]
    public async Task<string> SendData(string message)
    {
        //给前端监听的ReceiveMessage2方法传递参数
        await _hubContext.Clients.All.SendAsync("ReceiveMessage2", "van you see", "luckshit");

        return "something you want";
    }
}

三.前端代码和显示

前端的显示

需要微软提供的js文件

如果你使用node.js的话,可以在直接npm install下来,不使用的话也可以直接引入js文件

npm install @microsoft/signalr
# or
yarn add @microsoft/signalr

链接:

@microsoft/signalr - npm (npmjs.com)

在项目中创建页面,然后引入js

在这里插入图片描述

页面代码:

<!DOCTYPE html>
    <html>
    <head>
        <meta charset="utf-8" />
        <title></title>
    </head>
    <body>

    <div class="container">
        <div class="row">&nbsp;</div>
        <div class="row">
            <div class="col-2">User</div>
            <div class="col-4"><input type="text" id="userInput" /></div>
        </div>
        <div class="row">
            <div class="col-2">Message</div>
            <div class="col-4"><input type="text" id="messageInput" /></div>
        </div>
        <div class="row">&nbsp;</div>
        <div class="row">
            <div class="col-6">
                <input type="button" id="sendButton" value="Send Message" />
            </div>
        </div>
    </div>
    <div class="row">
        <div class="col-12">
            <hr />
        </div>
    </div>
    <div class="row">
        <div class="col-6">
            <ul id="messagesList"></ul>
        </div>
    </div>
    <!--引入js文件-->
    <script src="./lib/microsoft/signalr/dist/browser/signalr.js"></script>

    <script>
       
        //初始化客户端 官网 https://docs.microsoft.com/zh-cn/aspnet/core/signalr/javascript-client?view=aspnetcore-5.0&tabs=visual-studio

        //创建链接并指定到在StartUp中配置的Chathub的路由,
        const connection = new signalR.HubConnectionBuilder()
            .withUrl("/chathub")
            .configureLogging(signalR.LogLevel.Information)
            .build();

        //start开始连接,
        async function start() {
            try {
                //会在后台触发连接Hub的Task OnConnectedAsync()方法,
                await connection.start();
                
                //如果想要在链接处获取身份信息,即使用/获取自带的UserID/Group对象什么的,
                //需要使用ASP.NET CORE 官方的authorize, 和Identity的相关内容,如果使用的是自研的登陆和认证内容,则无法使用以上的user对象
                //请手动发送empno/username等信息
                
                console.log("SignalR Connected.");
                console.log(connection.connectionId);
                
            } catch (err) {
                console.log(err);
                //异步发起重连
                setTimeout(start, 5000);
            }
        };

        //重连机制
        connection.onclose(async () => {
            await start();
        });

        //ReceiveMessage2为监听的数据标识,可自定义
        //解释:当后台调用hub对象(IHubContext)SendAsync时,指定的第一个参数即为此标识时(或者直说第一个method参数等于此标识时),则前端会自动调用对应的函数,
        //      后台的返回值则会注入到前端的参数中
        connection.on("ReceiveMessage2", function (user, message) {

            //UI显示监听的数据
            var li = document.createElement("li");
            document.getElementById("messagesList").appendChild(li);
            li.textContent = `ReceiveMessage2:${user} says ${message}`;


        });



        //发起连接
        start();



        //按钮事件(发送链接)
        document.getElementById("sendButton").addEventListener("click", function (event) {
            var user = document.getElementById("userInput").value;
            var message = document.getElementById("messageInput").value;

            SendMessage2为自定义方法ChatHub.cs 定义的相同
            connection.invoke("SendMessage2", user, message).catch(function (err) {
                return console.error(err.toString());
            });

            event.preventDefault();
        });
    </script>
</body>
</html>

四.运行和测试

后台推送信息给前台

运行程序,开打页面和开发者工具

在这里插入图片描述

然后,调用Controller中的测试方法 api/Send/SendData

在这里插入图片描述

调用Hub对象(IHubContext)的SendAsync方法

在这里插入图片描述

然后再回到前端查看页面的效果

在这里插入图片描述

常规的前端请求到后台(在Signalr中可以不作响应)

在页面的输入框中输入数据,提交去触发前端 hubconnection的invoke方法,

后台调用invoke指定的Hub类的方法
(定义的Hub类中的对应方法,注意:这里的Hub类不是Hub对象(IHubContext))

在这里插入图片描述

然后在方法体中给前端的监听函数推送信息。

在这里插入图片描述

这种方式就和请求响应的模式很接近,但是也可以不响应(情况比较少)。

测试小节总结

一定要弄清Hub类的作用,

  • Hub类中定义的方法为只能被前端invoke调用,但是否响应(SendAsync)是可选的
  • 当你在其他的地方要推送信息(SendAsync)时,使用的是IHubContext
  • IHubContext可以使用DI,你可以在后台的任何地方自动发送消息
  • 不要尝试将IHubContext 转化为T,后台无法调用Hub类方法,路已被锁死

补充

Hub可以获取指定Client,
并有一套API和ASP.NET CORE 的Autherize,Identity配合可以
获取User,Group,Auth…的信息,
如果你的程序没有用到ASP.NET CORE的Authrize,那就用不了。
但是可以在连接开始阶段发送用户信息,然后借以统计是否存在链接/对手链接

https://download.csdn.net/download/jamenu/87380909?spm=1001.2014.3001.5501

不要尝试将IHubContext 转化为T,后台无法调用Hub类方法,路已被锁死

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/158744.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Docker部署 Oracle12c

Docker部署 Oracle12c Docker部署 registry Docker搭建 svn Docker部署 Harbor Docker 部署SQL Server 2017 Docker 安装 MS SqlServer Docker部署 Oracle12c 文章目录Docker部署 Oracle12c部署步骤1.查询oracle镜像2.下载镜像3.创建容器4.进入容器5.连接oracle数据库部署步骤…

Unreal动态多播委托

相对于普通多播委托,动态多播委托可以在蓝图中绑定事件。在这里记录一下它的使用方式:定义动态多播委托类型:声明委托变量:绑定函数:通过Add绑定:需要定义FScriptDelegate变量:为FScriptDelegate添加绑定函数这种方法的好处是可以针对单个函数进行解绑:通过AddDynamic标记宏绑定…

Linux 调度器之抢占式调度

文章目录前言一、简介1.1 need_resched标志1.2 try_to_wake_up二、抢占调度2.1 抢占简介2.2 用户态抢占2.2.1 从系统调用返回用户空间2.2.2 从中断返回用户空间2.3 内核态抢占2.2.1 preempt_count2.2.2 调用preempt_enable()2.2.3 从中断返回内核空间时总结参考资料前言 在这片…

worker多线程的使用与理解

JavaScript是单线程的&#xff0c;并不是说它是单线程语言&#xff0c;只能说在浏览器中运行是单线程的&#xff0c;单线程会免去许多麻烦&#xff0c;比如说&#xff0c;有两个线程同时进行DOM操作&#xff0c;一个是在父级下添加子元素&#xff0c;一个是删除这个父级元素&am…

Pandas数据清洗函数大全

文章目录 一、drop()&#xff1a;删除指定行列 1. 删除指定行2. 删除指定列 二、del()&#xff1a;删除指定列三、isnull()&#xff1a;判断是否为缺失 1. 判断是否为缺失2. 判断哪些列存在缺失3. 统计缺失个数 四、notnull()&#xff1a;判断是否不为缺失五、dropna()&#x…

Java笔记024-Math类、Arrays类、System类、BigInteger和BigDecimal类、日期类

常用类Math类基本介绍Math类包含用于执行基本数学运算的方法&#xff0c;如初等指数、对数、平方根和三角函数方法一览(均为静态方法)Math常见方法应用案例1、 abs绝对值2、pow求幂3、ceil向上取整4、floor 向下取整5、round 四舍五入6、sqrt 求开方7、random求随机数//思考&am…

Webpack常见的插件和模式

1、认识Plugin Webpack的另一个核心是Plugin&#xff0c;官方有这样一段对Plugin的描述&#xff1a; While loaders are used to transform certain types of modules, plugins can be leveraged to perform a wider range of tasks like bundle optimization, asset manageme…

《对线面试官》| 高频计算机网络面试题 pt.2

目录11、Get与POST的区别12、Session、Cookie 的区别13、简单聊聊 HTTP 协议吧14、URI 和 URL 的区别15、GET 和 POST 方法都是安全和幂等的吗&#xff1f;16、说说 HTTP/1.1 相比 HTTP/1.0 提高了什么性能&#xff1f;17、那上面的 HTTP/1.1 的性能瓶颈&#xff0c;HTTP/2 做了…

中国蚁剑的工作原理

中国蚁剑连接http://192.168.11.157/dvwa/hackable/uploads/pass.php蚁剑连接并同时用wireshark抓取流量1274 行&#xff0c;追踪tcp流因为我们的php.php内容是 $_POST[pass]&#xff0c;所以这里是post了一个pass参数&#xff0c;后面跟上了命令。通过站长工具-URL解码/编码 (…

15.Isaac教程--Isaac机器人引擎简介

Isaac机器人引擎简介 ISAAC教程合集地址: https://blog.csdn.net/kunhe0512/category_12163211.html 文章目录Isaac机器人引擎简介基础Codelets完整的应用基础 本节介绍如何使用 Isaac 机器人引擎。 它介绍了相关术语并解释了 Isaac 应用程序的结构。 Isaac 应用程序由 JavaS…

卫星AIS接收机

1.设备简介星载AIS模块&#xff0c;专门针对小卫星设计的AIS载荷&#xff0c;设计时考虑到CubeSat的尺寸、重量和功率限制&#xff0c;也可以作为较大的LEO卫星上的有效载荷。2.产品特征独立4信道AIS接收机集成LNA和SAW滤波器AIS帧的数据存储支持频谱样本采集安全在轨软件升级支…

【Wiki】XWiki安装教程_War包版本

目录0、XWiki说明1、war包安装说明1.1、环境说明1.2、如果懒得下载可以使用这边准备好的物料包汇总2、war包安装2.1、Tomcat安装2.2、java安装(需要root权限)2.3 、使用 source /etc/profile 刷新linux配置2.4、数据库安装2.5、解压war包与xip2.6、修改配置文件2.6.1、修改WEB-…

mysql快速生成100W条测试数据(4)全球各城市房价和销售数据并存入mysql数据库

首先这个就是我们需要生成的数据类型&#xff0c;这种只是我们用于测试以及学习时候使用&#xff0c;主要就是全球城市房价的均值和一些虚拟的销售数据 这是之前的文章里面包含一些以前的一些操作流程可以进行参考学习 更加详细操作步骤在第一篇文章里面 mysql快速生成100W条测…

Speckle Revit连接器使用教程

Speckle Revit 连接器目前支持 Autodesk Revit 2020、2021、2022 和 &#x1f195;2023。 1、安装Speckle revit连接器 要安装 Revit 连接器并添加 Speckle 帐户&#xff0c;请按照 Speckle 管理器中的说明进行操作。 安装后&#xff0c;可以在Speckle选项卡下的功能区菜单中…

一个前端大神电脑里的秘密

前言作为前端仔&#xff0c;当你入职一家公司&#xff0c;拿到新发的电脑&#xff0c;你会对电脑干点啥&#xff0c;装开发环境&#xff1f;装软件&#xff1f;你是否铺天盖地到处找之前电脑备份的东西&#xff1f;又或者是想不起来有什么上一台电脑好用的软件叫什么名&#xf…

KT148A语音芯片420s秒的语音空间是什么意思,mp3文件支持多大

一、问题简介 我想问一下KT148A这个芯片真的能存420秒的语音么&#xff1f;我随便一个5秒的语音mp3格式都65k了&#xff0c;如果是这样的话 那我的mp3的源文件在最小的采样率和最小码率的情况下 mp3文件可以支持多大&#xff1f;有没有实际测试的数据&#xff0c;使用的是一线串…

【可解释性机器学习】可解释机器学习简介与特征选择方法

特征选择&#xff1a;Feature Importance、Permutation Importance、SHAP1. Introduction什么是可解释机器学习&#xff08;Explainable ML&#xff09;&#xff1f;为什么需要Explainable ML?直接使用一些可以interpretable的模型不好吗&#xff1f;2. Local Explanation方法…

Homekit智能家居DIY-智能吸顶灯

灯要看什么因素 照度 可以简单理解为清晰度&#xff0c;复杂点套公式来说照度光通量&#xff08;亮度&#xff09;单位面积&#xff0c;简单理解的话就是越靠近灯光&#xff0c;看的就越清楚&#xff0c;是个常识性问题。 不同房间户型对照度的要求自然不尽相同&#xff0c;…

http协议之Range

http协议中可能会遇到&#xff1a;请求取消或数据传输中断&#xff0c;这时客户端已经收到了部分数据&#xff0c;后面再请求时最好能请求剩余部分&#xff08;断点续传&#xff09;&#xff1b;或者&#xff0c;对于某个较大的文件&#xff0c;能够支持客户端多线程分片下载..…

某集团汽车配件电子图册性能分析案例(三)

背景 汽车配件电子图册系统是某汽车集团的重要业务系统。业务部门反映&#xff0c;汽车配件电子图册调用图纸时&#xff0c;出现访问慢现象。 汽车集团总部已部署NetInside流量分析系统&#xff0c;使用流量分析系统提供实时和历史原始流量。本次分析重点针对汽车配件电子图册…