I am having issues with Azure Notification Hub. My iOS devices are initially being registered correctly and receiving pushes. However occasionally one or two devices just inexplicably stop receiving push notifications at all. Debugging this issue it appears that the problem is due to APNS expiring the channel the device was registered with:
The time elapsed between device registration and pushes stopping was no more than 10 minutes. I can 100% guarantee that this device was not manually unregistered via the notification hub. I was using the app as normal, and received some pushes and then it stopped receiving any.
For reference, the app is registered to Azure Notification Hub through a WebAPI back end. For reference, here is the code which registers the device for pushes whenever the user logs in or the app returns to the foreground. Please let me know if I am doing anything incorrectly in this logic:
private async Task<string> RegisterDevice(string token)
{
string newRegistrationId = null;
if (!string.IsNullOrWhiteSpace(token))
{
var registrations = await _notificationHub.GetRegistrationsByChannelAsync(token, 100);
foreach (var registration in registrations)
{
if (newRegistrationId == null)
{
newRegistrationId = registration.RegistrationId;
}
else
{
await _notificationHub.DeleteRegistrationAsync(registration);
}
}
}
return newRegistrationId ?? await _notificationHub.CreateRegistrationIdAsync();
}
public async Task<string> CreateOrUpdateRegistration(string userId, string token, string platform, string registrationId = null)
{
var userDetail = await _userDetailRepo.GetAsync(userId);
if (userDetail == null)
throw new ApiException(HttpStatusCode.BadRequest, "User details could not be found");
if (string.IsNullOrWhiteSpace(registrationId))
registrationId = await RegisterDevice(token);
RegistrationDescription registration;
switch (platform)
{
case Settings.Platforms.Android:
var gcmTemplate = "[REDACTED]"
registration = new GcmTemplateRegistrationDescription(token, gcmTemplate);
break;
case Settings.Platforms.Ios:
var apnsTemplate = "[REDACTED]";
registration = new AppleTemplateRegistrationDescription(token, apnsTemplate);
break;
default:
throw new ApiException(HttpStatusCode.BadRequest, "Platform not recognised");
}
registration.RegistrationId = registrationId;
SetDeviceRegistrationTags(registration, userId, userDetail.TwingleAcceptedNotificationEnabled, userDetail.TwingleDeclinedNotificationEnabled, userDetail.MessageReceivedNotificationEnabled, userDetail.ConnectionDeletedNotificationEnabled);
var registrationStale = false;
try
{
await _notificationHub.CreateOrUpdateRegistrationAsync(registration);
}
catch (MessagingException e)
{
var webEx = e.InnerException as WebException;
if (webEx != null && webEx.Status == WebExceptionStatus.ProtocolError)
{
var response = (HttpWebResponse)webEx.Response;
if (response.StatusCode == HttpStatusCode.Gone)
{
registrationStale = true;
}
}
}
// if the registration is stale and/or removed then it needs to be re-created with a new registrationId
if (registrationStale)
registrationId = await CreateOrUpdateRegistration(userId, token, platform);
return registrationId;
}
Can anyone tell me what causes the device to expire with APNS when no changes are made to its (at first successful) registration?