Skip to content

Commit

Permalink
fixup! Add imip processing
Browse files Browse the repository at this point in the history
  • Loading branch information
miaulalala committed Aug 11, 2022
1 parent 0d7c8fe commit fa7ec4e
Show file tree
Hide file tree
Showing 4 changed files with 38 additions and 33 deletions.
1 change: 0 additions & 1 deletion lib/Db/MessageMapper.php
Original file line number Diff line number Diff line change
Expand Up @@ -549,7 +549,6 @@ public function updateImipData(Message ...$messages): array {
$query->setParameter('imip_message', $message->isImipMessage(), IQueryBuilder::PARAM_BOOL);
$query->setParameter('imip_error', $message->isImipError(), IQueryBuilder::PARAM_BOOL);
$query->setParameter('imip_processed', $message->isImipProcessed(), IQueryBuilder::PARAM_BOOL);

$query->execute();
}

Expand Down
10 changes: 1 addition & 9 deletions lib/Model/IMAPMessage.php
Original file line number Diff line number Diff line change
Expand Up @@ -194,14 +194,6 @@ private function getRawReferences(): string {
return $references->value_single;
}

private function isImipMessage(): bool {
$schedulingHeader = $this->fetch->getEnvelope(); // how can I find out if this has a body part 'ics\text' and a method?
if($schedulingHeader === null) {
return false;
}
// return true;
}

private function getRawInReplyTo(): string {
return $this->fetch->getEnvelope()->in_reply_to;
}
Expand Down Expand Up @@ -803,7 +795,7 @@ public function toDbMessage(int $mailboxId, MailAccount $account): Message {
$msg->setFlagImportant(in_array('$important', $flags, true) || in_array('$labelimportant', $flags, true) || in_array(Tag::LABEL_IMPORTANT, $flags, true));
$msg->setFlagAttachments(false);
$msg->setFlagMdnsent(in_array(Horde_Imap_Client::FLAG_MDNSENT, $flags, true));
if($this->isImipMessage()) {
if(!empty($this->scheduling)) {
$msg->setImipMessage(true);
}

Expand Down
54 changes: 34 additions & 20 deletions lib/Service/IMipService.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
use OCA\Mail\Db\Message;
use OCA\Mail\Db\MessageMapper;
use OCA\Mail\Exception\ServiceException;
use OCA\Mail\Model\IMAPMessage;
use OCP\AppFramework\Db\DoesNotExistException;
use OCP\Calendar\IManager;
use Psr\Log\LoggerInterface;
Expand Down Expand Up @@ -68,13 +69,13 @@ public function process(): void {
return $message->getMailboxId();
}, $messages));

$mailboxes = array_combine($mailboxIds, array_map(function (int $mailboxId) {
$mailboxes = array_map(function (int $mailboxId) {
try {
return $this->mailboxMapper->findById($mailboxId);
} catch (DoesNotExistException | ServiceException $e) {
return null;
}
}, $mailboxIds));
}, $mailboxIds);

// Collect all accounts in memory
$accountIds = array_unique(array_map(function (Mailbox $mailbox) {
Expand All @@ -89,33 +90,48 @@ public function process(): void {
}
}, $accountIds));

// @todo loop through mailboxes with associated messages instead
foreach ($messages as $message) {
/** @var Mailbox $mailbox */
$mailbox = $mailboxes[$message->getMailboxId()];
if( $mailbox === null ) {
$message->setImipProcessed(true); // Silently drop from passing to DAV and mark as processed, so we won't run into this message again.
continue;
}

/** @var Mailbox $mailbox */
foreach ($mailboxes as $mailbox) {
/** @var Account $account */
$account = $accounts[$mailbox->getAccountId()];
$filteredMessages = array_filter($messages, function ($message) use ($mailbox) {
return $message->getMailboxId() === $mailbox->getId();
});

if (empty($filteredMessages)) {
continue;
}

// Check for accounts or mailboxes that no longer exist,
// no processing for drafts and sent items
if ($account === null || $mailbox->isSpecialUse("sent") || $mailbox->isSpecialUse("drafts")) { // does this need more use cases? Also probably won't work? @todo
$message->setImipProcessed(true); // Silently drop from passing to DAV and mark as processed, so we won't run into this message again.
// no processing for drafts, sent items, junk or trash
if ($account === null
|| $mailbox->isSpecialUse('sent')
|| $mailbox->isSpecialUse('drafts')
|| $mailbox->isSpecialUse('junk')
|| $mailbox->isSpecialUse('trash')
) {
array_map(function ($message) {
$message->setImipProcessed(true);
}, $filteredMessages); // Silently drop from passing to DAV and mark as processed, so we won't run into these messages again.
$this->messageMapper->updateImipData(...$filteredMessages);
continue;
}

try {
$imapMessages = $this->mailManager->getImapMessagesForScheduleProcessing($account, $mailbox, [$message->getUid()]); // UIDS should return an ordered result, no? @todo
$imapMessages = $this->mailManager->getImapMessagesForScheduleProcessing($account, $mailbox, array_map(function ($message) {
return $message->getUid();
}, $filteredMessages), true);
} catch (ServiceException $e) {
$this->logger->error('Could not get IMAP messages form IMIP server', ['exception' => $e]);
return;
}

foreach($imapMessages as $imapMessage) {


foreach ($filteredMessages as $message) {
$imapMessage = array_filter($imapMessages, function (IMAPMessage $imapMessage) use ($message) {
return $message->getUid() === $imapMessage->getUid();
});
if (empty($imapMessage->scheduling[0])) {
// No scheduling info, maybe the DB is wrong
$message->setImipError(true);
Expand All @@ -125,7 +141,7 @@ public function process(): void {
$principalUri = 'principals/users/' . $account->getUserId();
$sender = $imapMessage->getFrom()->first()->getEmail();
$recipient = $account->getEmail();
foreach($imapMessage->scheduling as $schedulingInfo) { // an IMAP message could contain more than one iMIP object
foreach ($imapMessage->scheduling as $schedulingInfo) { // an IMAP message could contain more than one iMIP object
if ($schedulingInfo['method'] === 'REPLY') {
$processed = $this->calendarManager->handleIMipReply($principalUri, $sender, $recipient, $schedulingInfo['contents']);
$message->setImipProcessed($processed);
Expand All @@ -141,10 +157,8 @@ public function process(): void {
$message->setImipError(!$processed);
}
}

}

$this->messageMapper->updateImipData(...$filteredMessages);
}
$this->messageMapper->updateImipData(...$messages);
}
}
6 changes: 3 additions & 3 deletions lib/Service/MailManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -198,21 +198,21 @@ public function getImapMessage(Account $account,
/**
* @param Account $account
* @param Mailbox $mailbox
* @param int[] $uid
* @param int[] $uids
* @param bool $loadBody
* @return IMAPMessage[]
* @throws ServiceException
*/
public function getImapMessagesForScheduleProcessing(Account $account,
Mailbox $mailbox,
array $uid,
array $uids,
bool $loadBody = false): array {
$client = $this->imapClientFactory->getClient($account);
try {
return $this->imapMessageMapper->findByIds(
$client,
$mailbox->getName(),
new Horde_Imap_Client_Ids($uid),
new Horde_Imap_Client_Ids($uids),
true
);
} catch (Horde_Imap_Client_Exception|DoesNotExistException $e) {
Expand Down

0 comments on commit fa7ec4e

Please sign in to comment.