azurewhatsappazure-communication-services

Azure communication service when using WhatsApp template throws an exception


I have an azure communication service where whatsapp channel is connected with the template also available. The template looks like this

The inputs supplied to the API are invalid Status: 400 (Bad Request) ErrorCode: ModelValidationError

Content: {"error":{"code":"ModelValidationError","message":"The inputs supplied to the API are invalid","details":[{"code":"ModelValidationError","message":"notificationContent: The notificationContent field is required.","target":"notificationContent"},{"code":"ModelValidationError","message":"buttons[0].subType: Error converting value "otpcode" to type 'Microsoft.Azure.Communication.CrossPlatformMessages.Contract.Model.V3.Notifications.Requests.WhatsAppMessageButtonSubType'. Path 'buttons[0].subType', line 1, position 193.","target":"buttons[0].subType"}]}}

Headers: Date: Fri, 14 Mar 2025 22:26:04 GMT Transfer-Encoding: chunked Connection: keep-alive Request-Context: REDACTED MS-CV: o9PMlhHpZ0OyQzokOm+uDQ.0 Strict-Transport-Security: REDACTED Repeatability-Result: REDACTED X-Processing-Time: REDACTED x-azure-ref: REDACTED X-Cache: REDACTED Content-Type: application/json; charset=utf-8

The whatsapp template has authentication template and which has a code button. The Azure communication service communicates with WhatsApp with the following code

      var channelRegistrationId = new Guid(options.Value.ChannelRegistrationId);
 var recipientList = new List<string> { phoneNumber };
 var value1 = new MessageTemplateText("otpcode", otpCode);
 var bindings = new WhatsAppMessageTemplateBindings();
  bindings.Body.Add(new(value1.Name));
 bindings.Buttons.Add(new WhatsAppMessageTemplateBindingsButton("otpcode", otpCode));
 var template = new MessageTemplate(options.Value.PhoneNumberValidationTemplateName, "en_us");
 template.Values.Add(value1);
 template.Bindings = bindings;           
 var content = new TemplateNotificationContent(channelRegistrationId, recipientList, template);
 Response<SendMessageResult> response = await notificationMessagesClient.SendAsync(content);

But when running it i get the following exception

> Given request contains a parameter for WhatsApp which was invalid. This includes channel ID and template parameters.
Status: 400 (Bad Request)
ErrorCode: BadRequest

Content:
{"error":{"code":"BadRequest","message":"Given request contains a parameter for WhatsApp which was invalid. This includes channel ID and template parameters.","innererror":{"code":"WhatsAppAdminClient+WaErrorCode.InvalidParameter","message":"InvalidParameter: (#131008) Required parameter is missing. buttons: Button at index 0 of type Url requires a parameter"}}}

Solution

  • The API expects a notificationContent field, but it's missing in the request. Without this, Azure rejects the request with a 400 Bad Request (ModelValidationError).

    csharp bindings.Buttons.Add(new WhatsAppMessageTemplateBindingsButton("otpcode", otpCode));

    To this:

    bindings.Buttons.Add(new WhatsAppMessageTemplateBindingsButton(WhatsAppMessageButtonSubType.Url.ToString(), otpCode));
    

    Bellow is to send the WhatsApp OTP message via Azure Communication Services:

    
    using System;
    using System.Collections.Generic;
    using System.Threading.Tasks;
    using Azure;
    using Azure.Communication.Messages;
    using Azure.Communication.Messages.Models.Channels;
    
    namespace WhatsAppAuthOTP
    {
        class Program
        {
            public static async Task Main(string[] args)
            {
                Console.WriteLine("Sending WhatsApp Authentication Template with OTP...\n");
    
                string connectionString = "connection string";
    
                NotificationMessagesClient notificationMessagesClient = new NotificationMessagesClient(connectionString);
    
                var channelRegistrationId = new Guid("c8b57863-73bf-4da3-961a-64d23f59e0c6");
                var recipientList = new List<string> { "+9196" };
    
                string templateName = "phonenumbervalidation";
                string templateLanguage = "en";
                string oneTimePassword = "3516517";
    
                MessageTemplate messageTemplate = new MessageTemplate(templateName, templateLanguage);
                WhatsAppMessageTemplateBindings bindings = new();
    
                var otpBody = new MessageTemplateText(name: "code", text: oneTimePassword);
                bindings.Body.Add(new(otpBody.Name));
    
                var otpButton = new MessageTemplateQuickAction("url")
                {
                    Text = oneTimePassword
                };
                bindings.Buttons.Add(new WhatsAppMessageTemplateBindingsButton(WhatsAppMessageButtonSubType.Url.ToString(), otpButton.Name));
    
    
                messageTemplate.Values.Add(otpBody);
                messageTemplate.Values.Add(otpButton);
                messageTemplate.Bindings = bindings;
                TemplateNotificationContent templateContent = new TemplateNotificationContent(channelRegistrationId, recipientList, messageTemplate);
                Response<SendMessageResult> result = await notificationMessagesClient.SendAsync(templateContent);
    
                PrintResponse(result);
            }
    
            public static void PrintResponse(Response<SendMessageResult> response)
            {
                Console.WriteLine($"Response: {response.GetRawResponse().Status} - {response.GetRawResponse().ReasonPhrase}");
                foreach (var receipt in response.Value.Receipts)
                {
                    Console.WriteLine($"Message ID: {receipt.MessageId}");
                }
            }
        }
    }
    

    Output