public function processRequest() { $request = $this->getRequest(); $viewer = $request->getUser(); $conn_table = new PhabricatorConduitConnectionLog(); $call_table = new PhabricatorConduitMethodCallLog(); $conn_r = $call_table->establishConnection('r'); $pager = new AphrontCursorPagerView(); $pager->readFromRequest($request); $pager->setPageSize(500); $query = id(new PhabricatorConduitLogQuery())->setViewer($viewer); $methods = $request->getStrList('methods'); if ($methods) { $query->withMethods($methods); } $calls = $query->executeWithCursorPager($pager); $conn_ids = array_filter(mpull($calls, 'getConnectionID')); $conns = array(); if ($conn_ids) { $conns = $conn_table->loadAllWhere('id IN (%Ld)', $conn_ids); } $table = $this->renderCallTable($calls, $conns); $box = id(new PHUIObjectBoxView())->setHeaderText(pht('Call Logs'))->appendChild($table); $crumbs = $this->buildApplicationCrumbs(); $crumbs->addTextCrumb(pht('Call Logs')); return $this->buildApplicationPage(array($crumbs, $box, $pager), array('title' => pht('Conduit Logs'))); }
protected function collectGarbage() { $table = new PhabricatorConduitConnectionLog(); $conn_w = $table->establishConnection('w'); queryfx($conn_w, 'DELETE FROM %T WHERE dateCreated < %d ORDER BY dateCreated ASC LIMIT 100', $table->getTableName(), $this->getGarbageEpoch()); return $conn_w->getAffectedRows() == 100; }
public function collectGarbage() { $key = 'gcdaemon.ttl.conduit-logs'; $ttl = PhabricatorEnv::getEnvConfig($key); if ($ttl <= 0) { return false; } $table = new PhabricatorConduitConnectionLog(); $conn_w = $table->establishConnection('w'); queryfx($conn_w, 'DELETE FROM %T WHERE dateCreated < %d ORDER BY dateCreated ASC LIMIT 100', $table->getTableName(), time() - $ttl); return $conn_w->getAffectedRows() == 100; }
private function renderCallTable(array $calls, array $conns) { $user = $this->getRequest()->getUser(); $rows = array(); foreach ($calls as $call) { $conn = idx($conns, $call->getConnectionID()); if (!$conn) { // If there's no connection, use an empty object. $conn = new PhabricatorConduitConnectionLog(); } $rows[] = array($call->getConnectionID(), phutil_escape_html($conn->getUserName()), phutil_escape_html($call->getMethod()), phutil_escape_html($call->getError()), number_format($call->getDuration()) . ' us', phabricator_datetime($call->getDateCreated(), $user)); } $table = new AphrontTableView($rows); $table->setHeaders(array('Connection', 'User', 'Method', 'Error', 'Duration', 'Date')); $table->setColumnClasses(array('', '', 'wide', '', 'n', 'right')); return $table; }
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()); }