diff --git a/lib/composer/composer/autoload_classmap.php b/lib/composer/composer/autoload_classmap.php
index f8d95a76c68dc6a3a91dd7a0c96a1a6ff0768231..8df7c5a26f9298265db0b038954c53fb444e9305 100644
--- a/lib/composer/composer/autoload_classmap.php
+++ b/lib/composer/composer/autoload_classmap.php
@@ -452,9 +452,21 @@ return array(
     'OCP\\User\\Backend\\IProvideAvatarBackend' => $baseDir . '/lib/public/User/Backend/IProvideAvatarBackend.php',
     'OCP\\User\\Backend\\ISetDisplayNameBackend' => $baseDir . '/lib/public/User/Backend/ISetDisplayNameBackend.php',
     'OCP\\User\\Backend\\ISetPasswordBackend' => $baseDir . '/lib/public/User/Backend/ISetPasswordBackend.php',
+    'OCP\\User\\Events\\BeforePasswordUpdatedEvent' => $baseDir . '/lib/public/User/Events/BeforePasswordUpdatedEvent.php',
+    'OCP\\User\\Events\\BeforeUserCreatedEvent' => $baseDir . '/lib/public/User/Events/BeforeUserCreatedEvent.php',
+    'OCP\\User\\Events\\BeforeUserDeletedEvent' => $baseDir . '/lib/public/User/Events/BeforeUserDeletedEvent.php',
+    'OCP\\User\\Events\\BeforeUserLoggedInEvent' => $baseDir . '/lib/public/User/Events/BeforeUserLoggedInEvent.php',
+    'OCP\\User\\Events\\BeforeUserLoggedInWithCookieEvent' => $baseDir . '/lib/public/User/Events/BeforeUserLoggedInWithCookieEvent.php',
+    'OCP\\User\\Events\\BeforeUserLoggedOutEvent' => $baseDir . '/lib/public/User/Events/BeforeUserLoggedOutEvent.php',
     'OCP\\User\\Events\\CreateUserEvent' => $baseDir . '/lib/public/User/Events/CreateUserEvent.php',
+    'OCP\\User\\Events\\PasswordUpdatedEvent' => $baseDir . '/lib/public/User/Events/PasswordUpdatedEvent.php',
     'OCP\\User\\Events\\PostLoginEvent' => $baseDir . '/lib/public/User/Events/PostLoginEvent.php',
+    'OCP\\User\\Events\\UserChangedEvent' => $baseDir . '/lib/public/User/Events/UserChangedEvent.php',
     'OCP\\User\\Events\\UserCreatedEvent' => $baseDir . '/lib/public/User/Events/UserCreatedEvent.php',
+    'OCP\\User\\Events\\UserDeletedEvent' => $baseDir . '/lib/public/User/Events/UserDeletedEvent.php',
+    'OCP\\User\\Events\\UserLoggedInEvent' => $baseDir . '/lib/public/User/Events/UserLoggedInEvent.php',
+    'OCP\\User\\Events\\UserLoggedInWithCookieEvent' => $baseDir . '/lib/public/User/Events/UserLoggedInWithCookieEvent.php',
+    'OCP\\User\\Events\\UserLoggedOutEvent' => $baseDir . '/lib/public/User/Events/UserLoggedOutEvent.php',
     'OCP\\Util' => $baseDir . '/lib/public/Util.php',
     'OCP\\WorkflowEngine\\EntityContext\\IDisplayName' => $baseDir . '/lib/public/WorkflowEngine/EntityContext/IDisplayName.php',
     'OCP\\WorkflowEngine\\EntityContext\\IDisplayText' => $baseDir . '/lib/public/WorkflowEngine/EntityContext/IDisplayText.php',
diff --git a/lib/composer/composer/autoload_static.php b/lib/composer/composer/autoload_static.php
index 91bf56af1eff490a473bdda9a17db8f6cd9553b1..1659953433a433fff9c6483ddecc618e799e4c7f 100644
--- a/lib/composer/composer/autoload_static.php
+++ b/lib/composer/composer/autoload_static.php
@@ -481,9 +481,21 @@ class ComposerStaticInit53792487c5a8370acc0b06b1a864ff4c
         'OCP\\User\\Backend\\IProvideAvatarBackend' => __DIR__ . '/../../..' . '/lib/public/User/Backend/IProvideAvatarBackend.php',
         'OCP\\User\\Backend\\ISetDisplayNameBackend' => __DIR__ . '/../../..' . '/lib/public/User/Backend/ISetDisplayNameBackend.php',
         'OCP\\User\\Backend\\ISetPasswordBackend' => __DIR__ . '/../../..' . '/lib/public/User/Backend/ISetPasswordBackend.php',
+        'OCP\\User\\Events\\BeforePasswordUpdatedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforePasswordUpdatedEvent.php',
+        'OCP\\User\\Events\\BeforeUserCreatedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforeUserCreatedEvent.php',
+        'OCP\\User\\Events\\BeforeUserDeletedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforeUserDeletedEvent.php',
+        'OCP\\User\\Events\\BeforeUserLoggedInEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforeUserLoggedInEvent.php',
+        'OCP\\User\\Events\\BeforeUserLoggedInWithCookieEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforeUserLoggedInWithCookieEvent.php',
+        'OCP\\User\\Events\\BeforeUserLoggedOutEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/BeforeUserLoggedOutEvent.php',
         'OCP\\User\\Events\\CreateUserEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/CreateUserEvent.php',
+        'OCP\\User\\Events\\PasswordUpdatedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/PasswordUpdatedEvent.php',
         'OCP\\User\\Events\\PostLoginEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/PostLoginEvent.php',
+        'OCP\\User\\Events\\UserChangedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserChangedEvent.php',
         'OCP\\User\\Events\\UserCreatedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserCreatedEvent.php',
+        'OCP\\User\\Events\\UserDeletedEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserDeletedEvent.php',
+        'OCP\\User\\Events\\UserLoggedInEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserLoggedInEvent.php',
+        'OCP\\User\\Events\\UserLoggedInWithCookieEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserLoggedInWithCookieEvent.php',
+        'OCP\\User\\Events\\UserLoggedOutEvent' => __DIR__ . '/../../..' . '/lib/public/User/Events/UserLoggedOutEvent.php',
         'OCP\\Util' => __DIR__ . '/../../..' . '/lib/public/Util.php',
         'OCP\\WorkflowEngine\\EntityContext\\IDisplayName' => __DIR__ . '/../../..' . '/lib/public/WorkflowEngine/EntityContext/IDisplayName.php',
         'OCP\\WorkflowEngine\\EntityContext\\IDisplayText' => __DIR__ . '/../../..' . '/lib/public/WorkflowEngine/EntityContext/IDisplayText.php',
diff --git a/lib/private/Server.php b/lib/private/Server.php
index 7fa01358afe3a79a5c0f1e4deeead205a94e522d..e7fb32ba1e586ad33ad3c99bbdedd99c47ac9505 100644
--- a/lib/private/Server.php
+++ b/lib/private/Server.php
@@ -113,7 +113,6 @@ use OC\Security\Bruteforce\Throttler;
 use OC\Security\CertificateManager;
 use OC\Security\CredentialsManager;
 use OC\Security\Crypto;
-use OC\Security\CSP\ContentSecurityPolicyManager;
 use OC\Security\CSP\ContentSecurityPolicyNonceManager;
 use OC\Security\CSRF\CsrfTokenGenerator;
 use OC\Security\CSRF\CsrfTokenManager;
@@ -163,6 +162,19 @@ use OCP\Remote\IInstanceFactory;
 use OCP\RichObjectStrings\IValidator;
 use OCP\Security\IContentSecurityPolicyManager;
 use OCP\Share\IShareHelper;
+use OCP\User\Events\BeforePasswordUpdatedEvent;
+use OCP\User\Events\BeforeUserCreatedEvent;
+use OCP\User\Events\BeforeUserDeletedEvent;
+use OCP\User\Events\BeforeUserLoggedInEvent;
+use OCP\User\Events\BeforeUserLoggedInWithCookieEvent;
+use OCP\User\Events\BeforeUserLoggedOutEvent;
+use OCP\User\Events\PasswordUpdatedEvent;
+use OCP\User\Events\UserChangedEvent;
+use OCP\User\Events\UserCreatedEvent;
+use OCP\User\Events\UserDeletedEvent;
+use OCP\User\Events\UserLoggedInEvent;
+use OCP\User\Events\UserLoggedInWithCookieEvent;
+use OCP\User\Events\UserLoggedOutEvent;
 use Symfony\Component\EventDispatcher\EventDispatcherInterface;
 use Symfony\Component\EventDispatcher\GenericEvent;
 
@@ -380,7 +392,7 @@ class Server extends ServerContainer implements IServerContainer {
 				$defaultTokenProvider = null;
 			}
 
-			$dispatcher = $c->getEventDispatcher();
+			$legacyDispatcher = $c->getEventDispatcher();
 
 			$userSession = new \OC\User\Session(
 				$manager,
@@ -395,45 +407,99 @@ class Server extends ServerContainer implements IServerContainer {
 			);
 			$userSession->listen('\OC\User', 'preCreateUser', function ($uid, $password) {
 				\OC_Hook::emit('OC_User', 'pre_createUser', array('run' => true, 'uid' => $uid, 'password' => $password));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforeUserCreatedEvent($uid, $password));
 			});
 			$userSession->listen('\OC\User', 'postCreateUser', function ($user, $password) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'post_createUser', array('uid' => $user->getUID(), 'password' => $password));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserCreatedEvent($user, $password));
 			});
