protected function execute(ConduitAPIRequest $request) { $client = $request->getValue('client'); $client_version = (int) $request->getValue('clientVersion'); $client_description = (string) $request->getValue('clientDescription'); $client_description = id(new PhutilUTF8StringTruncator())->setMaximumBytes(255)->truncateString($client_description); $username = (string) $request->getValue('user'); // Log the connection, regardless of the outcome of checks below. $connection = new PhabricatorConduitConnectionLog(); $connection->setClient($client); $connection->setClientVersion($client_version); $connection->setClientDescription($client_description); $connection->setUsername($username); $connection->save(); switch ($client) { case 'arc': $server_version = 6; $supported_versions = array($server_version => true, 4 => true, 5 => true); if (empty($supported_versions[$client_version])) { if ($server_version < $client_version) { $ex = new ConduitException('ERR-BAD-VERSION'); $ex->setErrorDescription(pht("Your '%s' client version is '%d', which is newer than the " . "server version, '%d'. Upgrade your Phabricator install.", 'arc', $client_version, $server_version)); } else { $ex = new ConduitException('NEW-ARC-VERSION'); $ex->setErrorDescription(pht('A new version of arc is available! You need to upgrade ' . 'to connect to this server (you are running version ' . '%d, the server is running version %d).', $client_version, $server_version)); } throw $ex; } break; default: // Allow new clients by default. break; } $token = $request->getValue('authToken'); $signature = $request->getValue('authSignature'); $user = id(new PhabricatorUser())->loadOneWhere('username = %s', $username); if (!$user) { throw new ConduitException('ERR-INVALID-USER'); } $session_key = null; if ($token && $signature) { $threshold = 60 * 15; $now = time(); if (abs($token - $now) > $threshold) { throw id(new ConduitException('ERR-INVALID-TOKEN'))->setErrorDescription(pht('The request you submitted is signed with a timestamp, but that ' . 'timestamp is not within %s of the current time. The ' . 'signed timestamp is %s (%s), and the current server time is ' . '%s (%s). This is a difference of %s seconds, but the ' . 'timestamp must differ from the server time by no more than ' . '%s seconds. Your client or server clock may not be set ' . 'correctly.', phutil_format_relative_time($threshold), $token, date('r', $token), $now, date('r', $now), $token - $now, $threshold)); } $valid = sha1($token . $user->getConduitCertificate()); if (!phutil_hashes_are_identical($valid, $signature)) { throw new ConduitException('ERR-INVALID-CERTIFICATE'); } $session_key = id(new PhabricatorAuthSessionEngine())->establishSession(PhabricatorAuthSession::TYPE_CONDUIT, $user->getPHID(), $partial = false); } else { throw new ConduitException('ERR-NO-CERTIFICATE'); } return array('connectionID' => $connection->getID(), 'sessionKey' => $session_key, 'userPHID' => $user->getPHID()); }
protected function execute(ConduitAPIRequest $request) { $this->validateHost($request->getValue('host')); $client = $request->getValue('client'); $client_version = (int) $request->getValue('clientVersion'); $client_description = (string) $request->getValue('clientDescription'); $username = (string) $request->getValue('user'); // Log the connection, regardless of the outcome of checks below. $connection = new PhabricatorConduitConnectionLog(); $connection->setClient($client); $connection->setClientVersion($client_version); $connection->setClientDescription($client_description); $connection->setUsername($username); $connection->save(); switch ($client) { case 'arc': $server_version = 3; switch ($client_version) { case $server_version: break; default: $ex = new ConduitException('ERR-BAD-VERSION'); if ($server_version < $client_version) { $upgrade = "Upgrade your Phabricator install."; } else { $upgrade = "Upgrade your 'arc' client."; } $ex->setErrorDescription("Your 'arc' client version is '{$client_version}', but this " . "server expects version '{$server_version}'. {$upgrade}"); throw $ex; } break; default: // Allow new clients by default. break; } $token = $request->getValue('authToken'); $signature = $request->getValue('authSignature'); $user = id(new PhabricatorUser())->loadOneWhere('username = %s', $username); if (!$user) { throw new ConduitException('ERR-INVALID-USER'); } $session_key = null; if ($token && $signature) { if (abs($token - time()) > 60 * 15) { throw new ConduitException('ERR-INVALID-TOKEN'); } $valid = sha1($token . $user->getConduitCertificate()); if ($valid != $signature) { throw new ConduitException('ERR-INVALID-CERTIFICATE'); } $session_key = $user->establishSession('conduit'); } else { throw new ConduitException('ERR-NO-CERTIFICATE'); } return array('connectionID' => $connection->getID(), 'sessionKey' => $session_key, 'userPHID' => $user->getPHID()); }
protected function execute(ConduitAPIRequest $request) { $this->validateHost($request->getValue('host')); $client = $request->getValue('client'); $client_version = (int) $request->getValue('clientVersion'); $client_description = (string) $request->getValue('clientDescription'); $username = (string) $request->getValue('user'); // Log the connection, regardless of the outcome of checks below. $connection = new PhabricatorConduitConnectionLog(); $connection->setClient($client); $connection->setClientVersion($client_version); $connection->setClientDescription($client_description); $connection->setUsername($username); $connection->save(); switch ($client) { case 'arc': $server_version = 5; $supported_versions = array($server_version => true, 4 => true); if (empty($supported_versions[$client_version])) { if ($server_version < $client_version) { $ex = new ConduitException('ERR-BAD-VERSION'); $ex->setErrorDescription("Your 'arc' client version is '{$client_version}', which " . "is newer than the server version, '{$server_version}'. " . "Upgrade your Phabricator install."); } else { $ex = new ConduitException('NEW-ARC-VERSION'); $ex->setErrorDescription("A new version of arc is available! You need to upgrade " . "to connect to this server (you are running version " . "{$client_version}, the server is running version " . "{$server_version})."); } throw $ex; } break; default: // Allow new clients by default. break; } $token = $request->getValue('authToken'); $signature = $request->getValue('authSignature'); $user = id(new PhabricatorUser())->loadOneWhere('username = %s', $username); if (!$user) { throw new ConduitException('ERR-INVALID-USER'); } $session_key = null; if ($token && $signature) { if (abs($token - time()) > 60 * 15) { throw new ConduitException('ERR-INVALID-TOKEN'); } $valid = sha1($token . $user->getConduitCertificate()); if ($valid != $signature) { throw new ConduitException('ERR-INVALID-CERTIFICATE'); } $session_key = $user->establishSession('conduit'); } else { throw new ConduitException('ERR-NO-CERTIFICATE'); } return array('connectionID' => $connection->getID(), 'sessionKey' => $session_key, 'userPHID' => $user->getPHID()); }