Skip to content

Updated ApnsConnection createBatch #885

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 41 additions & 7 deletions PushSharp.Apple/ApnsConnection.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
using System;
using System;
using System.IO;
using System.Net.Sockets;
using System.Net.Security;
Expand Down Expand Up @@ -153,14 +153,26 @@ async Task SendBatch ()
}
}

foreach (var n in toSend)
sent.Add (new SentNotification (n));
foreach (var n in toSend) {
// If the notification failed validation before being sent (i.e. it was skipped)
if (n.State == NotificationState.Failed)
continue;

sent.Add(new SentNotification(n));
}
}

} catch (Exception ex) {
Log.Error ("APNS-CLIENT[{0}]: Send Batch Error: Batch ID={1}, Error={2}", id, batchId, ex);
foreach (var n in toSend)
foreach (var n in toSend) {
// If the notification has already failed, don't fail it again (it's possible it failed validation already)
// - we want the original error intact (and CompleteFailed raises an exception if called twice on the same notification)
if (n.State == NotificationState.Failed)
continue;

// Fail the notification.
n.CompleteFailed (new ApnsNotificationException (ApnsNotificationErrorStatusCode.ConnectionError, n.Notification, ex));
}
}

Log.Info ("APNS-Client[{0}]: Sent Batch, waiting for possible response...", id);
Expand All @@ -185,9 +197,20 @@ byte[] createBatch (List<CompletableApnsNotification> toSend)
var batchData = new List<byte> ();

// Add all the frame data
foreach (var n in toSend)
batchData.AddRange (n.Notification.ToBytes ());

foreach (var n in toSend) {
try {
batchData.AddRange (n.Notification.ToBytes ());
} catch (NotificationException ex) {
// If a notification fails validation, simply fail it and skip
Log.Info("APNS-CLIENT[{0}]: Notification failed validation, failing notification {1}. Batch ID={2}, Error={3}", id, n.Notification.Identifier, batchId, ex);

// Raise the failed event for this notification so the caller knows it wasn't sent
n.CompleteFailed (new ApnsNotificationException (ApnsNotificationErrorStatusCode.ConnectionError, n.Notification, ex));

// Keep adding the other notifications to the batch data to send as we still want to send the others (provided they pass validation themselves)
}
}

return batchData.ToArray ();
}

Expand Down Expand Up @@ -433,6 +456,8 @@ public CompletableApnsNotification (ApnsNotification notification)

public ApnsNotification Notification { get; private set; }

public NotificationState State { get; private set; }

TaskCompletionSource<Exception> completionSource;

public Task<Exception> WaitForComplete ()
Expand All @@ -443,14 +468,23 @@ public Task<Exception> WaitForComplete ()
public void CompleteSuccessfully ()
{
completionSource.SetResult (null);
State = NotificationState.Successful;
}

public void CompleteFailed (Exception ex)
{
completionSource.SetResult (ex);
State = NotificationState.Failed;
}
}

public enum NotificationState
{
Pending,
Successful,
Failed
}

/// <summary>
/// Using IOControl code to configue socket KeepAliveValues for line disconnection detection(because default is toooo slow)
/// </summary>
Expand Down