Freigeben über


Hintergrundübertragung und NSURLSession in Xamarin.iOS

Eine Hintergrundübertragung wird initiiert, indem ein Hintergrund NSURLSession konfiguriert und Upload- oder Downloadaufgaben queuiert werden. Wenn Aufgaben abgeschlossen werden, während die Anwendung hintergrundgehängt, angehalten oder beendet wird, benachrichtigt iOS die Anwendung durch Aufrufen des Abschlusshandlers im AppDelegate der Anwendung. Das folgende Diagramm veranschaulicht dies in Aktion:

Eine Hintergrundübertragung wird initiiert, indem eine Hintergrund-NSURLSession konfiguriert und Upload- oder Downloadaufgaben in die Warteschlange gestellt werden.

Konfigurieren einer Hintergrundsitzung

Um eine Hintergrundsitzung zu erstellen, erstellen Sie eine neue NSUrlSession und konfigurieren sie mithilfe eines NSUrlSessionConfiguration Objekts.

Das Konfigurationsobjekt bestimmt, was die Sitzung ausführen kann, und welche Arten von Aufgaben ausgeführt werden können. Sitzungen, die mit der CreateBackgroundSessionConfiguration Methode konfiguriert sind, werden in einem separaten Prozess ausgeführt und führen diskretionäre Übertragungen (WiFi) durch, um Die Daten und die Akkulaufzeit zu erhalten. Im folgenden Codebeispiel wird die ordnungsgemäße Einrichtung einer Hintergrundübertragungssitzung mithilfe der CreateBackgroundSessionConfiguration Methode und eines eindeutigen Zeichenfolgenbezeichners veranschaulicht:

public partial class SimpleBackgroundTransferViewController : UIViewController
{
  NSUrlSession session = null;

  NSUrlSessionConfiguration configuration =
      NSUrlSessionConfiguration.CreateBackgroundSessionConfiguration ("com.SimpleBackgroundTransfer.BackgroundSession");
  session = NSUrlSession.FromConfiguration
      (configuration, new MySessionDelegate(), new NSOperationQueue());

}

Neben einem Konfigurationsobjekt erfordert eine Sitzung auch einen Sitzungsdelegat und eine Warteschlange. Die Warteschlange bestimmt die Reihenfolge, in der die Aufgaben abgeschlossen werden. Der Sitzungsdelegat führt den Übertragungsprozess durch und behandelt Authentifizierung, Zwischenspeicherung und andere sitzungsbezogene Probleme.

Arbeiten mit Aufgaben und Stellvertretungen

Nachdem wir nun eine Hintergrundsitzung konfiguriert haben, starten wir Aufgaben zur Behandlung der Übertragung. Wir können diese Aufgaben mithilfe der NSUrlSessionDelegate Instanz, die als Sitzungsdelegat bezeichnet wird, nachverfolgen. Der Sitzungsdelegat ist für das Aufwachen einer beendeten oder angehaltenen Anwendung im Hintergrund verantwortlich, um die Authentifizierung, Fehler oder den Abschluss der Übertragung zu behandeln.

Es NSUrlSessionDelegate werden die folgenden grundlegenden Methoden zum Überprüfen des Übertragungsstatus bereitgestellt:

  • DidFinishEventsForBackgroundSession – Diese Methode wird aufgerufen, wenn alle Aufgaben abgeschlossen sind und die Übertragung abgeschlossen ist.
  • DidReceiveChallenge – Wird aufgerufen, um Anmeldeinformationen anzufordern, wenn die Autorisierung erforderlich ist.
  • DidBecomeInvalidWithError – Wird aufgerufen, wenn dies NSURLSession ungültig wird.

Hintergrundsitzungen erfordern je nach ausgeführten Aufgabentypen speziellere Stellvertretungen. Hintergrundsitzungen sind auf zwei Arten von Aufgaben beschränkt:

  • Aufgaben hochladen – Aufgaben vom Typ NSUrlSessionUploadTask verwenden die INSUrlSessionTaskDelegate Schnittstelle, die implementiert INSUrlSessionDelegatewird. Dies bietet zusätzliche Methoden zum Nachverfolgen des Uploadfortschritts, behandeln sie die HTTP-Umleitung und vieles mehr.
  • Download-Aufgaben – Aufgaben vom Typ NSUrlSessionDownloadTask verwenden die INSUrlSessionDownloadDelegate Schnittstelle, die implementiert INSUrlSessionDelegate und INSUrlSessionTaskDelegate. Dadurch werden alle Methoden zum Hochladen von Aufgaben sowie downloadspezifische Methoden zum Nachverfolgen des Downloadfortschritts bereitgestellt und bestimmt, wann eine Downloadaufgabe fortgesetzt oder abgeschlossen wurde.

Der folgende Code definiert eine Aufgabe, die zum Herunterladen eines Bilds aus einer URL verwendet werden kann. Die Aufgabe wird gestartet, indem Sie die Hintergrundsitzung aufrufen CreateDownloadTask und die URL-Anforderung übergeben:

