diff --git a/core/src/core/src/pydio/Core/Controller/CliRunner.php b/core/src/core/src/pydio/Core/Controller/CliRunner.php index 88f6719e6c..3c5c7dede1 100644 --- a/core/src/core/src/pydio/Core/Controller/CliRunner.php +++ b/core/src/core/src/pydio/Core/Controller/CliRunner.php @@ -105,11 +105,7 @@ public static function applyActionInBackground(ContextInterface $ctx, $actionNam $cmd .= " --$key=" . escapeshellarg($value); } } - $envSet = false; - if ($ctx->getRepository()->getContextOption($ctx, "USE_SESSION_CREDENTIALS")) { - $envSet = MemorySafe::setEnv(); - } - + $envSet = MemorySafe::setEnvForContext($ctx); // NOW RUN COMMAND $res = self::runCommandInBackground($cmd, $logFile); diff --git a/core/src/core/src/pydio/Core/Exception/PydioPromptException.php b/core/src/core/src/pydio/Core/Exception/PydioPromptException.php index b4b8f4c839..63579a4ee5 100644 --- a/core/src/core/src/pydio/Core/Exception/PydioPromptException.php +++ b/core/src/core/src/pydio/Core/Exception/PydioPromptException.php @@ -20,6 +20,7 @@ */ namespace Pydio\Core\Exception; +use Pydio\Core\Http\Middleware\WorkspaceAuthMiddleware; use Pydio\Core\Http\Response\JSONSerializableResponseChunk; use Pydio\Core\Http\Response\XMLSerializableResponseChunk; @@ -78,31 +79,33 @@ public function __construct($promptType, $data, $messageString, $messageId = fal /** * Prompt user for credentials * @param array $parameters - * @param string $passFieldName * @param string $postSubmitCallback - * @throws PydioPromptException + * @return PydioPromptException */ - public static function promptForWorkspaceCredentials($parameters, $passFieldName, $postSubmitCallback = ""){ - $hiddens = []; - $getFields = [$passFieldName]; + public static function promptForWorkspaceCredentials($parameters, $postSubmitCallback = ""){ + $inputs = []; foreach($parameters as $key => $value){ - $hiddens[] = ""; - $getFields[] = $key; + if($key === WorkspaceAuthMiddleware::FORM_RESUBMIT_LOGIN) { + $inputs[] = ""; + }else if($key === WorkspaceAuthMiddleware::FORM_RESUBMIT_PASS){ + $inputs[] = ""; + }else{ + $inputs[] = ""; + } } - throw new PydioPromptException( + return new PydioPromptException( "confirm", array( "DIALOG" => "

Credentials Required

