Notification Hub Delivery failure C# - c#

I have two notification hub clients (nodejs and C#), both used for pushing messages into a hub.
The Node client sends perfectly fine, yet the C# client completes with no message being sent.
Below are the snippets for the used in each client.
C#
NotificationHubClient hub = NotificationHubClient.CreateClientFromConnectionString("<Connection String>", "<Hub Name>");
var notice = #"{'aps':{'alert':'Notification Hub test notification'}}";
var result = await hub.SendAppleNativeNotificationAsync(notice, "<tag>");
Console.WriteLine(result.State);
NodeJS
var azure = require('azure');
var notificationHubService = azure.createNotificationHubService('<Hub Name>','<Connection String>')
var notice = "{'aps':{'alert':'Notification Hub test notification'}}"
notificationHubService.apns.send("<tag>", notice, function(error, res){
console.log(res);
});
Both work fine when sending Android notifications and messages sent directly from the Azure portal Test feature are fine.
Any assistance would be greatly appreciated.

Duncan,
I think the issue is because your payload is malformed as you are using single quotes. Try the following:
var notice = "{\"aps\":{\"alert\":\"Notification Hub test notification\"}}";

You can try to use the EnableTestSend feature and look at the NotificationOutcome property for the detailed error message. This will send a test send message to 10 devices.
bool enableTestSend = true;
NotificationHubClient hub = NotificationHubClient.CreateClientFromConnectionString(connString, hubName, enableTestSend);
var outcome = await hub.SendWindowsNativeNotificationAsync(toast);
Console.WriteLine(outcome.State);
foreach (RegistrationResult result in outcome.Results)
{
Console.WriteLine(result.ApplicationPlatform + "\n" + result.RegistrationId + "\n" + result.Outcome);
}

TLDR - No '' (single quotes) allowed! Payload must containt alert key
Not a very exciting solution but...
If the notification payload contains single quotes even in a string literal the Notification hub will en-queue it without a malformed exception but when it reaches the APNS it will not be delivered as the payload is invalid according to them.
If the notification payload doesn't have alert key present it will also be en-queued but not delivered by the APNS

As already mentioned in my colleagues answers, you need to use double quotes in C# as a first step.
Second, you also need to escape the json characters:
Your payload should look like this:
var notice = "{{\"aps\":{{\"alert\":\"Notification Hub test notification\"}}}}";
Basically you escape the json braces { } by adding additional ones {{ }}.
This will send a valid json payload to the SendAppleNativeNotificationAsync() method. The payload now sent looks like this:
{"aps":{"alert":"Notification Hub test notification"}} (which is the correct notification format on iOS)
Here are the valid json payloads for iOS from the Apple Developer webpage.
You could always test if the json you are sending is a valid notification payload by using the 'Test Send' functionality in the Azure Notification Hub you are using.

Related

Can I verify if message is sent successfully using Response<SendReceipt> in Azure Storage Queue

I am using the Azure Storage Queue Client to send base 64 encoded string messages. A very straight forward usage. I have the following code snippet:
var options = new QueueClientOptions
{
MessageEncoding = QueueMessageEncoding.Base64
};
var _queueClient = new QueueClient(settings.Value.ConnectionString, settings.Value.Name, options);
var message = JsonConvert.SerializeObject(messageObject, jsonSetting);
_queueClient.SendMessageAsync(message);
I know that SendMessageAsync( . . .) returns Response<SendReceipt> how do I use that to verify if a message is sent successfully or not ?
SendReceipt has MessageId and InsetionTime properties but the documentation does not specify what happens to these properties if message does not get sent. Does the queue simply returns null receipt or an object with default values ?
When you try to send a message to a queue using SendMessageAsync and if for some reason message is not sent, an exception is raised. You will not receive anything in the Response<SendReceipt>.
You will need to wrap your await _queueClient.SendMessageAsync(message); in a try/catch block. If no exception is raised that would mean the message is sent successfully.

Twilio Error - 12200 - Schema validation warning - Content is not allowed in prolog

I have a webHook receiver that listens to Twilio POST. Scenario: SMS message is sent to my Twilio number, Twilio does POST to the webHook receiver, webHook processes the request (works as expected) and finally WebHook returns back a response object Twilio.TwiML.MessagingResponse. The problem is I'm receiving a warning in the Twilio Debugger with message "Content is not allowed in prolog." The warning shows in the REQUEST section of the Request Inspector and didn't know what to do about it.
screenshot of error/warn message
Thanks all for looking into this. Answer by #marcos-placona in here made me revisit the webHook return type. Sure enough the return type needs to be a TwiML formatted XML. That led to the discovery of the overloaded ToString() extension method.
public string ToString([System.Xml.Linq.SaveOptions formattingOptions = System.Xml.Linq.SaveOptions.None])
Member of Twilio.TwiML.TwiML
Summary:
Generate XML string from TwiML object
Parameters:
formattingOptions: Change generated string format.
for this to work, [System.Xml.Linq] needs to be referenced.
using Twilio.TwiML;
var twilioResponse = new MessagingResponse();
var message = new Twilio.TwiML.Messaging.Message("Thanks for your response.");
twilioResponse.Append(message);
return twilioResponse.ToString();
Hope this helps someone.

How to remove #strin3http//schemas.microsoft.com/2003/10/Serialization/� received from service bus queue received in python script?

I have set the output of Azure stream analytics job to service bus queue which sends the data in JSON serialized format. When I receive the queue message in python script, along with the data in curly braces, I get #strin3http//schemas.microsoft.com/2003/10/Serialization/� appended in front. I am not able to trim it as the received message is not being recognized as either a string or a message. Because of this I cannot de-serialize the data.
This TechNet article suggests the following code:
// Get indices of actual message
var start = jsonString.IndexOf("{");
var end = jsonString.LastIndexOf("}") + 1;
var length = end - start;
// Get actual message
string cleandJsonString = jsonString.Substring(start, length);
Pretty primitive but whatever works I suppose...
The issue was similiar with the SO thread Interoperability Azure Service Bus Message Queue Messages.
Per my experience, the data from Azure Stream Analytics to Service Bus was sent via AMQP protocol, but the protocol of receiving the data in Python is HTTP. The excess content was generated by AMQP during transmission.
Assumption that receiving the message via the code below, please see https://azure.microsoft.com/en-us/documentation/articles/service-bus-python-how-to-use-queues/#receive-messages-from-a-queue. The function receive_queue_message with the False value of the argument peek_lock wrapped the REST API Receive and Delete Message (Destructive Read).
msg = bus_service.receive_queue_message('taskqueue', peek_lock=False)
print(msg.body)
According to the source code of Azure Service Bus SDK for Python include the functions receive_queue_message, read_delete_queue_message and _create_message, I think you can directly remove the excess content from the msg.body using the string common function lstrip or strip.
I ran into this issue as well. The previous answers are only workarounds and do not fix the root cause of this issue. The problem you are encountering is likely due to your Stream Analytics compatibility level. Compatibility level 1.0 uses an XML serializer producing the XML tag you are seeing. Compatibility level 1.1 "fixes" this issue.
See my previous answer here: https://stackoverflow.com/a/49307178/263139.
I had the same issue but in a .net solution. I was writing a service which sends data to a queue, and on the other hand, I was writing a service which gets that data from the queue. I've tried to send a JSON, like this:
var documentMessage = new DocumentMessage();
var json = JsonConvert.SerializeObject(documentMessage);
BrokeredMessage message = new BrokeredMessage(json);
await _client.SendAsync(message);
In this second service I was getting the JSON but with this prefix:
#strin3http//schemas.microsoft.com/2003/10/Serialization/�
I solved this problem by add DataContractJsonSerializer like that:
var documentMessage = new DocumentMessage();
var serializer = new DataContractJsonSerializer(typeof(DocumentMessage));
BrokeredMessage message = new BrokeredMessage(documentMessage , serializer);
await _client.SendAsync(message);
If you want to solve the problem in that way, you will have to add Data Attributes from System.Runtime.Serialization to the model:
[DataContract]
public class DocumentMessage
{
[DataMember]
public string Property1 { get; private set; }
[DataMember]
public string Property2 { get; private set; }
}
When using Microsoft.ServiceBus nuget package, replace
message.GetBody<Stream>();
with
message.GetBody<string>();

Azure Service Bus Queue sending a message in NodeJs to .NET client

I am sending a message from a C# worker to the Queue, then I am getting it on another C# worker and call
string body = message.GetBody<string>();
This works and I later de-serialize the string/JSON message.
Now I am trying to send the same message from NodeJS in form of a JSON message. When I try to receive it and
string body = message.GetBody<string>();
call this I get an exception saying the input is in incorrect format.
My message object on NodeJS looks like this
{
body: JSON.stringify(message)
}
Any ideas?
Got it fixed!
By default the .NET Azure Queue library uses a DataContractSerializer and a binary XmlDictionaryWriter to serialize the string message when using
new BrokeredMessage("my message");
So instead you need to use this
new BrokeredMessage(new MemoryStream(Encoding.UTF8.GetBytes("my message")), true);
and to read the message in C# you need to use
string body = new StreamReader(message.GetBody<Stream>(), Encoding.UTF8).ReadToEnd();
I also stopped wrapping my JSON.stringify message in an object and pass it directly to the sendQueueMessage. The send message code looks like this now:
serviceBusService.sendQueueMessage('my_queue', JSON.stringify("my message"), function(error){});
JSON.stringify outputs a UTF8 string so it is fully compatible with the C# code.

Telegram C# example send message

I can't find an example of sending message by telegram protocol from C#. I tried to use this but failed.
Can you give me any examples?
TLSharp is basic implementation of Telegram API on C#. See it here https://github.com/sochix/TLSharp
You can use the WTelegramClient library to connect to Telegram Client API protocol (as a user, not a bot)
The library is very complete but also very easy to use. Follow the README on GitHub for an easy introduction.
To send a message to someone can be as simple as:
using TL;
using var client = new WTelegram.Client(); // or Client(Environment.GetEnvironmentVariable)
await client.LoginUserIfNeeded();
var result = await client.Contacts_ResolveUsername("USERNAME");
await client.SendMessageAsync(result.User, "Hello");
//or by phone number:
//var result = await client.Contacts_ImportContacts(new[] { new InputPhoneContact { phone = "+PHONENUMBER" } });
//client.SendMessageAsync(result.users[result.imported[0].user_id], "Hello");
For my bot I use Telegram.Bot nuget package. Full sample code is here.
Here is example of sending message in reply to incoming message.
// create bot instance
var bot = new TelegramBotClient("YourApiToken");
// test your api configured correctly
var me = await bot.GetMeAsync();
Console.WriteLine($"{me.Username} started");
// start listening for incoming messages
while (true)
{
//get incoming messages
var updates = await bot.GetUpdatesAsync(offset);
foreach (var update in updates)
{
// send response to incoming message
await bot.SendTextMessageAsync(message.Chat.Id,"The Matrix has you...");
}
}
The simplest way is to send http request directly to the Telegram BOT API as url string, you may test those url strings even in your browser, please see details in my another answer here:
https://stackoverflow.com/a/57341990/11687179
at the first step you have to generate a bot in botfather then use the code in bellow in C#
private void SendMessage(string msg)
{
string url = "https://api.telegram.org/{botid}:{botkey}/sendMessage?chat_id={#ChanalName}&text={0}";
WebClient Client = new WebClient();
/// If you need to use proxy
if (Program.UseProxy)
{
/// proxy elements are variable in Program.cs
Client.Proxy = new WebProxy(Program.ProxyUrl, Program.ProxyPort);
Client.Proxy.Credentials = new NetworkCredential("hjolany", "klojorasic");
}
Client.DownloadString(string.Format(url, msg));
}));
}
Telegram has an official API that can do exactly what you need, you will have to look into http requests though..
Here is the documentation on sending a message:
Function
messages.sendMessage
Params
peer InputPeer User or chat where a message will be sent
message string Message text
random_id long Unique client message ID required to prevent message resending
Query example
(messages.sendMessage (inputPeerSelf) "Hello, me!" 12345678901)
Return errors
Code Type Description
400 BAD_REQUEST PEER_ID_INVALID Invalid peer
400 BAD_REQUEST MESSAGE_EMPTY Empty or invalid UTF8 message was sent
400 BAD_REQUEST MESSAGE_TOO_LONG Message was too long.
Current maximum length is 4096 UTF8 characters
For the full documentation go here.

Categories