const string DownloadURLString = "http://xamarin.com/images/xamarin.png"; // or other hosted file
public NSUrlSessionDownloadTask downloadTask;

NSUrl downloadURL = NSUrl.FromString (DownloadURLString);
NSUrlRequest request = NSUrlRequest.FromUrl (downloadURL);
downloadTask = session.CreateDownloadTask (request);

Erstellen Sie als Nächstes einen neuen Downloaddelegat für Sitzungen, um alle Downloadaufgaben in dieser Sitzung nachzuverfolgen. Die Delegatklasse sollte von NSObject der erforderlichen Schnittstelle erben und implementieren:

public class MySessionDelegate : NSObject, INSUrlSessionDownloadDelegate
{
  public void DidWriteData (NSUrlSession session, NSUrlSessionDownloadTask downloadTask, long bytesWritten, long totalBytesWritten, long totalBytesExpectedToWrite)
  {
    Console.WriteLine (string.Format ("DownloadTask: {0}  progress: {1}", downloadTask, progress));
    InvokeOnMainThread( () => {
      // update UI with progress bar, if desired
    });
  }
  ...
}

Um den Fortschritt einer Downloadaufgabe zu ermitteln, überschreiben Sie die DidWriteData Methode, um den Fortschritt zu verfolgen und sogar die Benutzeroberfläche zu aktualisieren. Ui-Updates werden sofort angezeigt, wenn sich die Anwendung im Vordergrund befindet oder beim nächsten Öffnen der Anwendung auf den Benutzer wartet.

Die Sitzungsdelegat-API bietet ein breites Toolkit für die Interaktion mit Aufgaben. Eine vollständige Liste der Methoden des Sitzungsdelegats finden Sie in der NSUrlSessionDelegate API-Dokumentation.

Wichtig

Hintergrundsitzungen werden in einem Hintergrundthread gestartet, sodass alle Aufrufe zum Aktualisieren der Benutzeroberfläche explizit im UI-Thread ausgeführt werden müssen, indem sie aufrufen InvokeOnMainThread , um zu verhindern, dass die App von iOS beendet wird.

Behandeln des Abschlusses der Übertragung

Der letzte Schritt besteht darin, die Anwendung darüber zu informieren, wann alle aufgaben, die der Sitzung zugeordnet sind, abgeschlossen sind und den neuen Inhalt behandeln.

Abonnieren Sie im AppDelegateEreignis das HandleEventsForBackgroundUrl Ereignis. Wenn die Anwendung in den Hintergrund wechselt und eine Übertragungssitzung ausgeführt wird, wird diese Methode aufgerufen, und das System übergibt uns einen Abschlusshandler:

public System.Action backgroundSessionCompletionHandler;

public void HandleEventsForBackgroundUrl (UIApplication application, string sessionIdentifier, System.Action completionHandler)
{
  this.backgroundSessionCompletionHandler = completionHandler;
}

Verwenden Sie den Abschlusshandler, um iOS zu informieren, wann die Verarbeitung unserer Anwendung abgeschlossen ist.

Erinnern Sie sich daran, dass eine Sitzung mehrere Aufgaben zum Verarbeiten einer Übertragung erstellen kann. Nach Abschluss der letzten Aufgabe wird eine angehaltene oder beendete Anwendung erneut im Hintergrund gestartet. Anschließend stellt die Anwendung eine erneute Verbindung mit dem NSURLSession eindeutigen Sitzungsbezeichner und Aufrufen DidFinishEventsForBackgroundSession des Sitzungsdelegats wieder bereit. Diese Methode ist die Möglichkeit der Anwendung, neue Inhalte zu verarbeiten, einschließlich der Aktualisierung der Benutzeroberfläche, um die Ergebnisse der Übertragung widerzuspiegeln:

public void DidFinishEventsForBackgroundSession (NSUrlSession session) {
  // Handle new information, update UI, etc.
}

Rufen Sie nach Abschluss der Behandlung neuer Inhalte den Abschlusshandler auf, um dem System mitzuteilen, dass es sicher ist, eine Momentaufnahme der Anwendung zu nehmen und wieder in den Ruhezustand zu wechseln:

public void DidFinishEventsForBackgroundSession (NSUrlSession session) {
  var appDelegate = UIApplication.SharedApplication.Delegate as AppDelegate;

  // Handle new information, update UI, etc.

  // call completion handler when you're done
  if (appDelegate.backgroundSessionCompletionHandler != null) {
    NSAction handler = appDelegate.backgroundSessionCompletionHandler;
    appDelegate.backgroundSessionCompletionHandler = null;
    handler.Invoke ();
  }
}

In dieser exemplarischen Vorgehensweise wurden die grundlegenden Schritte zum Implementieren des Hintergrundübertragungsdiensts in iOS 7 und höher behandelt.