I have the following architecture piece that I am trying to test.
My goal is to read data published to Azure API Management through the AzurePubSub using a WebSocket client from my C# Console App. Azure PubSub is another element you are seeing on green that exposes a WebSocket endpoint that I am not going to make public for my clients. As part of Azure Api Management, I can expose it to external clients using a subscription key and my organization URL.
Using code from this repo: azure pubsub examples I was able to tap into the Azure PubSub element directly to read and write data from there. Here is my AzurePubSubSubscriber using the above repo
using System;
using System.Threading.Tasks;
using Azure.Messaging.WebPubSub;
using Websocket.Client;
namespace subscriber
{
class Program
{
static async Task Main(string[] args)
{
var connectionString = "Endpoint=https://pubsub.webpubsub.azure.com;AccessKey=myaccesskey;Version=1.0;";
var hub = "myhub";
// Either generate the URL or fetch it from server or fetch a temp one from the portal
var serviceClient = new WebPubSubServiceClient(connectionString, hub);
var url = serviceClient.GetClientAccessUri();
using (var client = new WebsocketClient(url))
{
// Disable the auto disconnect and reconnect because the sample would like the client to stay online even no data comes in
client.ReconnectTimeout = null;
client.MessageReceived.Subscribe(msg => Console.WriteLine($"Message received: {msg}"));
await client.Start();
Console.WriteLine("Connected.");
Console.Read();
}
}
}
}
Here is my AzurePubSubPublisher
using System.Threading.Tasks;
using Azure;
using Azure.Core;
using Azure.Messaging.WebPubSub;
namespace publisher
{
class Program
{
static async Task Main(string[] args)
{
await Method1();
}
public static async Task Method1()
{
var connectionString = $"Endpoint=https://pubsub.webpubsub.azure.com;AccessKey=myaccesskey;Version=1.0;";
var hub = "myhub";
while (true)
{
Console.WriteLine("Write your message");
var message = Console.ReadLine();
if (string.IsNullOrEmpty(message))
{
return;
}
// Either generate the token or fetch it from server or fetch a temp one from the portal
var serviceClient = new WebPubSubServiceClient(connectionString, hub);
await serviceClient.SendToAllAsync(message);
}
}
}
}
Now when I expose the endpoint through the Azure API Management to consume content from my Console C# App is where I am not receiving data and am not sure what I am missing here.
Here is the C# code I used from my Console App to read data from Azure API Management endpoint:
static async Task Main()
{
await StartWebSocketClient4();
Console.ReadLine();
}
static async Task StartWebSocketClient4()
{
try
{
Console.Write("Connecting....");
var cts = new CancellationTokenSource();
var socket = new ClientWebSocket();
string wsUri = "wss://myorganization.com/sub?subscription-key=ac3529b7619a383dc6ce6e618dbc9b7614a66";
await socket.ConnectAsync(new Uri(wsUri), cts.Token);
Console.WriteLine(socket.State);
await Task.Factory.StartNew(
async () =>
{
var rcvBytes = new byte[1024 * 1024];
var rcvBuffer = new ArraySegment<byte>(rcvBytes);
while (true)
{
WebSocketReceiveResult rcvResult = await socket.ReceiveAsync(rcvBuffer, cts.Token);
byte[] msgBytes = rcvBuffer.Skip(rcvBuffer.Offset).Take(rcvResult.Count).ToArray();
string rcvMsg = Encoding.UTF8.GetString(msgBytes);
Console.WriteLine("Received: {0}", rcvMsg);
}
}, cts.Token, TaskCreationOptions.LongRunning, TaskScheduler.Default);
}
catch(Exception ex)
{
Console.WriteLine(ex.Message);
}
}