-			$userSession->listen('\OC\User', 'preDelete', function ($user) use ($dispatcher) {
+			$userSession->listen('\OC\User', 'preDelete', function ($user) use ($legacyDispatcher) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'pre_deleteUser', array('run' => true, 'uid' => $user->getUID()));
-				$dispatcher->dispatch('OCP\IUser::preDelete', new GenericEvent($user));
+				$legacyDispatcher->dispatch('OCP\IUser::preDelete', new GenericEvent($user));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforeUserDeletedEvent($user));
 			});
 			$userSession->listen('\OC\User', 'postDelete', function ($user) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'post_deleteUser', array('uid' => $user->getUID()));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserDeletedEvent($user));
 			});
 			$userSession->listen('\OC\User', 'preSetPassword', function ($user, $password, $recoveryPassword) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'pre_setPassword', array('run' => true, 'uid' => $user->getUID(), 'password' => $password, 'recoveryPassword' => $recoveryPassword));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforePasswordUpdatedEvent($user, $password, $recoveryPassword));
 			});
 			$userSession->listen('\OC\User', 'postSetPassword', function ($user, $password, $recoveryPassword) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'post_setPassword', array('run' => true, 'uid' => $user->getUID(), 'password' => $password, 'recoveryPassword' => $recoveryPassword));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new PasswordUpdatedEvent($user, $password, $recoveryPassword));
 			});
 			$userSession->listen('\OC\User', 'preLogin', function ($uid, $password) {
 				\OC_Hook::emit('OC_User', 'pre_login', array('run' => true, 'uid' => $uid, 'password' => $password));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforeUserLoggedInEvent($uid, $password));
 			});
 			$userSession->listen('\OC\User', 'postLogin', function ($user, $password, $isTokenLogin) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'post_login', array('run' => true, 'uid' => $user->getUID(), 'password' => $password, 'isTokenLogin' => $isTokenLogin));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserLoggedInEvent($user, $password, $isTokenLogin));