-
Please provide a password to enter this workspace. You may have to manually redo the action you were currently trying to achieve.
+
Please provide a password to enter this workspace.
- ".implode("\n", $hiddens)." - + ".implode("\n", $inputs)."
", "OK" => array( - "GET_FIELDS" => $getFields, + "GET_FIELDS" => array_keys($parameters), "EVAL" => $postSubmitCallback ), "CANCEL" => array( diff --git a/core/src/core/src/pydio/Core/Exception/RepositoryLoadException.php b/core/src/core/src/pydio/Core/Exception/RepositoryLoadException.php index 40add21d70..0e6fbcf460 100644 --- a/core/src/core/src/pydio/Core/Exception/RepositoryLoadException.php +++ b/core/src/core/src/pydio/Core/Exception/RepositoryLoadException.php @@ -36,16 +36,16 @@ class RepositoryLoadException extends PydioException private $repository; /** * RepositoryLoadException constructor. - * @param RepositoryInterface|String $repository + * @param RepositoryInterface|String $workspace * @param array $errors */ - public function __construct($repository, $errors) + public function __construct($workspace, $errors) { - if($repository instanceof RepositoryInterface){ - $message = "Error while loading workspace ".$repository->getDisplay()." : ".implode("\n-", $errors); - $this->repository = $repository; + if($workspace instanceof RepositoryInterface){ + $message = "Error while loading workspace ".$workspace->getDisplay()." : ".implode("\n-", $errors); + $this->repository = $workspace; }else{ - $message = "Error while loading workspace ".$repository." : ".implode("\n-", $errors); + $message = "Error while loading workspace ".$workspace." : ".implode("\n-", $errors); } parent::__construct($message, false, 5000); } diff --git a/core/src/core/src/pydio/Core/Exception/WorkspaceAuthRequired.php b/core/src/core/src/pydio/Core/Exception/WorkspaceAuthRequired.php index 678f424a53..9b9f61656e 100644 --- a/core/src/core/src/pydio/Core/Exception/WorkspaceAuthRequired.php +++ b/core/src/core/src/pydio/Core/Exception/WorkspaceAuthRequired.php @@ -34,16 +34,19 @@ */ class WorkspaceAuthRequired extends PydioException { - private $repositoryId; + private $workspaceId; + private $requireLogin; /** * WorkspaceAuthRequired constructor. - * @param string $repositoryId + * @param string $workspaceId + * @param boolean $requireLogin * @param string $message */ - public function __construct($repositoryId, $message = "Authentication required for this workspace") + public function __construct($workspaceId, $requireLogin = false, $message = "Authentication required for this workspace") { - $this->repositoryId = $repositoryId; + $this->workspaceId = $workspaceId; + $this->requireLogin = $requireLogin; parent::__construct($message, false, null); } @@ -53,13 +56,31 @@ public function __construct($repositoryId, $message = "Authentication required f * @throws WorkspaceAuthRequired */ public static function testWorkspace($workspaceObject, $userObject){ - if($workspaceObject->getContextOption(Context::contextWithObjects($userObject, $workspaceObject), "USE_SESSION_CREDENTIALS") !== true){ + $ctx = Context::contextWithObjects($userObject, $workspaceObject); + $instanceId = MemorySafe::contextUsesInstance($ctx); + if($instanceId === false){ return; } - if(MemorySafe::loadCredentials() !== false){ + if(MemorySafe::loadCredentials($instanceId) !== false){ return; } - throw new WorkspaceAuthRequired($workspaceObject->getId()); + $allowFreeLogin = ($workspaceObject->getContextOption($ctx, "SESSION_CREDENTIALS_FREE_LOGIN") === true); + throw new WorkspaceAuthRequired($workspaceObject->getId(), $allowFreeLogin); } + /** + * @return string + */ + public function getWorkspaceId(){ + return $this->workspaceId; + } + + /** + * @return bool + */ + public function requiresLogin(){ + return $this->requireLogin; + } + + } \ No newline at end of file diff --git a/core/src/core/src/pydio/Core/Http/Cli/AuthCliMiddleware.php b/core/src/core/src/pydio/Core/Http/Cli/AuthCliMiddleware.php index 0cee2ddc80..67657ef3a9 100644 --- a/core/src/core/src/pydio/Core/Http/Cli/AuthCliMiddleware.php +++ b/core/src/core/src/pydio/Core/Http/Cli/AuthCliMiddleware.php @@ -76,6 +76,7 @@ protected static function authenticateFromCliParameters($options){ if($envPass !== false){ unset($optToken); $optPass = $envPass; + MemorySafe::storeCredentials($optUser, $optPass); } } diff --git a/core/src/core/src/pydio/Core/Http/Middleware/WorkspaceAuthMiddleware.php b/core/src/core/src/pydio/Core/Http/Middleware/WorkspaceAuthMiddleware.php index 28fc81a9c3..48c24bb072 100644 --- a/core/src/core/src/pydio/Core/Http/Middleware/WorkspaceAuthMiddleware.php +++ b/core/src/core/src/pydio/Core/Http/Middleware/WorkspaceAuthMiddleware.php @@ -22,6 +22,7 @@ use Psr\Http\Message\ResponseInterface; use Psr\Http\Message\ServerRequestInterface; +use Pydio\Access\Core\Model\AJXP_Node; use Pydio\Auth\Core\MemorySafe; use Pydio\Core\Exception\PydioException; @@ -30,6 +31,7 @@ use Pydio\Core\Http\Server; use Pydio\Core\Model\ContextInterface; use Pydio\Core\Services\SessionService; +use Pydio\Core\Utils\Vars\InputFilter; use Pydio\Core\Utils\Vars\StringHelper; defined('AJXP_EXEC') or die('Access not allowed'); @@ -47,7 +49,9 @@ class WorkspaceAuthMiddleware const RESUBMIT_AUTH_COUNT = "PYDIO_WORKSPACE_AUTH_RESUBMIT_COUNT"; const FORM_RESUBMIT_KEY = "workspace-auth-submission-id"; + const FORM_RESUBMIT_LOGIN = "workspace-auth-login"; const FORM_RESUBMIT_PASS = "workspace-auth-password"; + const FORM_SESSION_CREDS = "workspace-auth-test-session-credentials"; /** * @param ServerRequestInterface $requestInterface @@ -59,15 +63,33 @@ class WorkspaceAuthMiddleware public static function handleRequest(ServerRequestInterface $requestInterface, ResponseInterface $responseInterface, callable $next = null){ $vars = $requestInterface->getParsedBody(); + /** @var ContextInterface $ctx */ + $ctx = $requestInterface->getAttribute("ctx"); + if(isSet($vars[self::FORM_RESUBMIT_KEY]) && SessionService::has(self::RESUBMIT_AUTH_VARS."-".$vars[self::FORM_RESUBMIT_KEY]) && !empty($vars[self::FORM_RESUBMIT_PASS])){ $submittedId = $vars[self::FORM_RESUBMIT_KEY]; - // Count a max number of submission? - /** @var ContextInterface $ctx */ - $ctx = $requestInterface->getAttribute("ctx"); if($ctx->hasUser()){ + $userId = $ctx->getUser()->getId(); + } + if(isSet($vars[self::FORM_RESUBMIT_LOGIN]) && !empty($vars[self::FORM_RESUBMIT_LOGIN])){ + $userId = InputFilter::sanitize($vars[self::FORM_RESUBMIT_LOGIN], InputFilter::SANITIZE_EMAILCHARS); + } + + if(!empty($userId)){ $password = $vars[self::FORM_RESUBMIT_PASS]; - MemorySafe::storeCredentials($ctx->getUser()->getId(), $password); + if(isSet($vars[self::FORM_SESSION_CREDS])){ + $node = new AJXP_Node("pydio://".$userId."@".$vars[self::FORM_SESSION_CREDS]."/"); + try{ + MemorySafe::storeCredentials($userId, $password); + if(!is_writeable($node->getUrl())){ + MemorySafe::clearCredentials(); + } + }catch (\Exception $e){ + MemorySafe::clearCredentials(); + throw new PydioException($e->getMessage()); + } + } } $newVars = SessionService::fetch(self::RESUBMIT_AUTH_VARS."-".$submittedId); @@ -89,13 +111,21 @@ public static function handleRequest(ServerRequestInterface $requestInterface, R // Generate a random ID. $submissionId = StringHelper::generateRandomString(24); SessionService::save(self::RESUBMIT_AUTH_VARS."-".$submissionId, $vars); - $parameters = [self::FORM_RESUBMIT_KEY => $submissionId]; + $parameters = []; + if($ex->requiresLogin()){ + $parameters[self::FORM_RESUBMIT_LOGIN] = $ctx->hasUser() ? $ctx->getUser()->getId() : ""; + } + $parameters = array_merge($parameters, [ + self::FORM_RESUBMIT_KEY => $submissionId, + self::FORM_RESUBMIT_PASS => "", + self::FORM_SESSION_CREDS => $ex->getWorkspaceId() + ]); $postSubmitCallback = ""; if($requestInterface->getAttribute("action") === "switch_repository"){ $postSubmitCallback = "ajaxplorer.loadXmlRegistry();"; } // Will throw a prompt exception with all current values - return PydioPromptException::promptForWorkspaceCredentials($parameters, self::FORM_RESUBMIT_PASS, $postSubmitCallback); + throw PydioPromptException::promptForWorkspaceCredentials($parameters, $postSubmitCallback); } diff --git a/core/src/plugins/access.ajxp_conf/src/ConfAccessDriver.php b/core/src/plugins/access.ajxp_conf/src/ConfAccessDriver.php index a4169bd48f..9b2e29c31e 100644 --- a/core/src/plugins/access.ajxp_conf/src/ConfAccessDriver.php +++ b/core/src/plugins/access.ajxp_conf/src/ConfAccessDriver.php @@ -309,7 +309,6 @@ public function editAction(ServerRequestInterface $requestInterface, ResponseInt case "user_reorder_roles": case "users_bulk_update_roles": case "save_custom_user_params": - case "save_repository_user_params": case "update_user_pwd": $this->usersAction($requestInterface, $responseInterface); break; diff --git a/core/src/plugins/access.ajxp_conf/src/UsersManager.php b/core/src/plugins/access.ajxp_conf/src/UsersManager.php index fb28b30724..82c51827db 100644 --- a/core/src/plugins/access.ajxp_conf/src/UsersManager.php +++ b/core/src/plugins/access.ajxp_conf/src/UsersManager.php @@ -552,40 +552,7 @@ public function usersActions(ServerRequestInterface $requestInterface, ResponseI $responseInterface = $responseInterface->withBody(new SerializableResponseStream(new UserMessage($mess["ajxp_conf.47"].$userId))); break; - - case "save_repository_user_params" : - - $userId = InputFilter::sanitize($httpVars["user_id"], InputFilter::SANITIZE_EMAILCHARS); - $currentIsLogged = false; - if ($userId === $ctx->getUser()->getId()) { - $currentIsLogged = true; - $user = $ctx->getUser(); - } else { - $user = $this->getUserIfAuthorized($ctx, $userId); - } - - $wallet = $user->getPref("AJXP_WALLET"); - if(!is_array($wallet)) $wallet = array(); - $repoID = InputFilter::sanitize($httpVars["repository_id"], InputFilter::SANITIZE_ALPHANUM); - if (!array_key_exists($repoID, $wallet)) { - $wallet[$repoID] = array(); - } - $options = $wallet[$repoID]; - $existing = $options; - $newCtx = new Context($userId, $ctx->getRepositoryId()); - $this->parseParameters($newCtx, $httpVars, $options, false, $existing); - $wallet[$repoID] = $options; - $user->setPref("AJXP_WALLET", $wallet); - $user->save(); - - if ($currentIsLogged) { - AuthService::updateSessionUser($user); - } - - $responseInterface = $responseInterface->withBody(new SerializableResponseStream(new UserMessage($mess["ajxp_conf.47"].$userId))); - - break; - + case "update_user_pwd" : $userId = isSet($httpVars["user_id"]) ? InputFilter::sanitize($httpVars["user_id"], InputFilter::SANITIZE_EMAILCHARS) : null; diff --git a/core/src/plugins/access.fs/FsAccessDriver.php b/core/src/plugins/access.fs/FsAccessDriver.php index f13d94bc88..e98cca29db 100644 --- a/core/src/plugins/access.fs/FsAccessDriver.php +++ b/core/src/plugins/access.fs/FsAccessDriver.php @@ -2527,8 +2527,9 @@ public function makeSharedRepositoryOptions(ContextInterface $ctx, $httpVars) "DEFAULT_RIGHTS" => "", "DATA_TEMPLATE" => "" ]; - if ($repository->getContextOption($ctx, "USE_SESSION_CREDENTIALS") === true) { - $newOptions["ENCODED_CREDENTIALS"] = MemorySafe::getEncodedCredentialString(); + $sessionCredsInstance = MemorySafe::contextUsesInstance($ctx); + if($sessionCredsInstance !== false){ + $newOptions["ENCODED_CREDENTIALS"] = MemorySafe::getInstance($sessionCredsInstance)->getEncodedCredentials(); } $customData = []; foreach ($httpVars as $key => $value) { @@ -2543,7 +2544,7 @@ public function makeSharedRepositoryOptions(ContextInterface $ctx, $httpVars) $newOptions["META_SOURCES"] = $repository->getContextOption($ctx, "META_SOURCES"); foreach ($newOptions["META_SOURCES"] as $index => &$data) { if (isSet($data["USE_SESSION_CREDENTIALS"]) && $data["USE_SESSION_CREDENTIALS"] === true) { - $newOptions["META_SOURCES"][$index]["ENCODED_CREDENTIALS"] = MemorySafe::getEncodedCredentialString(); + $newOptions["META_SOURCES"][$index]["ENCODED_CREDENTIALS"] = MemorySafe::getInstance()->getEncodedCredentials(); } } Controller::applyHook("workspace.share_metasources", [$ctx, &$newOptions["META_SOURCES"]]); diff --git a/core/src/plugins/access.smb/manifest.xml b/core/src/plugins/access.smb/manifest.xml index ad1b11fa73..a96ac86ec8 100644 --- a/core/src/plugins/access.smb/manifest.xml +++ b/core/src/plugins/access.smb/manifest.xml @@ -10,6 +10,7 @@ + diff --git a/core/src/plugins/authfront.cas/CasAuthFrontend.php b/core/src/plugins/authfront.cas/CasAuthFrontend.php index 96080fbbad..a050d78647 100644 --- a/core/src/plugins/authfront.cas/CasAuthFrontend.php +++ b/core/src/plugins/authfront.cas/CasAuthFrontend.php @@ -241,7 +241,7 @@ function tryToLogUser(ServerRequestInterface &$request, ResponseInterface &$resp try { $userObj = AuthService::logUser($cas_user, "", true); AuthService::updateSessionUser($userObj); - MemorySafe::storeCredentials($cas_user, $_SESSION['PROXYTICKET']); + MemorySafe::storeCredentials($cas_user, $_SESSION['PROXYTICKET'], 'authfront.cas'); $_SESSION['LOGGED_IN_BY_CAS'] = true; if (!empty($this->cas_additional_role)) { diff --git a/core/src/plugins/core.ajaxplorer/ajxp_mixins.xml b/core/src/plugins/core.ajaxplorer/ajxp_mixins.xml index c62c1ce8fc..ec5e1a2695 100644 --- a/core/src/plugins/core.ajaxplorer/ajxp_mixins.xml +++ b/core/src/plugins/core.ajaxplorer/ajxp_mixins.xml @@ -5,7 +5,8 @@ - + + diff --git a/core/src/plugins/core.auth/MemorySafe.php b/core/src/plugins/core.auth/MemorySafe.php index eba8c3af0a..6844dd7732 100644 --- a/core/src/plugins/core.auth/MemorySafe.php +++ b/core/src/plugins/core.auth/MemorySafe.php @@ -39,97 +39,79 @@ class MemorySafe const SAFE_CREDENTIALS_KEY = "PYDIO_SAFE_CREDENTIALS"; - private static $instance; + private static $instances; + private $instanceId = ""; private $user; private $encodedPassword; private $secretKey; private $separator = "__SAFE_SEPARATOR__"; private $forceSessionCredentials = false; + /** * Instance constructor + * @param string $instanceId */ - public function __construct() + public function __construct($instanceId = "") { $this->secretKey = Crypto::getApplicationSecret(); + $this->instanceId = $instanceId; } + /** - * Store the user/password pair. Password will be encoded - * @param string $user - * @param string $password - * @return void + * @return null|string */ - public function setCredentials($user, $password) - { - $this->user = $user; - $this->encodedPassword = $this->_encodePassword($password, $user); + public function getEncodedCredentials(){ + return SessionService::fetch(self::SAFE_CREDENTIALS_KEY.$this->instanceId); } + + /**********************/ + /* STATIC ENV METHODS */ + /**********************/ /** - * Return the user/password pair, or false if cannot find it. - * @return array|bool + * @param ContextInterface $ctx + * @return bool|string FALSE if no need, or String (warning, it can be an empty string) if instance needed. */ - public function getCredentials() - { - if (isSet($this->user) && isSet($this->encodedPassword)) { - $decoded = $this->_decodePassword($this->encodedPassword, $this->user); - return array( - "user" => $this->user, - "password" => $decoded, - 0 => $this->user, - 1 => $decoded - ); - } else { - return false; + public static function contextUsesInstance($ctx){ + if ($ctx->getRepository()->getContextOption($ctx, "USE_SESSION_CREDENTIALS")) { + $instanceId = $ctx->getRepository()->getContextOption($ctx, "SESSION_CREDENTIALS_AUTHFRONT", null); + if (empty($instanceId)) $instanceId = ""; + return $instanceId; } + return false; } + /** - * Use mcrypt function to encode the password - * @param $password - * @param $user - * @return string - */ - private function _encodePassword($password, $user) - { - return Crypto::encrypt($password, Crypto::buildKey($user, $this->secretKey)); - } - /** - * Use mcrypt functions to decode the password - * @param $encoded - * @param $user - * @return string - */ - private function _decodePassword($encoded, $user) - { - return Crypto::decrypt($encoded, Crypto::buildKey($user, $this->secretKey, $encoded)); - } - /** - * Store the password credentials in the session - * @return void + * @param ContextInterface $ctx + * @return bool */ - public function store() { - SessionService::save(self::SAFE_CREDENTIALS_KEY, base64_encode($this->user.$this->separator.$this->encodedPassword)); + public static function setEnvForContext($ctx){ + $instanceId = self::contextUsesInstance($ctx); + if($instanceId !== false){ + return self::setEnv($instanceId); + } + return false; } - /** * Set the encrypted string in the environment for running a CLI. + * @param string * @return bool */ - public static function setEnv(){ - $encodedCreds = self::getEncodedCredentialString(); + public static function setEnv($instanceId = ""){ + // Pass Default Instance Credentials + $encodedCreds = self::getInstance($instanceId)->getEncodedCredentials(); if (!empty($encodedCreds)) { putenv(self::SAFE_CREDENTIALS_KEY. "=" . $encodedCreds); return true; } return false; } - /** * Clear the environment variable */ public static function clearEnv(){ putenv(self::SAFE_CREDENTIALS_KEY); } - /** * Try to load encrypted string, decode, and get password if the user is corresponding. * @param string $userId @@ -146,32 +128,6 @@ public static function loadPasswordStringFromEnvironment($userId){ return false; } - /** - * Load the credentials from session - * @param string $encodedString - * @return void - */ - public function load($encodedString = "") - { - if ($encodedString == "" && SessionService::has(self::SAFE_CREDENTIALS_KEY)) { - $encodedString = SessionService::fetch(self::SAFE_CREDENTIALS_KEY); - } - if(empty($encodedString)) return; - $sessData = base64_decode($encodedString); - $parts = explode($this->separator, $sessData); - $this->user = $parts[0]; - $this->encodedPassword = $parts[1]; - } - /** - * Remove the credentials from session - * @return void - */ - public function clear() - { - SessionService::delete(self::SAFE_CREDENTIALS_KEY); - $this->user = null; - $this->encodedPassword = null; - } /** * For the session credentials to override other credentials set via config * @return void @@ -181,60 +137,66 @@ public function forceSessionCredentialsUsage() $this->forceSessionCredentials = true; } - - + /****************************/ + /* STATIC INSTANCE METHODS */ + /****************************/ /** * Creates the singleton instance + * @param string $instanceId * @return MemorySafe */ - public static function getInstance() + public static function getInstance($instanceId = '') { - if (empty(self::$instance)) { - self::$instance = new MemorySafe(); + $instanceKey = $instanceId; + if(empty($instanceKey)) { + $instanceKey = '__DEFAULT__'; + } + if (empty(self::$instances)) { + self::$instances = []; } - return self::$instance; + if(!isSet(self::$instances[$instanceKey])){ + self::$instances[$instanceKey] = new MemorySafe($instanceId); + } + return self::$instances[$instanceKey]; } /** * Store the user/pass key pair * @static * @param string $user * @param string $password + * @param string $instanceId * @return void */ - public static function storeCredentials($user, $password) + public static function storeCredentials($user, $password, $instanceId = '') { - $inst = MemorySafe::getInstance(); + $inst = MemorySafe::getInstance($instanceId); $inst->setCredentials($user, $password); $inst->store(); } /** * Remove the user/pass encoded from the session + * @param string $instanceId * @static * @return void */ - public static function clearCredentials() + public static function clearCredentials($instanceId = '') { - $inst = MemorySafe::getInstance(); + $inst = MemorySafe::getInstance($instanceId); $inst->clear(); } /** * Retrieve the user/pass from the session + * @param string $instanceId * @static * @return array|bool */ - public static function loadCredentials() + public static function loadCredentials($instanceId = '') { - $inst = MemorySafe::getInstance(); + $inst = MemorySafe::getInstance($instanceId); $inst->load(); return $inst->getCredentials(); } - /** - * @return mixed - */ - public static function getEncodedCredentialString() { - return SessionService::fetch(self::SAFE_CREDENTIALS_KEY); - } /** * @param $encoded @@ -246,11 +208,10 @@ public static function getCredentialsFromEncodedString($encoded) $tmpInstance->load($encoded); return $tmpInstance->getCredentials(); } - /** * Will try to get the credentials for a given repository as follow : * + Try to get the credentials from the url parsing - * + Try to get them from the user "Wallet" (personal data) + * + Try to get them from the user merged role * + Try to get them from the repository configuration * + Try to get them from the MemorySafe. * @@ -265,26 +226,7 @@ public static function tryLoadingCredentialsFromSources($ctx) if ($repository->getAccessType() == "ftp") { $optionsPrefix = "FTP_"; } - // Get USER/PASS - // 1. Try from URL - /* - if (isSet($parsedUrl["user"]) && isset($parsedUrl["pass"])) { - $user = rawurldecode($parsedUrl["user"]); - $password = rawurldecode($parsedUrl["pass"]); - } - */ - // 2. Try from user wallet - if ($user=="") { - $loggedUser = $ctx->getUser(); - if ($loggedUser != null) { - $wallet = $loggedUser->getPref("AJXP_WALLET"); - if (is_array($wallet) && isSet($wallet[$repository->getId()][$optionsPrefix."USER"])) { - $user = $wallet[$repository->getId()][$optionsPrefix."USER"]; - $password = OptionsHelper::decypherStandardFormPassword($loggedUser->getId(), $wallet[$repository->getId()][$optionsPrefix . "PASS"]); - } - } - } - // 2bis. Wallet is now a custom parameter + // 1. Look in Role parameters if ($user =="") { $loggedUser = $ctx->getUser(); if ($loggedUser != null) { @@ -296,16 +238,16 @@ public static function tryLoadingCredentialsFromSources($ctx) } } } - // 3. Try from repository config + // 2. Try from repository config if ($user=="") { $user = $repository->getContextOption($ctx, $optionsPrefix."USER"); $password = $repository->getContextOption($ctx, $optionsPrefix."PASS"); } - // 4. Test if there are encoded credentials available + // 3. Test if there are encoded credentials available if ($user == "" && $repository->getContextOption($ctx, "ENCODED_CREDENTIALS") != "") { list($user, $password) = MemorySafe::getCredentialsFromEncodedString($repository->getContextOption($ctx, "ENCODED_CREDENTIALS")); } - // 5. Try from session + // 4. Try from session $storeCreds = false; if ($repository->getContextOption($ctx, "META_SOURCES")) { $options["META_SOURCES"] = $repository->getContextOption($ctx, "META_SOURCES"); @@ -317,7 +259,9 @@ public static function tryLoadingCredentialsFromSources($ctx) } } if ($user=="" && ( $repository->getContextOption($ctx, "USE_SESSION_CREDENTIALS") || $storeCreds || self::getInstance()->forceSessionCredentials )) { - $safeCred = MemorySafe::loadCredentials(); + $instanceId = $repository->getContextOption($ctx, "SESSION_CREDENTIALS_AUTHFRONT"); + $instanceId = empty($instanceId) ? "" : $instanceId; + $safeCred = MemorySafe::loadCredentials($instanceId); if ($safeCred !== false) { $user = $safeCred["user"]; $password = $safeCred["password"]; @@ -327,4 +271,92 @@ public static function tryLoadingCredentialsFromSources($ctx) } + /*******************/ + /* PRIVATE METHODS */ + /*******************/ + + /** + * Store the user/password pair. Password will be encoded + * @param string $user + * @param string $password + * @return void + */ + private function setCredentials($user, $password) + { + $this->user = $user; + $this->encodedPassword = $this->_encodePassword($password, $user); + } + /** + * Return the user/password pair, or false if cannot find it. + * @return array|bool + */ + private function getCredentials() + { + if (isSet($this->user) && isSet($this->encodedPassword)) { + $decoded = $this->_decodePassword($this->encodedPassword, $this->user); + return array( + "user" => $this->user, + "password" => $decoded, + 0 => $this->user, + 1 => $decoded + ); + } else { + return false; + } + } + /** + * Use mcrypt function to encode the password + * @param $password + * @param $user + * @return string + */ + private function _encodePassword($password, $user) + { + return Crypto::encrypt($password, Crypto::buildKey($user, $this->secretKey)); + } + /** + * Use mcrypt functions to decode the password + * @param $encoded + * @param $user + * @return string + */ + private function _decodePassword($encoded, $user) + { + return Crypto::decrypt($encoded, Crypto::buildKey($user, $this->secretKey, $encoded)); + } + /** + * Store the password credentials in the session + * @return void + */ + private function store() { + SessionService::save(self::SAFE_CREDENTIALS_KEY.$this->instanceId, base64_encode($this->user.$this->separator.$this->encodedPassword)); + } + /** + * Load the credentials from session + * @param string $encodedString + * @return void + */ + private function load($encodedString = "") + { + if ($encodedString == "" && SessionService::has(self::SAFE_CREDENTIALS_KEY.$this->instanceId)) { + $encodedString = SessionService::fetch(self::SAFE_CREDENTIALS_KEY.$this->instanceId); + } + if(empty($encodedString)) return; + $sessData = base64_decode($encodedString); + $parts = explode($this->separator, $sessData); + $this->user = $parts[0]; + $this->encodedPassword = $parts[1]; + } + /** + * Remove the credentials from session + * @return void + */ + private function clear() + { + SessionService::delete(self::SAFE_CREDENTIALS_KEY.$this->instanceId); + $this->user = null; + $this->encodedPassword = null; + } + + } diff --git a/core/src/plugins/core.conf/AbstractUser.php b/core/src/plugins/core.conf/AbstractUser.php index 7c60fb32c3..84a3d4d68e 100644 --- a/core/src/plugins/core.conf/AbstractUser.php +++ b/core/src/plugins/core.conf/AbstractUser.php @@ -698,19 +698,7 @@ protected function migrateRightsToPersonalRole() } } } - - // Move old WALLET values to personal role parameter - $wallet = $this->getPref("AJXP_WALLET"); - if (is_array($wallet) && count($wallet)) { - foreach ($wallet as $repositoryId => $walletData) { - $repoObject = RepositoryService::getRepositoryById($repositoryId); - if($repoObject == null) continue; - $accessType = "access.".$repoObject->getAccessType(); - foreach ($walletData as $paramName => $paramValue) { - $this->personalRole->setParameterValue($accessType, $paramName, $paramValue, $repositoryId); - } - } - } + return $changes; } diff --git a/core/src/plugins/gui.ajax/res/themes/orbit/css/pydio.css b/core/src/plugins/gui.ajax/res/themes/orbit/css/pydio.css index 787bf8a580..59c3ceb3db 100644 --- a/core/src/plugins/gui.ajax/res/themes/orbit/css/pydio.css +++ b/core/src/plugins/gui.ajax/res/themes/orbit/css/pydio.css @@ -6328,10 +6328,16 @@ div.dialogButtons.inlineEdition input { .dialogBox.simple-modal-auth-prompt .dialogContent h3 { color: rgba(0, 0, 0, 0.73); } -.dialogBox.simple-modal-auth-prompt .dialogContent input[type="password"] { +.dialogBox.simple-modal-auth-prompt .dialogContent input[type="password"], +.dialogBox.simple-modal-auth-prompt .dialogContent input[type="text"] { margin-top: 10px; font-size: 13px !important; } +@media only screen and (max-width: 420px) { + .dialogBox.simple-modal-auth-prompt { + left: 80px; + } +} .toolbars_buttons_mixin { box-sizing: border-box; height: 30px; diff --git a/core/src/plugins/gui.ajax/res/themes/orbit/css/theme/dialogs.less b/core/src/plugins/gui.ajax/res/themes/orbit/css/theme/dialogs.less index 48d9a36162..3aa8ae552e 100644 --- a/core/src/plugins/gui.ajax/res/themes/orbit/css/theme/dialogs.less +++ b/core/src/plugins/gui.ajax/res/themes/orbit/css/theme/dialogs.less @@ -152,9 +152,13 @@ div.dialogButtons.inlineEdition{ h3{ color: rgba(0,0,0,0.73); } - input[type="password"] { + input[type="password"], input[type="text"] { margin-top: 10px; font-size: 13px !important; } } + @media only screen + and (max-width : 420px) { + left:80px; + } } \ No newline at end of file