Beispiel für eine SignalR Console-App

84

Gibt es ein kleines Beispiel für eine Konsole oder Winform-App, die signalR verwendet, um eine Nachricht an einen .net-Hub zu senden? Ich habe die .net-Beispiele ausprobiert und mir das Wiki angesehen, aber für mich ist die Beziehung zwischen Hub (.net) und Client (Konsolen-App) nicht sinnvoll (ich konnte kein Beispiel dafür finden). Benötigt die App nur die Adresse und den Namen des Hubs, um eine Verbindung herzustellen?

Wenn jemand einen kleinen Code bereitstellen könnte, der zeigt, wie die App eine Verbindung zu einem Hub herstellt und "Hello World" sendet oder etwas, das der .net-Hub empfängt?

PS. Ich habe ein Standard-Hub-Chat-Beispiel, das gut funktioniert. Wenn ich versuche, ihm einen Hub-Namen in Cs zuzuweisen, funktioniert es nicht mehr, dh [Hub-Name ("Test")]. Kennen Sie den Grund dafür?

Vielen Dank.

Aktueller Konsolen-App-Code.

static void Main(string[] args)
{
    //Set connection
    var connection = new HubConnection("http://localhost:41627/");
    //Make proxy to hub based on hub name on server
    var myHub = connection.CreateProxy("chat");
    //Start connection
    connection.Start().ContinueWith(task =>
    {
        if (task.IsFaulted)
        {
            Console.WriteLine("There was an error opening the connection:{0}", task.Exception.GetBaseException());
        }
        else
        {
            Console.WriteLine("Connected");
        }
    }).Wait();

    //connection.StateChanged += connection_StateChanged;

    myHub.Invoke("Send", "HELLO World ").ContinueWith(task => {
        if(task.IsFaulted)
        {
            Console.WriteLine("There was an error calling send: {0}",task.Exception.GetBaseException());
        }
        else
        {
            Console.WriteLine("Send Complete.");
        }
    });
 }

Hub-Server. (anderer Projektarbeitsbereich)

public class Chat : Hub
{
    public void Send(string message)
    {
        // Call the addMessage method on all clients
        Clients.addMessage(message);
    }
}

Das Info-Wiki hierfür ist http://www.asp.net/signalr/overview/signalr-20/hubs-api/hubs-api-guide-net-client

user685590
quelle
OK, eigentlich hat das tatsächlich funktioniert, nur weil ich das gleiche Ergebnis erhalten habe, habe ich nur einige Haltepunkte hinzugefügt und Console.ReadLine (); Am Ende. Whoop!.
user685590

Antworten:

109

Zunächst sollten Sie SignalR.Host.Self in der Serveranwendung und SignalR.Client in Ihrer Clientanwendung per Nuget installieren:

PM> Install-Package SignalR.Hosting.Self -Version 0.5.2

PM> Installationspaket Microsoft.AspNet.SignalR.Client

Fügen Sie dann den folgenden Code zu Ihren Projekten hinzu;)

(Führen Sie die Projekte als Administrator aus.)

Serverkonsolen-App:

using System;
using SignalR.Hubs;

namespace SignalR.Hosting.Self.Samples {
    class Program {
        static void Main(string[] args) {
            string url = "http://127.0.0.1:8088/";
            var server = new Server(url);

            // Map the default hub url (/signalr)
            server.MapHubs();

            // Start the server
            server.Start();

            Console.WriteLine("Server running on {0}", url);

            // Keep going until somebody hits 'x'
            while (true) {
                ConsoleKeyInfo ki = Console.ReadKey(true);
                if (ki.Key == ConsoleKey.X) {
                    break;
                }
            }
        }

        [HubName("CustomHub")]
        public class MyHub : Hub {
            public string Send(string message) {
                return message;
            }

            public void DoSomething(string param) {
                Clients.addMessage(param);
            }
        }
    }
}

Client-Konsolen-App:

using System;
using SignalR.Client.Hubs;

namespace SignalRConsoleApp {
    internal class Program {
        private static void Main(string[] args) {
            //Set connection
            var connection = new HubConnection("http://127.0.0.1:8088/");
            //Make proxy to hub based on hub name on server
            var myHub = connection.CreateHubProxy("CustomHub");
            //Start connection

            connection.Start().ContinueWith(task => {
                if (task.IsFaulted) {
                    Console.WriteLine("There was an error opening the connection:{0}",
                                      task.Exception.GetBaseException());
                } else {
                    Console.WriteLine("Connected");
                }

            }).Wait();

            myHub.Invoke<string>("Send", "HELLO World ").ContinueWith(task => {
                if (task.IsFaulted) {
                    Console.WriteLine("There was an error calling send: {0}",
                                      task.Exception.GetBaseException());
                } else {
                    Console.WriteLine(task.Result);
                }
            });

            myHub.On<string>("addMessage", param => {
                Console.WriteLine(param);
            });

            myHub.Invoke<string>("DoSomething", "I'm doing something!!!").Wait();


            Console.Read();
            connection.Stop();
        }
    }
}
Mehrdad Bahrainy
quelle
Sie können den obigen Code in der Windows-Anwendung verwenden, aber ist er wirklich notwendig?! Ich bin nicht sicher, was du meinst, du kannst in Windows auf andere Weise benachrichtigen.
Mehrdad Bahrainy
1
Der Client arbeitet mit Server 0.5.2 bis 1.0.0-alpha2, z. B. Install-Package Microsoft.AspNet.SignalR.Client -version 1.0.0-alpha2 nuget.org/packages/Microsoft.AspNet.SignalR.Client/1.0.0-alpha2 (Code- und SignalR-Versionen sollten mit .net 4.0 unter Verwendung von VS2010 SP1 funktionieren) haben versucht herauszufinden, warum ich es nicht zum Laufen bringen konnte, und schließlich den Client mit frühen SignalR-Versionen ausprobiert.
Nick Giles
nett, wirklich hilfreich
Dika Arta Karunia
4
Beachten Sie, dass Sie die Ereignis-Listener (die .On<T>()Methodenaufrufe) hinzufügen müssen, bevor Sie die connection.Start()Methode aufrufen .
Nicolocodev
Es verdient, diesen Link bereitzustellen: docs.microsoft.com/en-us/aspnet/signalr/overview/…
Mohammed Noureldin
24

