Beispiel #1
0
/*!	Writes UID, and flags to the message, and notifies the protocol that a
	message has been fetched. This method also closes the \a file passed in.
*/
void
IMAPFolder::MessageStored(entry_ref& ref, BFile& file, uint32 fetchFlags,
	uint32 uid, uint32 flags)
{
	_WriteUniqueIDValidity(file);
	_WriteUniqueID(file, uid);
	if ((fetchFlags & IMAP::kFetchFlags) != 0)
		_WriteFlags(file, flags);

	BMessage attributes;
	_IMAPToMailFlags(flags, attributes);

	fProtocol.MessageStored(*this, ref, file, fetchFlags, attributes);
	file.Unset();

	fRefMap.insert(std::make_pair(uid, ref));

	if (uid > fLastUID) {
		// Update last known UID
		fLastUID = uid;

		BNode directory(&fRef);
		status_t status = _WriteUInt32(directory, kLastUIDAttribute, uid);
		if (status != B_OK) {
			fprintf(stderr, "IMAP: Could not write last UID for mailbox "
				"%s: %s\n", fMailboxName.String(), strerror(status));
		}
	}
}
Beispiel #2
0
/*!	Synchronizes the message flags/state from the server with the local
	one.
*/
void
IMAPFolder::SyncMessageFlags(uint32 uid, uint32 mailboxFlags)
{
	if (uid > LastUID())
		return;

	entry_ref ref;
	BNode node;

	while (true) {
		status_t status = GetMessageEntryRef(uid, ref);
		if (status == B_ENTRY_NOT_FOUND) {
			// The message does not exist anymore locally, delete it on the
			// server
			// TODO: copy it to the trash directory first!
			fProtocol.UpdateMessageFlags(*this, uid, IMAP::kDeleted);
			return;
		}
		if (status == B_OK)
			status = node.SetTo(&ref);
		if (status == B_TIMED_OUT) {
			// We don't know the message state yet
			fPendingFlagsMap.insert(std::make_pair(uid, mailboxFlags));
		}
		if (status != B_OK)
			return;

		break;
	}
	fSynchronizedUIDsSet.insert(uid);

	uint32 previousFlags = MessageFlags(uid);
	uint32 currentFlags = previousFlags;
	if (_MailToIMAPFlags(node, currentFlags) != B_OK)
		return;

	// Compare flags to previous/current flags, and update either the
	// message on the server, or the message locally (or even both)

	uint32 nextFlags = mailboxFlags;
	_TestMessageFlags(previousFlags, mailboxFlags, currentFlags,
		IMAP::kSeen, nextFlags);
	_TestMessageFlags(previousFlags, mailboxFlags, currentFlags,
		IMAP::kAnswered, nextFlags);

	if (nextFlags != previousFlags)
		_WriteFlags(node, nextFlags);
	if (currentFlags != nextFlags) {
		// Update mail message attributes
		BMessage attributes;
		_IMAPToMailFlags(nextFlags, attributes);
		node << attributes;

		fFlagsMap[uid] = nextFlags;
	}
	if (mailboxFlags != nextFlags) {
		// Update server flags
		fProtocol.UpdateMessageFlags(*this, uid, nextFlags);
	}
}
Beispiel #3
0
status_t
IMAPStorage::SetFlags(int32 uid, int32 flags)
{
    MailEntryMap::iterator it = fMailEntryMap.find(uid);
    if (it == fMailEntryMap.end())
        return B_ENTRY_NOT_FOUND;
    StorageMailEntry& entry = (*it).second;

    BPath filePath = fMailboxPath;
    filePath.Append(entry.fileName);
    BNode node(filePath.Path());

    status_t status = _WriteFlags(flags, node);
    if (status != B_OK)
        return status;

    entry.flags = flags;
    return B_OK;
}
Beispiel #4
0
status_t
IMAPStorage::AddNewMessage(int32 uid, int32 flags, BPositionIO** file)
{
    if (file != NULL)
        *file = NULL;
    // TODO: make sure there is not a valid mail with this name
    BString fileName = "Downloading file... uid: ";
    fileName << uid;

    BPath filePath = fMailboxPath;
    filePath.Append(fileName);
    TRACE("AddNewMessage %s\n", filePath.Path());
    BFile* newFile = new BFile(filePath.Path(), B_READ_WRITE | B_CREATE_FILE
                               | B_ERASE_FILE);
    if (newFile == NULL)
        return B_NO_MEMORY;

    StorageMailEntry storageEntry;
    storageEntry.uid = uid;
    storageEntry.flags = flags;
    storageEntry.fileName = fileName;
    newFile->GetNodeRef(&storageEntry.nodeRef);

    if (_WriteUniqueID(*newFile, uid) != B_OK) {
        delete newFile;
        return B_ERROR;
    }

    status_t status = _WriteFlags(flags, *newFile);
    if (status != B_OK) {
        delete newFile;
        return status;
    }

    if (file)
        *file = newFile;
    else
        delete newFile;
    fMailEntryMap[uid] = storageEntry;
    return B_OK;
}