如果App Service使用身份验证,则Azure通知中心设备注册失败

时间:2016-11-14 10:09:08

标签: azure azure-web-sites azure-mobile-services azure-notificationhub

我有一个工作的Azure应用服务连接到配置了GCM和APNS的通知中心。它在两个平台上都运行了好几个月。

我现在已经开启了应用服务中的身份验证,并配置了google和facebook。这些也可以很好地工作,并且正确的访问权限适用于简单的表格。

但是,自启用身份验证以来,移动应用程序中的设备注册现已失败。

以下是我在应用服务(NodeJS)上遇到的错误:

System.NullReferenceException: Object reference not set to an instance of an object.
  at Microsoft.Azure.AppService.Push.PushRequestHandler.<HandleCreateOrUpdateInstallationAsync>d__14.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
 at  System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Push.PushRequestHandler.<HandlePushRequestAsync>d__f.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Push.PushModule.<OnPostAuthenticateRequestAsync>d__0.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Authentication.HttpModuleDispatcher.<DispatchAsync>d__13.MoveNext()
2016-11-14T09:43:00  PID[7348] Information Sending response: 500.79 Internal Server Error
2016-11-14T09:43:00  PID[7348] Critical    System.ComponentModel.Win32Exception (0x80004005): An operation was attempted on a nonexistent network connection
at CHttpRequest.ReadEntityBody(Byte[] buffer, Int32 maxLength, Boolean allowAsync, Int32& bytesReceived, Int32& bytesRemaining, Boolean& completionPending)
at Microsoft.Azure.AppService.Authentication.HttpRequestBase.AsyncReadHelper.Read()
at Microsoft.Azure.AppService.Authentication.HttpRequestBase.AsyncReadHelper..ctor(HttpRequestBase request, Int32 maxLength)
at Microsoft.Azure.AppService.Authentication.HttpRequestBase.<ReadRequestContentAsync>d__8.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Push.PushRequestHandler.<HandleCreateOrUpdateInstallationAsync>d__14.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Push.PushRequestHandler.<HandlePushRequestAsync>d__f.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Push.PushModule.<OnPostAuthenticateRequestAsync>d__0.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.AppService.Authentication.HttpModuleDispatcher.<DispatchAsync>d__13.MoveNext()
2016-11-14T09:43:00  PID[7348] Information Sending response: 500.79 Internal Server Error

我能够将通知(使用测试发送和通过我的服务器推送代码)发送到现有注册,我只是无法创建新的注册。

当我关闭身份验证时,它会再次正常工作。

在此身份验证方案中,是否需要在通知中心中手动创建注册?

我不知道自己哪里出错了,所以任何帮助都会非常感激。

3 个答案:

答案 0 :(得分:3)

作为导致问题的RegisterAsync的替代方案;您可以使用HttpClient调用来PUT Notification Hub安装。以下代码将在Android上设置安装,例如:

public async Task RegisterForPushNotifications(MobileServiceClient client)
{
    if (GcmClient.IsRegistered(RootView))
    {
        try
        {
            var registrationId = GcmClient.GetRegistrationId(RootView);
            //var push = client.GetPush();
            //await push.RegisterAsync(registrationId);

            var installation = new DeviceInstallation
            {
                InstallationId = client.InstallationId,
                Platform = "gcm",
                PushChannel = registrationId
            };
            // Set up tags to request
            installation.Tags.Add("topic:Sports");
            // Set up templates to request
            PushTemplate genericTemplate = new PushTemplate
            {
                Body = "{\"data\":{\"message\":\"$(messageParam)\"}}"
            };
            // Register with NH
            var response = await client.InvokeApiAsync<DeviceInstallation, DeviceInstallation>(
                $"/push/installations/{client.InstallationId}",
                installation,
                HttpMethod.Put,
                new Dictionary<string, string>());
        }
        catch (Exception ex)
        {
            Log.Error("DroidPlatformProvider", $"Could not register with NH: {ex.Message}");
        }
    }
    else
    {
        Log.Error("DroidPlatformProvider", $"Not registered with GCM");
    }
}

DeviceInstallation类看起来像这样:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Newtonsoft.Json;

namespace TaskList.Abstractions
{
    public class DeviceInstallation
    {
        public DeviceInstallation()
        {
            Tags = new List<string>();
            Templates = new Dictionary<string, PushTemplate>();
        }

        [JsonProperty(PropertyName = "installationId")]
        public string InstallationId { get; set; }

        [JsonProperty(PropertyName = "platform")]
        public string Platform { get; set; }

        [JsonProperty(PropertyName = "pushChannel")]
        public string PushChannel { get; set; }

        [JsonProperty(PropertyName = "tags")]
        public List<string> Tags { get; set; }

        [JsonProperty(PropertyName = "templates")]
        public Dictionary<string, PushTemplate> Templates { get; set; }
    }

    public class PushTemplate
    {
        public PushTemplate()
        {
            Tags = new List<string>();
            Headers = new Dictionary<string, string>();
        }

        [JsonProperty(PropertyName = "body")]
        public string Body { get; set; }

        [JsonProperty(PropertyName = "tags")]
        public List<string> Tags { get; set; }

        [JsonProperty(PropertyName = "headers")]
        public Dictionary<string, string> Headers { get; set; }
    }
}

将RegisterForPushNotifications()方法放在特定于平台的代码中。 DeviceInstallation可以在PCL中。

答案 1 :(得分:0)

这是推刀片的一个问题,而不是你自己可以解决的问题。我已通过电子邮件与您联系,以便我们直接为您提供支持。

答案 2 :(得分:0)