+			});
+			$userSession->listen('\OC\User', 'preRememberedLogin', function ($uid) {
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforeUserLoggedInWithCookieEvent($uid));
 			});
 			$userSession->listen('\OC\User', 'postRememberedLogin', function ($user, $password) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'post_login', array('run' => true, 'uid' => $user->getUID(), 'password' => $password));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserLoggedInWithCookieEvent($user, $password));
 			});
-			$userSession->listen('\OC\User', 'logout', function () {
+			$userSession->listen('\OC\User', 'logout', function ($user) {
 				\OC_Hook::emit('OC_User', 'logout', array());
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new BeforeUserLoggedOutEvent($user));
+			});
+			$userSession->listen('\OC\User', 'postLogout', function ($user) {
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserLoggedOutEvent($user));
 			});
 			$userSession->listen('\OC\User', 'changeUser', function ($user, $feature, $value, $oldValue) {
 				/** @var $user \OC\User\User */
 				\OC_Hook::emit('OC_User', 'changeUser', array('run' => true, 'user' => $user, 'feature' => $feature, 'value' => $value, 'old_value' => $oldValue));
+
+				/** @var IEventDispatcher $dispatcher */
+				$dispatcher = $this->query(IEventDispatcher::class);
+				$dispatcher->dispatchTyped(new UserChangedEvent($user, $feature, $value, $oldValue));
 			});
 			return $userSession;
 		});