Beispiel für SignalR 2.2.1 (Mai 2017)

Server

Installationspaket Microsoft.AspNet.SignalR.SelfHost -Version 2.2.1

[assembly: OwinStartup(typeof(Program.Startup))]
namespace ConsoleApplication116_SignalRServer
{
    class Program
    {
        static IDisposable SignalR;

        static void Main(string[] args)
        {
            string url = "http://127.0.0.1:8088";
            SignalR = WebApp.Start(url);

            Console.ReadKey();
        }

        public class Startup
        {
            public void Configuration(IAppBuilder app)
            {
                app.UseCors(CorsOptions.AllowAll);

                /*  CAMEL CASE & JSON DATE FORMATTING
                 use SignalRContractResolver from
                /programming/30005575/signalr-use-camel-case

                var settings = new JsonSerializerSettings()
                {
                    DateFormatHandling = DateFormatHandling.IsoDateFormat,
                    DateTimeZoneHandling = DateTimeZoneHandling.Utc
                };

                settings.ContractResolver = new SignalRContractResolver();
                var serializer = JsonSerializer.Create(settings);
                  
               GlobalHost.DependencyResolver.Register(typeof(JsonSerializer),  () => serializer);                
            
                 */

                app.MapSignalR();
            }
        }

        [HubName("MyHub")]
        public class MyHub : Hub
        {
            public void Send(string name, string message)
            {
                Clients.All.addMessage(name, message);
            }
        }
    }
}

Klient

(fast das gleiche wie Mehrdad Bahrainy Antwort)

Installationspaket Microsoft.AspNet.SignalR.Client -Version 2.2.1

namespace ConsoleApplication116_SignalRClient
{
    class Program
    {
        private static void Main(string[] args)
        {
            var connection = new HubConnection("http://127.0.0.1:8088/");
            var myHub = connection.CreateHubProxy("MyHub");

            Console.WriteLine("Enter your name");    
            string name = Console.ReadLine();

            connection.Start().ContinueWith(task => {
                if (task.IsFaulted)
                {
                    Console.WriteLine("There was an error opening the connection:{0}", task.Exception.GetBaseException());
                }
                else
                {
                    Console.WriteLine("Connected");

                    myHub.On<string, string>("addMessage", (s1, s2) => {
                        Console.WriteLine(s1 + ": " + s2);
                    });

                    while (true)
                    {
                        Console.WriteLine("Please Enter Message");
                        string message = Console.ReadLine();

                        if (string.IsNullOrEmpty(message))
                        {
                            break;
                        }

                        myHub.Invoke<string>("Send", name, message).ContinueWith(task1 => {
                            if (task1.IsFaulted)
                            {
                                Console.WriteLine("There was an error calling send: {0}", task1.Exception.GetBaseException());
                            }
                            else
                            {
                                Console.WriteLine(task1.Result);
                            }
                        });
                    }
                }

            }).Wait();

            Console.Read();
            connection.Stop();
        }
    }
}
ADOConnection
quelle
4
Funktioniert bei mir nicht ... löst bei WebApp.Start () eine Null-Ref-Ausnahme aus
Fᴀʀʜᴀɴ Aɴᴀᴍ
Wie kann ich die Nachricht im Hub sehen? ist das möglich?
Kob_24
wie man das in dotnet core macht :(?
Kob_24
@ Kob_24 siehe Klasse MyHub, Methode Senden - dort können Sie Nachrichten sehen. Für Dotnet Core funktioniert es fast genauso
ADOConnection
2
@XarisFytrakis super einfach, ich habe die Antwort aktualisiert, Sie benötigen Vertragsauflöser von hier: stackoverflow.com/questions/30005575/signalr-use-camel-case sowie DateFormatHandling = DateFormatHandling.IsoDateFormat, wenn Sie es von js verbrauchen.
ADOConnection
2

Dies ist für dot net core 2.1 - nach vielem Ausprobieren habe ich es endlich geschafft, einwandfrei zu funktionieren:

var url = "Hub URL goes here";

var connection = new HubConnectionBuilder()
    .WithUrl($"{url}")
    .WithAutomaticReconnect() //I don't think this is totally required, but can't hurt either
    .Build();

//Start the connection
var t = connection.StartAsync();

//Wait for the connection to complete
t.Wait();

//Make your call - but in this case don't wait for a response 
//if your goal is to set it and forget it
await connection.InvokeAsync("SendMessage", "User-Server", "Message from the server");

Dieser Code stammt vom Chat-Client eines typischen armen SignalR-Mannes. Das Problem, auf das ich und anscheinend viele andere Menschen gestoßen sind, besteht darin, eine Verbindung herzustellen, bevor versucht wird, eine Nachricht an den Hub zu senden. Dies ist wichtig, daher ist es wichtig, auf den Abschluss der asynchronen Aufgabe zu warten. Dies bedeutet, dass wir sie synchronisieren, indem wir auf den Abschluss der Aufgabe warten.

Legasthenikeraboko
quelle
Sie könnten den Start tatsächlich
verketten