1<?php
2
3declare(strict_types=1);
4
5/**
6 * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
7 *
8 * @author Christoph Wurst <christoph@winzerhof-wurst.at>
9 * @author Joas Schilling <coding@schilljs.com>
10 *
11 * @license GNU AGPL version 3 or any later version
12 *
13 * This program is free software: you can redistribute it and/or modify
14 * it under the terms of the GNU Affero General Public License as
15 * published by the Free Software Foundation, either version 3 of the
16 * License, or (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Affero General Public License for more details.
22 *
23 * You should have received a copy of the GNU Affero General Public License
24 * along with this program. If not, see <http://www.gnu.org/licenses/>.
25 *
26 */
27namespace OC\Authentication\Listeners;
28
29use Exception;
30use OC\Authentication\Events\RemoteWipeFinished;
31use OC\Authentication\Events\RemoteWipeStarted;
32use OCP\EventDispatcher\Event;
33use OCP\EventDispatcher\IEventListener;
34use OCP\IL10N;
35use OCP\IUser;
36use OCP\IUserManager;
37use OCP\L10N\IFactory as IL10nFactory;
38use OCP\Mail\IMailer;
39use OCP\Mail\IMessage;
40use Psr\Log\LoggerInterface;
41use function substr;
42
43/**
44 * @template-implements IEventListener<\OC\Authentication\Events\ARemoteWipeEvent>
45 */
46class RemoteWipeEmailListener implements IEventListener {
47
48	/** @var IMailer */
49	private $mailer;
50
51	/** @var IUserManager */
52	private $userManager;
53
54	/** @var IL10N */
55	private $l10n;
56
57	/** @var LoggerInterface */
58	private $logger;
59
60	public function __construct(IMailer $mailer,
61								IUserManager $userManager,
62								IL10nFactory $l10nFactory,
63								LoggerInterface $logger) {
64		$this->mailer = $mailer;
65		$this->userManager = $userManager;
66		$this->l10n = $l10nFactory->get('core');
67		$this->logger = $logger;
68	}
69
70	/**
71	 * @param Event $event
72	 */
73	public function handle(Event $event): void {
74		if ($event instanceof RemoteWipeStarted) {
75			$uid = $event->getToken()->getUID();
76			$user = $this->userManager->get($uid);
77			if ($user === null) {
78				$this->logger->warning("not sending a wipe started email because user <$uid> does not exist (anymore)");
79				return;
80			}
81			if ($user->getEMailAddress() === null) {
82				$this->logger->info("not sending a wipe started email because user <$uid> has no email set");
83				return;
84			}
85
86			try {
87				$this->mailer->send(
88					$this->getWipingStartedMessage($event, $user)
89				);
90			} catch (Exception $e) {
91				$this->logger->error("Could not send remote wipe started email to <$uid>", [
92					'exception' => $e,
93				]);
94			}
95		} elseif ($event instanceof RemoteWipeFinished) {
96			$uid = $event->getToken()->getUID();
97			$user = $this->userManager->get($uid);
98			if ($user === null) {
99				$this->logger->warning("not sending a wipe finished email because user <$uid> does not exist (anymore)");
100				return;
101			}
102			if ($user->getEMailAddress() === null) {
103				$this->logger->info("not sending a wipe finished email because user <$uid> has no email set");
104				return;
105			}
106
107			try {
108				$this->mailer->send(
109					$this->getWipingFinishedMessage($event, $user)
110				);
111			} catch (Exception $e) {
112				$this->logger->error("Could not send remote wipe finished email to <$uid>", [
113					'exception' => $e,
114				]);
115			}
116		}
117	}
118
119	private function getWipingStartedMessage(RemoteWipeStarted $event, IUser $user): IMessage {
120		$message = $this->mailer->createMessage();
121		$emailTemplate = $this->mailer->createEMailTemplate('auth.RemoteWipeStarted');
122		$plainHeading = $this->l10n->t('Wiping of device %s has started', [$event->getToken()->getName()]);
123		$htmlHeading = $this->l10n->t('Wiping of device »%s« has started', [$event->getToken()->getName()]);
124		$emailTemplate->setSubject(
125			$this->l10n->t(
126				'»%s« started remote wipe',
127				[
128					substr($event->getToken()->getName(), 0, 15)
129				]
130			)
131		);
132		$emailTemplate->addHeader();
133		$emailTemplate->addHeading(
134			$htmlHeading,
135			$plainHeading
136		);
137		$emailTemplate->addBodyText(
138			$this->l10n->t('Device or application »%s« has started the remote wipe process. You will receive another email once the process has finished', [$event->getToken()->getName()])
139		);
140		$emailTemplate->addFooter();
141		$message->setTo([$user->getEMailAddress()]);
142		$message->useTemplate($emailTemplate);
143
144		return $message;
145	}
146
147	private function getWipingFinishedMessage(RemoteWipeFinished $event, IUser $user): IMessage {
148		$message = $this->mailer->createMessage();
149		$emailTemplate = $this->mailer->createEMailTemplate('auth.RemoteWipeFinished');
150		$plainHeading = $this->l10n->t('Wiping of device %s has finished', [$event->getToken()->getName()]);
151		$htmlHeading = $this->l10n->t('Wiping of device »%s« has finished', [$event->getToken()->getName()]);
152		$emailTemplate->setSubject(
153			$this->l10n->t(
154				'»%s« finished remote wipe',
155				[
156					substr($event->getToken()->getName(), 0, 15)
157				]
158			)
159		);
160		$emailTemplate->addHeader();
161		$emailTemplate->addHeading(
162			$htmlHeading,
163			$plainHeading
164		);
165		$emailTemplate->addBodyText(
166			$this->l10n->t('Device or application »%s« has finished the remote wipe process.', [$event->getToken()->getName()])
167		);
168		$emailTemplate->addFooter();
169		$message->setTo([$user->getEMailAddress()]);
170		$message->useTemplate($emailTemplate);
171
172		return $message;
173	}
174}
175