diff --git a/lib/private/User/Session.php b/lib/private/User/Session.php
index 16d3b13cbabd2ac2bd14ef83910b6675ab3d0e72..4aa9074b4a4cdf1e1c504186fbd90c17c706a3a5 100644
--- a/lib/private/User/Session.php
+++ b/lib/private/User/Session.php
@@ -900,9 +900,9 @@ class Session implements IUserSession, Emitter {
 	 * logout the user from the session
 	 */
 	public function logout() {
-		$this->manager->emit('\OC\User', 'logout');
 		$user = $this->getUser();
-		if (!is_null($user)) {
+		$this->manager->emit('\OC\User', 'logout', [$user]);
+		if ($user !== null) {
 			try {
 				$this->tokenProvider->invalidateToken($this->session->getId());
 			} catch (SessionNotAvailableException $ex) {
@@ -914,7 +914,7 @@ class Session implements IUserSession, Emitter {
 		$this->setToken(null);
 		$this->unsetMagicInCookie();
 		$this->session->clear();
-		$this->manager->emit('\OC\User', 'postLogout');
+		$this->manager->emit('\OC\User', 'postLogout', [$user]);
 	}
 
 	/**
diff --git a/lib/public/User/Events/BeforePasswordUpdatedEvent.php b/lib/public/User/Events/BeforePasswordUpdatedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..c40bd92b619d26a54fe8d1967eaefa480d501488
--- /dev/null
+++ b/lib/public/User/Events/BeforePasswordUpdatedEvent.php
@@ -0,0 +1,82 @@
+<?php declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class BeforePasswordUpdatedEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/** @var string */
+	private $password;
+
+	/** @var string|null */
+	private $recoveryPassword;
+
+	/**
+	 * @param IUser $user
+	 * @param string $password
+	 * @param string|null $recoveryPassword
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user,
+								string $password,
+								string $recoveryPassword = null) {
+		parent::__construct();
+		$this->user = $user;
+		$this->password = $password;
+		$this->recoveryPassword = $recoveryPassword;
+	}
+
+	/**
+	 * @return IUser
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+	/**
+	 * @return string
+	 * @since 18.0.0
+	 */
+	public function getPassword(): string {
+		return $this->password;
+	}
+
+	/**
+	 * @return string|null
+	 * @since 18.0.0
+	 */
+	public function getRecoveryPassword(): ?string {
+		return $this->recoveryPassword;
+	}
+
+}
diff --git a/lib/public/User/Events/BeforeUserCreatedEvent.php b/lib/public/User/Events/BeforeUserCreatedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..1a00a167dbbae373be7b6e2d09c2421d2560ecdc
--- /dev/null
+++ b/lib/public/User/Events/BeforeUserCreatedEvent.php
@@ -0,0 +1,66 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+
+/**
+ * @since 18.0.0
+ */
+class BeforeUserCreatedEvent extends Event {
+
+	/** @var string */
+	private $uid;
+
+	/** @var string */
+	private $password;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(string $uid,
+								string $password) {
+		parent::__construct();
+		$this->uid = $uid;
+		$this->password = $password;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUid(): string {
+		return $this->uid;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getPassword(): string {
+		return $this->password;
+	}
+
+}
diff --git a/lib/public/User/Events/BeforeUserDeletedEvent.php b/lib/public/User/Events/BeforeUserDeletedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..b40c498350f537673b1b9bd288cc77ea5d7a2a1b
--- /dev/null
+++ b/lib/public/User/Events/BeforeUserDeletedEvent.php
@@ -0,0 +1,54 @@
+<?php declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class BeforeUserDeletedEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/**
+	 * @param IUser $user
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user) {
+		parent::__construct();
+		$this->user = $user;
+	}
+
+	/**
+	 * @return IUser
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+}
diff --git a/lib/public/User/Events/BeforeUserLoggedInEvent.php b/lib/public/User/Events/BeforeUserLoggedInEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..8b8194787370d97b5135332aa4abdfdf40f0124f
--- /dev/null
+++ b/lib/public/User/Events/BeforeUserLoggedInEvent.php
@@ -0,0 +1,66 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class BeforeUserLoggedInEvent extends Event {
+
+	/** @var IUser */
+	private $username;
+
+	/** @var string */
+	private $password;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(string $username, string $password) {
+		parent::__construct();
+		$this->username = $username;
+		$this->password = $password;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUsername(): IUser {
+		return $this->username;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getPassword(): string {
+		return $this->password;
+	}
+
+}
diff --git a/lib/public/User/Events/BeforeUserLoggedInWithCookieEvent.php b/lib/public/User/Events/BeforeUserLoggedInWithCookieEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..35f9715516bd6f19279bf908f3ee510d69aac428
--- /dev/null
+++ b/lib/public/User/Events/BeforeUserLoggedInWithCookieEvent.php
@@ -0,0 +1,55 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class BeforeUserLoggedInWithCookieEvent extends Event {
+
+	/** @var string */
+	private $username;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(string $username) {
+		parent::__construct();
+		$this->username = $username;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUsername(): string {
+		return $this->username;
+	}
+
+}
diff --git a/lib/public/User/Events/BeforeUserLoggedOutEvent.php b/lib/public/User/Events/BeforeUserLoggedOutEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..a5d617089f72e106368e57cbdaafd8e14cba801e
--- /dev/null
+++ b/lib/public/User/Events/BeforeUserLoggedOutEvent.php
@@ -0,0 +1,55 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class BeforeUserLoggedOutEvent extends Event {
+
+	/** @var IUser|null */
+	private $user;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user = null) {
+		parent::__construct();
+		$this->user = $user;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUser(): ?IUser {
+		return $this->user;
+	}
+
+}
diff --git a/lib/public/User/Events/PasswordUpdatedEvent.php b/lib/public/User/Events/PasswordUpdatedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..83b5b0a7bfd7692c1c08a7656fec53da14e811e6
--- /dev/null
+++ b/lib/public/User/Events/PasswordUpdatedEvent.php
@@ -0,0 +1,82 @@
+<?php declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class PasswordUpdatedEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/** @var string */
+	private $password;
+
+	/** @var string|null */
+	private $recoveryPassword;
+
+	/**
+	 * @param IUser $user
+	 * @param string $password
+	 * @param string|null $recoveryPassword
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user,
+								string $password,
+								string $recoveryPassword = null) {
+		parent::__construct();
+		$this->user = $user;
+		$this->password = $password;
+		$this->recoveryPassword = $recoveryPassword;
+	}
+
+	/**
+	 * @return IUser
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+	/**
+	 * @return string
+	 * @since 18.0.0
+	 */
+	public function getPassword(): string {
+		return $this->password;
+	}
+
+	/**
+	 * @return string|null
+	 * @since 18.0.0
+	 */
+	public function getRecoveryPassword(): ?string {
+		return $this->recoveryPassword;
+	}
+
+}
diff --git a/lib/public/User/Events/UserChangedEvent.php b/lib/public/User/Events/UserChangedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..86b2f439bfb6d21c70723bb82484ffd1ac0f4b20
--- /dev/null
+++ b/lib/public/User/Events/UserChangedEvent.php
@@ -0,0 +1,93 @@
+<?php declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class UserChangedEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/** @var string */
+	private $feature;
+
+	/** @var mixed */
+	private $value;
+
+	/** @var mixed */
+	private $oldValue;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user,
+								string $feature,
+								$value,
+								$oldValue = null) {
+		parent::__construct();
+		$this->user = $user;
+		$this->feature = $feature;
+		$this->value = $value;
+		$this->oldValue = $oldValue;
+	}
+
+	/**
+	 * @return IUser
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+	/**
+	 * @return string
+	 * @since 18.0.0
+	 */
+	public function getFeature(): string {
+		return $this->feature;
+	}
+
+	/**
+	 * @return mixed
+	 * @since 18.0.0
+	 */
+	public function getValue() {
+		return $this->value;
+	}
+
+	/**
+	 * @return mixed
+	 * @since 18.0.0
+	 */
+	public function getOldValue() {
+		return $this->oldValue;
+	}
+
+
+}
diff --git a/lib/public/User/Events/UserDeletedEvent.php b/lib/public/User/Events/UserDeletedEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..284ee35a2427ac314b73cbd33f5c3bb05a2e54a4
--- /dev/null
+++ b/lib/public/User/Events/UserDeletedEvent.php
@@ -0,0 +1,54 @@
+<?php declare(strict_types=1);
+
+/**
+ * @copyright 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @author 2019 Christoph Wurst <christoph@winzerhof-wurst.at>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class UserDeletedEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/**
+	 * @param IUser $user
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user) {
+		parent::__construct();
+		$this->user = $user;
+	}
+
+	/**
+	 * @return IUser
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+}
diff --git a/lib/public/User/Events/UserLoggedInEvent.php b/lib/public/User/Events/UserLoggedInEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..8ce83f42308e6bf5ac846884b201276c98af70c3
--- /dev/null
+++ b/lib/public/User/Events/UserLoggedInEvent.php
@@ -0,0 +1,77 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Christoph Wurst <christoph@winzerhof-wurst.at>
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class UserLoggedInEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/** @var string */
+	private $password;
+
+	/** @var bool */
+	private $isTokenLogin;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user, string $password, bool $isTokenLogin) {
+		parent::__construct();
+		$this->user = $user;
+		$this->password = $password;
+		$this->isTokenLogin = $isTokenLogin;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getPassword(): string {
+		return $this->password;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function isTokenLogin(): bool {
+		return $this->isTokenLogin;
+	}
+}
diff --git a/lib/public/User/Events/UserLoggedInWithCookieEvent.php b/lib/public/User/Events/UserLoggedInWithCookieEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..c9848e1cc7d55f53a8e51df951b35525232a24e8
--- /dev/null
+++ b/lib/public/User/Events/UserLoggedInWithCookieEvent.php
@@ -0,0 +1,66 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class UserLoggedInWithCookieEvent extends Event {
+
+	/** @var IUser */
+	private $user;
+
+	/** @var string|null */
+	private $password;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user, ?string $password) {
+		parent::__construct();
+		$this->user = $user;
+		$this->password = $password;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUser(): IUser {
+		return $this->user;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getPassword(): ?string {
+		return $this->password;
+	}
+
+}
diff --git a/lib/public/User/Events/UserLoggedOutEvent.php b/lib/public/User/Events/UserLoggedOutEvent.php
new file mode 100644
index 0000000000000000000000000000000000000000..14259149533cea4261ba7340d17414f3c4710341
--- /dev/null
+++ b/lib/public/User/Events/UserLoggedOutEvent.php
@@ -0,0 +1,55 @@
+<?php
+
+declare(strict_types=1);
+
+/**
+ * @copyright Copyright (c) 2019, Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @author Roeland Jago Douma <roeland@famdouma.nl>
+ *
+ * @license GNU AGPL version 3 or any later version
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as
+ * published by the Free Software Foundation, either version 3 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCP\User\Events;
+
+use OCP\EventDispatcher\Event;
+use OCP\IUser;
+
+/**
+ * @since 18.0.0
+ */
+class UserLoggedOutEvent extends Event {
+
+	/** @var IUser|null */
+	private $user;
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function __construct(IUser $user = null) {
+		parent::__construct();
+		$this->user = $user;
+	}
+
+	/**
+	 * @since 18.0.0
+	 */
+	public function getUser(): ?IUser {
+		return $this->user;
+	}
+
+}