.Net6使用SignalR实现前后端实时通信

代码部分

  • 后端代码 (Asp.net core web api,用的.net6)
  • Program.cs

代码运行逻辑:
​1. 通过 WebApplication.CreateBuilder(args) 创建一个 ASP.NET Core 应用程序建造器。
2. 使用 builder.Services.AddControllers() 添加 MVC 控制器服务和 builder.Services.AddSignalR() 添加 SignalR 服务。
3. 注册 Swagger 和 Cors 跨域设置的服务,并添加 ChatHub 类作为单例服务。
4. 通过 builder.Build() 构建应用程序。
5. 在 if (app.Environment.IsDevelopment()) 中使用 Swagger 和 SwaggerUI 中间件,只在当前环境下使用。
6. 使用 app.UseAuthorization() 添加授权中间件。
7. 使用 app.UseRouting() 开启路由功能中间件。
8. 使用 app.UseCors(“CorsSingnalR”) 设置跨域策略,使用名为 “CorsSingnalR” 的策略,允许来自任何来源的访问。
9. 使用 app.MapControllers() 将 MVC 控制器添加到请求处理管道中。
10. 使用 app.MapHub(“/chathub”) 添加 SignalR 路由,并将 ChatHub 类注册为路由,在客户端和服务器之间建立 WebSocket 连接
11. 最后,使用 app.Run() 启动应用程序。

using Microsoft.AspNetCore.SignalR;
using PracticeProjects.Logic;var builder = WebApplication.CreateBuilder(args); //创建asp.net core程序建造器,这个建造器允许我们配置应用程序的服务和中间件builder.Services.AddControllers();  //添加mvc控制器服务。用于处理http请求俄响应
builder.Services.AddSignalR();//用来实现实时通信builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();builder.Services.AddSingleton<ChatHub>();
//跨域设置
builder.Services.AddCors(op =>
{op.AddPolicy("CorsSingnalR",set =>{set.SetIsOriginAllowed(origin => true).AllowAnyHeader().AllowAnyMethod().AllowCredentials();});
});
var app = builder.Build();// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{app.UseSwagger();app.UseSwaggerUI();
}app.UseAuthorization();app.UseRouting();//中间件,用于开启路由功能。
app.UseCors("CorsSingnalR");//app.UseRouting(),之后app.UseCors设置跨域策略app.MapControllers();//将MVC控制器添加到请求处理管道中
app.MapHub<ChatHub>("/chathub");//添加SignalR路由;将SignalR的ChatHub类作为路由,在客户端与服务段建立WebSocket连接app.Run();//应用程序启动

ChatController.cs

  • List item
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.SignalR;
using PracticeProjects.Logic;
using PracticeProjects.Model;namespace PracticeProjects.Controllers
{[Route("[controller]")][ApiController]public class ChatController : ControllerBase{private readonly ChatHub _chatHubContext;private readonly ILogger<ChatController> _logger;public ChatController(ChatHub chatHubContext, ILogger<ChatController> logger){_chatHubContext = chatHubContext;_logger = logger;}[Route("api/SendMsg")][HttpPost]public async Task<dynamic> SendMessage(ChatModel chat){await _chatHubContext.SendMessage(chat);return "发送成功";}}
}

方法类(ChatHub:继成Hub,Hub是SignalR中用于处理客户端与服务端双向通信的关键组件。)

using Microsoft.AspNetCore.SignalR;
using PracticeProjects.Model;namespace PracticeProjects.Logic
{/// <summary>/// 消息发送/// </summary>public class ChatHub : Hub{public async Task SendMessage(ChatModel chat){if(Clients!=null)await Clients.All.SendAsync("RecieveMessage", chat.name+":"+chat.content);}}
}

Model类(ChatModel):

namespace PracticeProjects.Model
{public class ChatModel{public string? name { get; set; }public string? content { get; set; }}
}
  • 前端关键部分代码(网上找的代码,用来模拟客户端)
    App.vue
