Permanent login

git-svn-id: https://adminer.svn.sourceforge.net/svnroot/adminer/trunk@1281 7c3ca157-0c34-0410-bff1-cbf682f78f5c
This commit is contained in:
jakubvrana 2009-12-18 17:39:48 +00:00
parent 1bcee1ebad
commit 95b4ea471d
6 changed files with 64 additions and 4 deletions

View file

@ -23,6 +23,13 @@ class Adminer {
return array($_GET["server"], $_SESSION["usernames"][$_GET["server"]], $_SESSION["passwords"][$_GET["server"]]); return array($_GET["server"], $_SESSION["usernames"][$_GET["server"]], $_SESSION["passwords"][$_GET["server"]]);
} }
/** Get key used for permanent login
* @return string cryptic string which gets combined with password
*/
function permanentLogin() {
return "";
}
/** Identifier of selected database /** Identifier of selected database
* @return string * @return string
*/ */
@ -43,6 +50,9 @@ class Adminer {
<tr><th><?php echo lang('Password'); ?><td><input type="password" name="password"> <tr><th><?php echo lang('Password'); ?><td><input type="password" name="password">
</table> </table>
<?php <?php
if ($this->permanentLogin()) {
echo "<p>" . checkbox("permanent", 1, $_COOKIE["adminer_permanent"], lang('Permanent login')) . "\n";
}
} }
/** Authorize the user /** Authorize the user

View file

@ -3,8 +3,15 @@ if (isset($_POST["server"])) {
session_regenerate_id(); // defense against session fixation session_regenerate_id(); // defense against session fixation
$_SESSION["usernames"][$_POST["server"]] = $_POST["username"]; $_SESSION["usernames"][$_POST["server"]] = $_POST["username"];
$_SESSION["passwords"][$_POST["server"]] = $_POST["password"]; $_SESSION["passwords"][$_POST["server"]] = $_POST["password"];
if (count($_POST) == 3) { // 3 - count($ignore) if ($_POST["permanent"]) {
$location = ((string) $_GET["server"] === $_POST["server"] ? remove_from_uri(session_name()) : preg_replace('~^([^?]*).*~', '\\1', $_SERVER["REQUEST_URI"]) . (strlen($_POST["server"]) ? '?server=' . urlencode($_POST["server"]) : '')); cookie("adminer_permanent",
base64_encode($_POST["server"])
. ":" . base64_encode($_POST["username"])
. ":" . base64_encode(cipher_password($_POST["password"], pack("H*", sha1(str_pad($_POST["username"], 1) . $adminer->permanentLogin())))) // str_pad - to hide original key
);
}
if (count($_POST) == 3 + ($_POST["permanent"] ? 1 : 0)) { // 3 - server, username, password
$location = ((string) $_GET["server"] === $_POST["server"] ? remove_from_uri(session_name()) : preg_replace('~^([^?]*).*~', '\\1', ME) . (strlen($_POST["server"]) ? '?server=' . urlencode($_POST["server"]) : ''));
if (SID) { if (SID) {
$pos = strpos($location, '?'); $pos = strpos($location, '?');
$location = ($pos ? substr_replace($location, SID . "&", $pos + 1, 0) : "$location?" . SID); $location = ($pos ? substr_replace($location, SID . "&", $pos + 1, 0) : "$location?" . SID);
@ -12,7 +19,7 @@ if (isset($_POST["server"])) {
redirect($location); redirect($location);
} }
$_GET["server"] = $_POST["server"]; $_GET["server"] = $_POST["server"];
} elseif (isset($_POST["logout"])) { } elseif ($_POST["logout"]) {
$token = $_SESSION["tokens"][$_GET["server"]]; $token = $_SESSION["tokens"][$_GET["server"]];
if ($token && $_POST["token"] != $token) { if ($token && $_POST["token"] != $token) {
page_header(lang('Logout'), lang('Invalid CSRF token. Send the form again.')); page_header(lang('Logout'), lang('Invalid CSRF token. Send the form again.'));
@ -25,8 +32,42 @@ if (isset($_POST["server"])) {
if (!isset($_SESSION["passwords"])) { // don't require login to logout if (!isset($_SESSION["passwords"])) { // don't require login to logout
$_SESSION["passwords"] = array(); $_SESSION["passwords"] = array();
} }
cookie("adminer_permanent", "");
redirect(substr(ME, 0, -1), lang('Logout successful.')); redirect(substr(ME, 0, -1), lang('Logout successful.'));
} }
} elseif ($_COOKIE["adminer_permanent"] && !isset($_SESSION["usernames"][$_GET["server"]])) {
list($server, $username, $cipher) = array_map('base64_decode', explode(":", $_COOKIE["adminer_permanent"]));
if (!strlen($_GET["server"]) || $server == $_GET["server"]) {
session_regenerate_id(); // defense against session fixation
$_SESSION["usernames"][$server] = $username;
$_SESSION["passwords"][$server] = decipher_password($cipher, pack("H*", sha1(str_pad($username, 1) . $adminer->permanentLogin())));
if (!$_POST && $server != $_GET["server"]) {
redirect(preg_replace('~^([^?]*).*~', '\\1', ME) . '?server=' . urlencode($server));
}
}
}
/** Cipher password
* @param string plain-text password
* @param string binary key, should be longer than $password
* @return string binary cipher
*/
function cipher_password($password, $key) {
$password2 = strlen($password) . ":" . str_pad($password, 17);
$repeat = ceil(strlen($password2) / strlen($key));
return $password2 ^ str_repeat($key, $repeat);
}
/** Decipher password
* @param string binary cipher
* @param string binary key
* @return string plain-text password
*/
function decipher_password($cipher, $key) {
$repeat = ceil(strlen($cipher) / strlen($key));
$password2 = $cipher ^ str_repeat($key, $repeat);
list($length, $password) = explode(":", $password2, 2);
return substr($password, 0, $length);
} }
function auth_error($exception = null) { function auth_error($exception = null) {

View file

@ -226,4 +226,5 @@ $translations = array(
'Editor' => 'Editor', 'Editor' => 'Editor',
'Webserver file %s' => 'Soubor %s na webovém serveru', 'Webserver file %s' => 'Soubor %s na webovém serveru',
'File does not exist.' => 'Soubor neexistuje.', 'File does not exist.' => 'Soubor neexistuje.',
'Permanent login' => 'Trvalé přihlášení',
); );

View file

@ -1,4 +1,5 @@
Adminer 2.2.2-dev: Adminer 2.2.2-dev:
Support for permanent login (customization required)
Add Delete button to Edit page (regression from 2.0.0) Add Delete button to Edit page (regression from 2.0.0)
Simplify SQL syntax error message Simplify SQL syntax error message
Print SQL query info if available Print SQL query info if available

View file

@ -11,6 +11,10 @@ class Adminer {
return array(); // default INI settings return array(); // default INI settings
} }
function permanentLogin() {
return "";
}
function database() { function database() {
global $connection; global $connection;
$dbs = get_databases(false); $dbs = get_databases(false);
@ -27,6 +31,9 @@ class Adminer {
<tr><th><?php echo lang('Password'); ?><td><input type="password" name="password"> <tr><th><?php echo lang('Password'); ?><td><input type="password" name="password">
</table> </table>
<?php <?php
if ($this->permanentLogin()) {
echo "<p>" . checkbox("permanent", 1, $_COOKIE["adminer_permanent"], lang('Permanent login')) . "\n";
}
} }
function login($login, $password) { function login($login, $password) {

View file

@ -7,7 +7,7 @@ Mass editation of individual rows
Offer enum and set items in search - whisperer Offer enum and set items in search - whisperer
Variables editation, especially timezone Variables editation, especially timezone
Use event $intervals + microseconds in relative date functions Use event $intervals + microseconds in relative date functions
Improve concurrency by calling session_write_close before executing command, message id will be sent in query string Optionally check IP address
? Column and table names auto-completition in SQL textarea ? Column and table names auto-completition in SQL textarea
? Aliasing of built-in functions can save 7 KB, function minification can save 7 KB, substitution of repetitive $a["a"] can save 4 KB, substitution of $_GET and friends can save 2 KB, JS packer can save 1 KB, not enclosing HTML attribute values can save 1.2 KB, replacing \\n by \n can save .3 KB ? Aliasing of built-in functions can save 7 KB, function minification can save 7 KB, substitution of repetitive $a["a"] can save 4 KB, substitution of $_GET and friends can save 2 KB, JS packer can save 1 KB, not enclosing HTML attribute values can save 1.2 KB, replacing \\n by \n can save .3 KB
? Branch binary_compile: LZW compression of translations can save 30 KB, LZW compression of all texts can save 11 KB, remove of base64_decode() + using chars 127-255 in minification can save 1 KB ? Branch binary_compile: LZW compression of translations can save 30 KB, LZW compression of all texts can save 11 KB, remove of base64_decode() + using chars 127-255 in minification can save 1 KB