From 22fb97d0c4675b8cc801c1293da5591954c69144 Mon Sep 17 00:00:00 2001 From: Skylar Ittner Date: Mon, 11 Feb 2019 16:08:56 -0700 Subject: [PATCH] Add app passwords (close #15) --- api/actions/auth.php | 11 ++++- api/actions/login.php | 2 +- api/apisettings.php | 3 +- api/functions.php | 10 ++-- database.mwb | Bin 22861 -> 23725 bytes database.sql | 21 +++++++- database_upgrade/2.1_2.2.sql | 18 ++++++- langs/en/apppasswords.json | 11 +++++ lib/User.lib.php | 16 +++++++ login/index.php | 3 ++ pages/security.php | 90 ++++++++++++++++++++++++++++++++++- 11 files changed, 175 insertions(+), 10 deletions(-) create mode 100644 langs/en/apppasswords.json diff --git a/api/actions/auth.php b/api/actions/auth.php index ede643b..d1cfe9c 100644 --- a/api/actions/auth.php +++ b/api/actions/auth.php @@ -7,7 +7,16 @@ */ $user = User::byUsername($VARS['username']); -if ($user->checkPassword($VARS['password'])) { + +$ok = false; +if (empty($VARS['apppass']) && ($user->checkPassword($VARS['password']) || $user->checkAppPassword($VARS['password']))) { + $ok = true; +} else { + if ((!$user->has2fa() && $user->checkPassword($VARS['password'])) || $user->checkAppPassword($VARS['password'])) { + $ok = true; + } +} +if ($ok) { Log::insert(LogType::API_AUTH_OK, null, "Username: " . strtolower($VARS['username']) . ", Key: " . getCensoredKey()); sendJsonResp($Strings->get("login successful", false), "OK"); } else { diff --git a/api/actions/login.php b/api/actions/login.php index 6372b16..c7ed41b 100644 --- a/api/actions/login.php +++ b/api/actions/login.php @@ -8,7 +8,7 @@ engageRateLimit(); $user = User::byUsername($VARS['username']); -if ($user->checkPassword($VARS['password'])) { +if ((!$user->has2fa() && $user->checkPassword($VARS['password'])) || $user->checkAppPassword($VARS['password'])) { switch ($user->getStatus()->getString()) { case "LOCKED_OR_DISABLED": Log::insert(LogType::API_LOGIN_FAILED, $uid, "Username: " . strtolower($VARS['username']) . ", Key: " . getCensoredKey()); diff --git a/api/apisettings.php b/api/apisettings.php index 32ce97f..8acb6f8 100644 --- a/api/apisettings.php +++ b/api/apisettings.php @@ -19,7 +19,8 @@ $APIS = [ "load" => "auth.php", "vars" => [ "username" => "string", - "password" => "string" + "password" => "string", + "apppass (optional)" => "/[0-1]/" ], "keytype" => "AUTH" ], diff --git a/api/functions.php b/api/functions.php index 551f34f..e77b507 100644 --- a/api/functions.php +++ b/api/functions.php @@ -90,11 +90,13 @@ function checkVars($vars, $or = false) { continue; } } - $checkmethod = "is_$val"; - if ($checkmethod($VARS[$key]) !== true) { - $ok[$key] = false; + + if (strpos($val, "/") === 0) { + // regex + $ok[$key] = preg_match($val, $VARS[$key]) === 1; } else { - $ok[$key] = true; + $checkmethod = "is_$val"; + $ok[$key] = !($checkmethod($VARS[$key]) !== true); } } if ($or) { diff --git a/database.mwb b/database.mwb index a7fea3b060f553ace419e09f7fcf7f4fc134dcbb..873a326f43a8f247aa6d4e28b60c7a9b2bea343f 100644 GIT binary patch delta 23419 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

Bu943JV6z*BgtCMn~POu?6V_YAcZ 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 = $user['authsecret']; $this->has2fa = !empty($user['authsecret']); $this->exists = true; + $this->apppasswords = $database->select('apppasswords', 'hash', ['uid' => $this->uid]); } else { $this->uid = $uid; $this->username = $username; @@ -107,6 +109,20 @@ class User { return password_verify($password, $this->passhash); } + /** + * Check the given password against the user's app passwords. + * @param string $apppassword + * @return bool + */ + function checkAppPassword(string $apppassword): bool { + foreach ($this->apppasswords as $hash) { + if (password_verify($apppassword, $hash)) { + return true; + } + } + return false; + } + /** * Change the user's password. * @global $database $database diff --git a/login/index.php b/login/index.php index 55c63f7..8b8ffc1 100644 --- a/login/index.php +++ b/login/index.php @@ -93,6 +93,9 @@ if (!empty($_SESSION['check'])) { } } else { $error = $Strings->get("Password incorrect.", false); + if ($user->checkAppPassword($_POST['password'])) { + $error = $Strings->get("App passwords are not allowed here.", false); + } Log::insert(LogType::LOGIN_FAILED, $user); } break; diff --git a/pages/security.php b/pages/security.php index d1bb78e..d0a95ab 100644 --- a/pages/security.php +++ b/pages/security.php @@ -10,6 +10,12 @@ use Endroid\QrCode\ErrorCorrectionLevel; use Endroid\QrCode\QrCode; $user = new User($_SESSION['uid']); + +if (!empty($_GET['delpass'])) { + if ($database->has("apppasswords", ["AND" => ["uid" => $_SESSION['uid'], "passid" => $_GET['delpass']]])) { + $database->delete("apppasswords", ["AND" => ["uid" => $_SESSION['uid'], "passid" => $_GET['delpass']]]); + } +} ?>

@@ -138,5 +144,87 @@ $user = new User($_SESSION['uid']); ?>
- + +
+
+ insert('apppasswords', ['uid' => $_SESSION['uid'], 'hash' => password_hash($chunk_code, PASSWORD_DEFAULT), 'description' => $desc]); + ?> +
+
get("App Passwords"); ?>
+
+ + build("app password setup instructions", ["app_name" => $desc]); ?> +
+
+
+
get("username"); ?>:
+
+
+
+
get("password"); ?>
+
+
+
+ + select("apppasswords", ["passid", "description"], ["uid" => $_SESSION['uid']]); + ?> +
+
get("App Passwords"); ?>
+
+

+ build("app passwords explained", ["site_name" => $SETTINGS['site_title']]); ?> +

+
+ " required /> + +
+
+
+
+ get("App Passwords"); ?> +
+ 0) { + foreach ($activecodes as $c) { + ?> + + +
+ get("You don't have any app passwords."); ?> +
+ +
+ +
+ +
\ No newline at end of file