<script setup>
import { ref, reactive, onMounted, onBeforeUnmount } from 'vue';import { connection, connect, send, disconnect } from './utils/signalr';const msgInfo = reactive({ name: '张三', content: '' });
const receivemsglist = ref([]);//发送消息
const sendMsg = async () => {await send("SendMessage", msgInfo);
}onMounted(async () => {// 建立连接connect('http://localhost:5130/chathub'); // 开始连接await connection.start();// 注册方法(接收服务器推送过来的数据)connection.on('RecieveMessage', (res) => {console.log(`${new Date().toLocaleString()}】:从服务器同步消息成功!`);receivemsglist.value.push(res);});
});// 卸载
onBeforeUnmount(() => {// 断开连接disconnect();
});</script><template><div><a href="https://vitejs.dev" target="_blank"><img src="/vite.svg" class="logo" alt="Vite logo" /></a><a href="https://vuejs.org/" target="_blank"><img src="./assets/vue.svg" class="logo vue" alt="Vue logo" /></a></div><!-- <HelloWorld msg="Vite + Vue" /> --><div>姓名:<input type="text" v-model="msgInfo.name"><br>内容:<input type="text" v-model="msgInfo.content"><br><button type="button" @click="sendMsg">发送</button><br><table><tr><th>消息列表:</th></tr><tr v-for="(item, i) in receivemsglist" :key="i"><td>{{ item }}</td></tr></table></div>
</template><style scoped>
.logo {height: 6em;padding: 1.5em;will-change: filter;transition: filter 300ms;
}.logo:hover {filter: drop-shadow(0 0 2em #646cffaa);
}.logo.vue:hover {filter: drop-shadow(0 0 2em #42b883aa);
}
</style>

signalr.js

import * as signalR from '@microsoft/signalr';//如果需要身份验证
//.withUrl('/messageHub', {accessTokenFactory: () => sessionStorage.getItem('token')})
let connection;// 建立连接
async function start(url) {try {connection = new signalR.HubConnectionBuilder().withUrl(url)//跨域需要使用绝对地址.configureLogging(signalR.LogLevel.Information).withAutomaticReconnect() // 设置自动重连机制.build();} catch (err) {console.log(err);setTimeout(start, 10000);//错误重连}
}// 开始signalr连接
const connect = async (url) => {await start(url);console.log(`${new Date().toLocaleString()}:SignalR已连接成功!`);
};// 调用服务端方法 发送消息
async function send(methodName, param) {try {await connection.invoke(methodName, param);} catch (err) { console.error(err); }
}//断开连接
const disconnect = async () => {await connection.stop();console.log(`${new Date().toLocaleString()}:SignalR已断开连接!`);
};export { connection, connect, send, disconnect };

运行测试:

  1. 前后端代码启动
  2. 客户端请求服务端建立websocket连接:
    在这里插入图片描述
  3. 连接建立后,服务端可主动向前端推送消息
    在这里插入图片描述

上传的资源:

SignalR实时通信代码资源

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

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

相关文章

两周掌握Vue3(五):自定义指令、路由、ajax

文章目录 一、自定义指令1.创建和使用自定义指令2.钩子函数3.使用参数 二、路由1.创建一个router实例2.在components目录中创建组件3.将路由实例挂载到应用4.使用路由 三、Ajax 代码仓库&#xff1a;跳转 当前分支&#xff1a;05 一、自定义指令 自定义指令是Vue.js框架提供的…

基于Springboot的善筹网(众筹网-有报告)。Javaee项目,springboot项目。

演示视频&#xff1a; 基于Springboot的善筹网(众筹网-有报告)。Javaee项目&#xff0c;springboot项目。 项目介绍&#xff1a; 采用M&#xff08;model&#xff09;V&#xff08;view&#xff09;C&#xff08;controller&#xff09;三层体系结构&#xff0c;通过Spring S…

Vue入门七(Vuex的使用|Vue-router|LocalStorage与SessionStorage和cookie的使用)

文章目录 一、Vuex1&#xff09;理解vuex2&#xff09;优点3&#xff09;何时使用&#xff1f;4&#xff09;使用步骤① 安装vuex② 注册vuex③ 引用vuex④ 创建仓库Store五个模块介绍 5&#xff09;基本使用 二、Vue-router三、LocalStorage与SessionStorage、cookie的使用 一…

ChatGPT Plus 经验分享:是否值得花钱升级?

ChatGPT Plus 经验分享&#xff1a;是否值得花钱升级&#xff1f; 五星上将麦克阿瑟曾经说过&#xff1a;“在有钱与没钱面前&#xff0c;我选择了or” ChatGPT 的每月订阅方案- ChatGPT Plus 已经推出一段时间了&#xff0c;目前的费用是$20 USD / 月(约TWD 610 / 月)。 Open…

Spirng MVC见解1

1. SpringMVC概述 1.1 MVC介绍 MVC是一种设计模式&#xff0c;将软件按照模型、视图、控制器来划分&#xff1a; M&#xff1a;Model&#xff0c;模型层&#xff0c;指工程中的JavaBean&#xff0c;作用是处理数据 JavaBean分为两类&#xff1a; 一类称为数据承载Bean&#x…

mybatis基本注解、增删改查、结果集映射、一对一、一对多

mybatis注解 基本注解新增删除修改查询 结果映射注解Results结果映射一对一映射一对多映射 基本注解 新增 功能&#xff1a;Insert完成新增操作&#xff0c;类似配置文件的 元素&#xff1b; 说明&#xff1a;新增时所用的参数取值是接口方法的入参&#xff0c;可以是对象&a…

Linux入门级常用命令学习笔记

以下命令是我跟着编程界的大佬鱼皮学习Linux时用的命令&#xff0c;我把它都记下来&#xff0c;权当作笔记&#xff0c;可供自己后期反复练习使用&#xff0c;让我们学习一下最基本的Linux命令吧。 一、Linux实战命令 在dos下 【ssh 服务器ip】可以连接服务器&#xff0c;输入…

运筹说 第80期 | 最小费用最大流问题

前面我们学习了图与网络分析的基础知识及经典问题&#xff0c;大家是否已经学会了呢&#xff1f;接下来小编和大家学习最后一个经典问题——最小费用最大流问题。 最小费用最大流问题是经济学和管理学中的一类典型问题。在一个网络中每段路径都有“容量”和“费用”两个限制的…

MOS管驱动电流计算以及分立器件驱动电路

自记&#xff1a; 1.先根据mos数据手册查找参数&#xff0c;计算电流&#xff1b; 2.分立器件驱动电路图&#xff1b; 3.分立器件选择 仔细学&#xff0c;能看懂&#xff01; 1.计算电流&#xff1a; 2.分立器件驱动电流&#xff1a;两种&#xff0c;第一种反向&#xff0c…

什么是TestNG以及如何创建testng.xml文件?

目录 什么是TestNG&#xff1f; 如何创建testng.xml文件 手动创建testng.xml 通过testng.xml运行整个包 通过testng.xml运行类 使用Eclipse创建testng.xml 本文将讨论TestNG以及如何通过执行testng.xml文件在TestNG中运行第一个测试用例。 什么是TestNG&#xff1f; Te…

线性表小结

线性表小结 单链表、循环链表和双向链表的时间效率比较 顺序表和链表的比较

强化学习11——DQN算法

DQN算法的全称为&#xff0c;Deep Q-Network&#xff0c;即在Q-learning算法的基础上引用深度神经网络来近似动作函数 Q ( s , a ) Q(s,a) Q(s,a) 。对于传统的Q-learning&#xff0c;当状态或动作数量特别大的时候&#xff0c;如处理一张图片&#xff0c;假设为 210 160 3 …

加密经济学:Web3时代的新经济模型

随着Web3技术的迅猛发展&#xff0c;我们正迈入一个全新的数字经济时代。加密经济学作为这一时代的核心&#xff0c;不仅在数字货币领域崭露头角&#xff0c;更是重新定义了传统经济模型&#xff0c;为我们开启了一个充满创新和机遇的新纪元。 1. 去中心化的经济体系 Web3时代…

7.3 CONSTANT MEMORY AND CACHING

掩模数组M在卷积中的使用方式有三个有趣的属性。首先&#xff0c;M阵列的大小通常很小。大多数卷积掩模在每个维度上都少于10个元素。即使在3D卷积的情况下&#xff0c;掩码通常也只包含少于1000个元素。其次&#xff0c;在内核执行过程中&#xff0c;M的内容不会改变。第三&am…

启动Vue项目,报错:‘vue-cli-service‘ 不是内部或外部命令,也不是可运行的程序

前言&#xff1a; 最近在打开一个Vue项目的时候&#xff0c;打开之后输入命令行&#xff1a;npm run serve之后发现&#xff0c;报错&#xff1a;vue-cli-service 不是内部或外部命令&#xff0c;也不是可运行的程序&#xff0c;以下是解决方案&#xff1a; 报错图片截图&…

HNU-算法设计与分析-实验3

算法设计与分析实验3 计科210X 甘晴void 202108010XXX 目录 文章目录 算法设计与分析<br>实验31 用Dijkstra贪心算法求解单源最短路径问题问题重述证明模板&#xff1a;Dijkstra算法代码验证算法分析 1【扩展】 使用堆优化的Dijkstra原因代码算法分析验证 2 回溯法求解…

运筹说 第98期|无约束极值问题

上一期我们一起学习了关于非线性规划问题的一维搜索方法的相关内容&#xff0c;本期小编将带大家学习非线性规划的无约束极值问题。 下面&#xff0c;让我们从实际问题出发&#xff0c;学习无约束极值问题吧&#xff01; 一、问题描述及求解原理 1 无约束极值问题的定义 无约…

ArkUI-X跨平台已至,何需其它!

运行环境 DevEco Studio&#xff1a;4.0Release OpenHarmony SDK API10 开发板&#xff1a;润和DAYU200 自从写了一篇ArkUI-X跨平台的文章之后&#xff0c;好多人都说对这个项目十分关注。 那么今天我们就来完整的梳理一下这个项目。 1、ArkUI-X 我们之前可能更多接触的…

登录验证

目录 会话技术 Cookie Session JWT JWT生成 JWT校验 会话技术 会话 打开浏览器&#xff0c;访问web服务器的资源&#xff0c;会话建立&#xff0c;直到有一方断开连接&#xff0c;会话结束。在一次会话中可以包含多次请求与响应 会话跟踪 一种维护浏览器的方法 服务器需要…

性能测试jmeter

选的这些怎么添加 在一个列表里面 方法调用${__time(YMD)} 两个下划线&#xff0c;后跟函数名&#xff0c;小括号内是输入参数&#xff0c;整个用大括号包裹。 注意POST一定要在消息体数据里面写,不能再参数里面 否则报错:loginOut,没cookie等