2009-07-05 5 views
18

Ich schreibe eine Client-Anwendung, die E-Mails von einem IMAP-Server abruft und sie dann in einer Datenbank speichert. Das Problem ist, dass ich, sobald ich die Mail überprüft habe, das nächste Mal nur die Mail herunterladen möchte, die seitdem angekommen ist. Also, wenn ich vor zwei Stunden den Server auf Mails überprüft hätte, möchte ich nur die Post bekommen, die in den letzten zwei Stunden angekommen ist.Nur neue E-Mails von einem IMAP-Server abrufen

Ich könnte SEARCH mit SEIT DATUM verwenden, aber es gibt keine Unterstützung für Zeit + Datum konnte leicht gefälscht werden.

Ich habe auch die RECENT-Flagge versucht, aber das scheint nicht mit Google Mail zu funktionieren (in Ruby zeigt es immer Null).

Antwort

40

Sie möchten die UniqueId (UID) für die Nachrichten verwenden. Dies ist insbesondere, warum es erstellt wurde.

Sie sollten die letzte angeforderte UID verfolgen und dann alle neuen Nachrichten anfordern, indem Sie den Nachrichtensatz "[UID]: *" verwenden, wobei [UID] der tatsächliche UID-Wert ist.

Zum Beispiel sagen wir, die letzte Nachricht hatte eine eindeutige ID von "123456". *

Dann werfen Sie die erste Nachricht zurückgegeben: Sie würden

123456 holen.

UIDs "sollen" über Sitzungen hinweg stabil sein, sich niemals ändern und immer an Wert gewinnen. Um dies zu überprüfen, überprüfen Sie die UIDValidity, wenn Sie den Ordner auswählen. Wenn sich die UIDValidity-Nummer nicht geändert hat, sollten die UIDs weiterhin in den Sitzungen gültig sein.

Hier sind die relevanten Teile aus der RFC:

2.3.1.1. Eindeutige Kennung (UID) Nachrichtenattribut

Ein 32-Bit-Wert zu jeder Nachricht zugeordnet ist, die, wenn sie mit dem eindeutigen Identifikator Gültigkeitswert (siehe unten) ein 64-Bit-Wert verwendet, die auf jede andere Nachricht verweisen NICHT in der Mailbox oder einem beliebigen anderen Mailbox mit dem gleichen Namen für immer. Eindeutige Bezeichner werden streng aufsteigend in der Mailbox vergeben; Wenn jede Nachricht dem Postfach hinzugefügt wird, erhält sie eine höhere UID als die Nachricht (en), die zuvor hinzugefügt wurden. Im Gegensatz zu Nachrichtenfolgenummern sind eindeutige Kennungen nicht notwendigerweise zusammenhängend.

Die eindeutige ID einer Nachricht darf sich während der Sitzung NICHT ändern und SOLLTE sich NICHT zwischen den Sitzungen ändern. Jede Änderung von eindeutigen Bezeichnern zwischen Sitzungen MUSS unter Verwendung des UIDVALIDITY-Mechanismus, der unten diskutiert wird, nachweisbar sein.Beständige eindeutige Identifizierer werden benötigt, damit ein Client seinen Zustand von einer vorherigen Sitzung mit dem Server resynchronisiert (z. B. getrennte Clients oder Offline-Zugriff Clients); Dies wird weiter in [IMAP-DISC] diskutiert.

Hinweis: Der nächste eindeutige Kennung Wert sollte ein Mittel zum einem Client, um zu bestimmen, ob irgendwelche Nachrichten haben auf die Mailbox, da die vorherige Zeit diesen Wert geprüft ausgeliefert.

Hier ist der Link mit mehr Info:

http://www.faqs.org/rfcs/rfc3501.html

Was ich tun würde, halten auch den Überblick über das INTERNALDATE der heruntergeladenen Nachrichten. Auf diese Weise können Sie, wenn Sie die UID-Synchronisierung verlieren, zumindest die Nachrichten durchlaufen und anhand des internen Datums der Nachricht die zuletzt heruntergeladene Nachricht finden.

+0

ja das ist perfekt! Stellen Sie sicher, dass Sie den Befehl "UID 123: *" statt nur "123: *" ausführen, was zu unerwarteten Ergebnissen führt - z. client.Folders.Inbox.Search ("UID 123: *") –

4

Es gibt ein IMAP-Flag namens "gesehen". Die meisten Clients markieren eine Nachricht, die beim Anzeigen der Nachricht angezeigt wird. Daher sollten Sie über Nachrichten auf dem Server iterieren, für die dieses Flag nicht festgelegt ist.

Hier ist ein Codeausschnitt, der Ihnen die richtige Idee geben sollte. Das operative Bit natürlich ist

imap.search(["NOT", "SEEN"]).each do bla.bla.bla 
+0

danke, aber meine Anwendung ist nicht die einzige, die Zugriff auf dieses E-Mail-Konto hat. Zum Beispiel könnte eine bestimmte Nachricht in Outlook gelesen und somit als "gesehen" markiert worden sein. Mit "gesehen" würde meine Bewerbung es vermissen. –

+0

In diesem Fall möchten Sie möglicherweise nur über die Nachrichten-ID-Header in der Mail auf dem Server iterieren und vergleichen, was Sie in der Datenbank haben. http://www.freesoft.org/CIE/RFC/850/10.htm – JosefAssad

0

Wenn Sie Sie in der Lage zu filtern eingehende E-Mails in einem bestimmten IMAP-Ordner auf dem Server sind, Ihre App neue Nachrichten in diesem Ordner lesen kann und sie dann in den Standard-Inbox bewegen Ordner, nachdem es fertig ist.

Verwandte Themen