使用 SignalR 的 Angular 2 TypeScript

Posted

技术标签:

【中文标题】使用 SignalR 的 Angular 2 TypeScript【英文标题】:Angular 2 TypeScript using SignalR 【发布时间】:2017-05-13 17:06:16 【问题描述】:

我正在尝试设置一个 Angular 2 应用程序以使用 Microsoft 的 SignalR。我一直在关注this tutorial,虽然这很好,但我不喜欢通过 index.html 文件中的脚本标签将 jQuery 和 SignalR 加载到应用程序中的事实,以及这两个库不使用它们各自的事实类型定义。

因此,考虑到这一点,我一直在尝试使用节点模块和相应的类型定义在我的应用程序中包含 jQuery 和 SignalR。我已经通过 Microsoft 的 TypeSearch 搜索了要使用的正确类型定义文件。

由于 SignalR 对 jQuery 的依赖,我只在我的应用程序中包含 jQuery。

jQuery

我首先开始在我的应用程序中安装 jQuery 模块,我还必须在 Webpack 配置中添加它。设置完成后,由于量角器,我正面临“冲突”问题。这在Aurelia JS Rocks' website 上进行了描述。虽然它建议卸载量角器类型,但我现在尝试了另一种解决方案described in this answer。我不知道这是否是最好的解决方案。

信号R

关于 SignalR,我有点卡住了 - 到目前为止,似乎没有为 SignalR 提供“官方”节点模块。我不确定是否应该通过下载文件并将其包含在我的应用程序中来包含 Microsoft 的 SignalR javascript 库。

问题是我已经安装了 SignalR 的类型定义。但是现在我不确定如何实际使用 SignalR,因为当我输入 $jQuery 时,我并没有被建议 .connections ——这是有道理的,因为这不是 jQuery 库的一部分。

我确定我可能会误解有关“设置”的内容。在 Angular2 TypeScript 应用程序中使用 SignalR 的最佳方式是什么?

【问题讨论】:

你知道HUB吗? 问题不在于 HUB .. 正如我在我的问题“我已经安装了 SignalR 的类型定义”中提到的那样。但是现在我不确定如何实际使用 SignalR,因为当我输入$jQuery 不建议我例如 .connections" // 声明一个代理来引用集线器。聊天 = $.connection.YourHUBNAME;创建一个你可以使用的代理 【参考方案1】:

这是您可以使用的启动代码。

C#

//create an interface that contains definition of client side methods
public interface IClient

    void messageReceived(string msg);


//create your Hub class that contains implementation of client methods
public class ChatHub : Hub<IClient>

    public void sendMessage(string msg)
    
        //log the incoming message here to confirm that its received

        //send back same message with DateTime
        Clients.All.messageReceived("Message received at: " + DateTime.Now.ToString());
    

HTML

添加对jQuerysignalRscript文件的引用。

<script src="path/to/jquery.min.js"></script>
<script src="path/to/jquery.signalR.min.js"></script>

<!--this is the default path where SignalR generates its JS files so you don't need to change it.-->
<script src="~/signalr/hubs"></script>

JS

您需要为 SignalR 和 jQuery 安装 TypeScript 定义文件。如果您使用TypeScript 2,则无需在使用时添加对index.d.ts 文件的引用。只需使用以下命令安装类型。

npm install --save @types/jquery
npm install --save @types/signalr

完成所有设置后,您可以编写一个简单的TypeScript class 来处理发送和接收消息的逻辑。

export class MessageService 
    //signalR connection reference
    private connection: SignalR;
    
    //signalR proxy reference
    private proxy: SignalR.Hub.Proxy;


    constructor() 
        //initialize connection
        this.connection = $.connection;
        
        //to create proxy give your hub class name as parameter. IMPORTANT: notice that I followed camel casing in giving class name
        this.proxy = $.connection.hub.createHubProxy('chatHub');

        //define a callback method for proxy
        this.proxy.on('messageReceived', (latestMsg) => this.onMessageReceived(latestMsg));

        this.connection.hub.start();
    
    
    private onMessageReceived(latestMsg: string) 
        console.log('New message received: ' + latestMsg);
    

    //method for sending message
    broadcastMessage(msg: string) 
        //invoke method by its name using proxy 
        this.proxy.invoke('sendMessage', msg);
    

我正在使用上面的代码,显然已根据我的需要进行了修改,并且运行良好。


更新 1:这是一个相当古老的答案,从那时起情况发生了很大变化。使用npm 安装jQuerySignalR,然后使用angular.json 文件加载它们,如下所示:

1- 安装npm install jquery signalr

2- 加载angular.json -&gt; projects -&gt; your-app -&gt; architect -&gt; build -&gt; options

scripts: [
  "./node_modules/jquery/dist/jquery.min.js", 
  "./node_modules/signalr/jquery.signalR.min.js"
]

感谢Robert's answer 提供更新。

【讨论】:

这很有帮助!非常感谢......有一件事是即使我使用的是 TypeScript 2.0.9,我似乎仍然必须使用对 index.d.ts 文件的引用。例如,如果没有参考,当我尝试调用 SignalR 时会出错。 @DanielGrima:听起来很奇怪,不客气。如果这解决了您的问题,请将其标记为答案,以便将来对其他人有所帮助。 是的,这很奇怪。我会进一步调查,看看会发生什么 我设法解决了类型定义引用的问题...我必须在 types 文件的 types 数组中添加 "signalr",一旦我这样做了,问题就是解决了:)不确定它是否应该自动添加..无论如何现在一切都好:) 我收到此错误:类型“SignalR”不可分配给类型“连接”。 “SignalR”类型中缺少属性“代理”。对于 this.connection = $.connection;有任何想法吗?我已经通过 npm 安装了类型。【参考方案2】:

@Syed Ali Taqi 的回答基本上还可以,但并不完美(如果您错过了配置 ts 编译器,甚至无法正常工作)。这是我最新 Angular 的步骤(截至我写作时的版本 8):

    安装 jquery 和 signalr 运行时库:npm install jquery signalr

    通过配置 angular.json 告诉 Angular 在运行时加载库,就像它们在 &lt;script&gt;&lt;/script&gt; 标记中一样:

    projects:
      <your-app>:
        architect:
          build:
            options:
              ...
              scripts: [
                "./node_modules/jquery/dist/jquery.min.js",
                "./node_modules/signalr/jquery.signalR.min.js"
              ]
          ...
          test:
            options:
              ...
              scripts: [
                "./node_modules/jquery/dist/jquery.min.js",
                "./node_modules/signalr/jquery.signalR.min.js"
              ]
    

    为 jquery 和 signalr 安装类型,以便 ts 编译器可以识别它们:npm install @types/jquery @types/signalr --save-dev

    通过编辑 tsconfig.app.json 和 tsconfig.spec.json 的 types 部分,告诉 ts 编译器加载类型默认
    compilerOptions:
      types: [..., "jquery", "signalr"]
    

好的,全部完成!祝 SignalR 编码愉快!

let conn = $.hubConnection("<base-path>");
let proxy = conn.createHubProxy("<some-hub>");
...

注意:永远不要像https://angular.io/guide/using-libraries#using-runtime-global-libraries-inside-your-app所说的那样,在你的代码中显式地尝试从jqueryimport ...

有关 angular.json 配置的更多信息,请参阅https://angular.io/guide/workspace-config

【讨论】:

以上是关于使用 SignalR 的 Angular 2 TypeScript的主要内容,如果未能解决你的问题,请参考以下文章

来自 Angular 的 SignalR Core 中的 JWT 身份验证

ASP.NET Core Angular - 根据登录用户发送不同的 SignalR 消息

SignalR Asp.netcore 和 angular(WebSocket 未处于 OPEN 状态)断开信号R.HttpTransportType.WebSockets

使用 SIGNAL R 的 Angular 7 和 ASP.NET Core 2.2 的 CORS 策略问题

在 SignalR 的事件处理程序中访问属性时始终未定义

SignalR 授权无法在带有 Identity Server 的 asp.net core angular SPA 中开箱即用