/**
  * Gets the user that solved more problems during last month
  * 
  * @global type $conn
  * @param string (date) $firstDay
  * @return null|Users
  */
 public static function calculateCoderOfTheMonth($firstDay)
 {
     $endTime = $firstDay;
     $startTime = null;
     $lastMonth = intval(date('m')) - 1;
     if ($lastMonth === 0) {
         // First month of the year, we need to check into last month of last year.
         $lastYear = intval(date('Y')) - 1;
         $startTime = date($lastYear . '-12-01');
     } else {
         $startTime = date('Y-' . $lastMonth . '-01');
     }
     $sql = "\n\t\t\tSELECT\n\t\t\t\tusername, name, up.user_id, COUNT(ps.problem_id) ProblemsSolved, SUM(ROUND(100 / LOG(2, ps.accepted+1) , 0)) score\n\t\t\tFROM\n\t\t\t\t(\n\t\t\t\t\tSELECT DISTINCT\n\t\t\t\t\t\tr.user_id, r.problem_id\n\t\t\t\t\tFROM\n\t\t\t\t\t\tRuns r\n\t\t\t\t\tWHERE\n\t\t\t\t\t\tr.verdict = 'AC' AND r.test = 0 AND \n\t\t\t\t\t\tr.time >= ? AND \n\t\t\t\t\t\tr.time <= ?\n\t\t\t\t) AS up\n\t\t\tINNER JOIN\n\t\t\t\tProblems ps ON ps.problem_id = up.problem_id and ps.public = 1\n\t\t\tINNER JOIN\n\t\t\t\tUsers u ON u.user_id = up.user_id \n\t\t\tGROUP BY\n\t\t\t\tuser_id\n\t\t\tORDER BY\n\t\t\t\tscore DESC\n\t\t\tLIMIT 1\n\t\t";
     $val = array($startTime, $endTime);
     global $conn;
     $rs = $conn->GetRow($sql, $val);
     if (count($rs) == 0) {
         return NULL;
     }
     $totalCount = $rs['ProblemsSolved'];
     $user = UsersDAO::getByPK($rs['user_id']);
     $score = $rs['score'];
     return array("totalCount" => $totalCount, "user" => $user, "score" => $score);
 }
 /**
  * Test that we are able to submit a problem without testplan
  */
 public function testValidProblemNoTestplan()
 {
     // Get the problem data
     $problemData = ProblemsFactory::getRequest(OMEGAUP_RESOURCES_ROOT . 'triangulos.zip');
     $r = $problemData['request'];
     $problemAuthor = $problemData['author'];
     // Login user
     $r['auth_token'] = $this->login($problemAuthor);
     // Get File Uploader Mock and tell Omegaup API to use it
     FileHandler::SetFileUploader($this->createFileUploaderMock());
     // Call the API
     $response = ProblemController::apiCreate($r);
     // Validate
     // Verify response
     $this->assertEquals('ok', $response['status']);
     $this->assertEquals('cases/1.in', $response['uploaded_files'][0]);
     // Verify data in DB
     $problem_mask = new Problems();
     $problem_mask->setTitle($r['title']);
     $problems = ProblemsDAO::search($problem_mask);
     // Check that we only retreived 1 element
     $this->assertEquals(1, count($problems));
     $problem = $problems[0];
     // Verify contest was found
     $this->assertNotNull($problem);
     $this->assertNotNull($problem->getProblemId());
     // Verify DB data
     $this->assertEquals($r['title'], $problem->getTitle());
     $this->assertEquals(substr($r['title'], 0, 32), $problem->getAlias());
     $this->assertEquals($r['validator'], $problem->getValidator());
     $this->assertEquals($r['time_limit'], $problem->getTimeLimit());
     $this->assertEquals($r['memory_limit'], $problem->getMemoryLimit());
     $this->assertEquals($r['order'], $problem->getOrder());
     $this->assertEquals($r['source'], $problem->getSource());
     // Verify author username -> author id conversion
     $user = UsersDAO::getByPK($problem->getAuthorId());
     $this->assertEquals($user->getUsername(), $r['author_username']);
     // Verify problem contents were copied
     $targetpath = PROBLEMS_PATH . DIRECTORY_SEPARATOR . $problem->getAlias() . DIRECTORY_SEPARATOR;
     $this->assertFileExists($targetpath . 'cases');
     $this->assertFileExists($targetpath . 'statements' . DIRECTORY_SEPARATOR . 'es.html');
     // Default data
     $this->assertEquals(0, $problem->getVisits());
     $this->assertEquals(0, $problem->getSubmissions());
     $this->assertEquals(0, $problem->getAccepted());
     $this->assertEquals(0, $problem->getDifficulty());
 }
 /**
  * Returns the list of coders of the month
  *
  * @param Request $r
  */
 public static function apiCoderOfTheMonthList(Request $r)
 {
     $response = array();
     $response['coders'] = array();
     try {
         $coders = CoderOfTheMonthDAO::getAll(null, null, 'time', 'DESC');
         foreach ($coders as $c) {
             $user = UsersDAO::getByPK($c->user_id);
             $email = EmailsDAO::getByPK($user->getMainEmailId());
             $response['coders'][] = array('username' => $user->getUsername(), 'gravatar_32' => 'https://secure.gravatar.com/avatar/' . md5($email->getEmail()) . '?s=32', 'date' => $c->getTime());
         }
     } catch (Exception $ex) {
         throw new InvalidDatabaseOperationException($e);
     }
     $response['status'] = 'ok';
     return $response;
 }
 /**
  * Details of a scoreboard. Returns a list with all contests that belong to
  * the given scoreboard_alias
  * 
  * @param Request $r
  */
 public static function apiDetails(Request $r)
 {
     self::validateGroupScoreboard($r);
     $response = array();
     // Fill contests
     $response["contests"] = array();
     $response["ranking"] = array();
     try {
         $groupScoreboardContestKey = new GroupsScoreboardsContests(array("group_scoreboard_id" => $r["scoreboard"]->group_scoreboard_id));
         $r["gscs"] = GroupsScoreboardsContestsDAO::search($groupScoreboardContestKey);
         $i = 0;
         $contest_params = array();
         foreach ($r["gscs"] as $gsc) {
             $contest = ContestsDAO::getByPK($gsc->contest_id);
             $response["contests"][$i] = $contest->asArray();
             $response["contests"][$i]["only_ac"] = $gsc->only_ac;
             $response["contests"][$i]["weight"] = $gsc->weight;
             // Fill contest params to pass to scoreboardMerge
             $contest_params[$contest->alias] = array("only_ac" => $gsc->only_ac == 0 ? false : true, "weight" => $gsc->weight);
             $i++;
         }
     } catch (ApiException $ex) {
         throw $ex;
     } catch (Exception $ex) {
         throw new InvalidDatabaseOperationException($ex);
     }
     $r["contest_params"] = $contest_params;
     // Fill details of this scoreboard
     $response["scoreboard"] = $r["scoreboard"]->asArray();
     // If we have contests, calculate merged&filtered scoreboard
     if (count($response["contests"]) > 0) {
         // Get merged scoreboard
         $r["contest_aliases"] = "";
         foreach ($response["contests"] as $contest) {
             $r["contest_aliases"] .= $contest["alias"] . ",";
         }
         $r["contest_aliases"] = rtrim($r["contest_aliases"], ",");
         try {
             $groupUsers = GroupsUsersDAO::search(new GroupsUsers(array("group_id" => $r["scoreboard"]->group_id)));
             $r["usernames_filter"] = "";
             foreach ($groupUsers as $groupUser) {
                 $user = UsersDAO::getByPK($groupUser->user_id);
                 $r["usernames_filter"] .= $user->username . ",";
             }
             $r["usernames_filter"] = rtrim($r["usernames_filter"], ",");
         } catch (Exception $ex) {
             throw new InvalidDatabaseOperationException($ex);
         }
         $mergedScoreboardResponse = ContestController::apiScoreboardMerge($r);
         $response["ranking"] = $mergedScoreboardResponse["ranking"];
     }
     $response["status"] = "ok";
     return $response;
 }
 public function LoginViaFacebook()
 {
     //ok, the user does not have any auth token
     //if he wants to test facebook login
     //Facebook must send me the state=something
     //query, so i dont have to be testing
     //facebook sessions on every single petition
     //made from the front-end
     if (!isset($_GET['state'])) {
         return false;
     }
     //if that is not true, may still be logged with
     //facebook, lets test that
     $facebook = self::getFacebookInstance();
     // Get User ID
     $fb_user = $facebook->getUser();
     if ($fb_user == 0) {
         self::$log->info('FB session unavailable.');
         return false;
     }
     // We may or may not have this data based on whether the user is logged in.
     // If we have a $fb_user id here, it means we know the user is logged into
     // Facebook, but we don't know if the access token is valid. An access
     // token is invalid if the user logged out of Facebook.
     try {
         // Proceed knowing you have a logged in user who's authenticated.
         $fb_user_profile = $facebook->api('/me');
     } catch (FacebookApiException $e) {
         $fb_user = null;
         self::$log->error('FacebookException:' . $e);
         return false;
     }
     //ok we know the user is logged in,
     //lets look for his information on the database
     //if there is none, it means that its the first
     //time the user has been here, lets register his info
     self::$log->info('User is logged in via facebook !!');
     $results = UsersDAO::FindByEmail($fb_user_profile['email']);
     if (!is_null($results)) {
         //user has been here before with facebook!
         $vo_User = $results;
         self::$log->info('user has been here before with facebook!');
     } else {
         // The user has never been here before, let's register him
         // I have a problem with this:
         $username = self::getUniqueUsernameFromEmail($fb_user_profile['email']);
         // Even if the user gave us his/her email, we should not
         // just go ahead and assume its ok to share with the world
         // maybe we could do:
         // $username = str_replace(" ", "_", $fb_user_profile["name"] ),
         UserController::$permissionKey = uniqid();
         $r = new Request(array('name' => $fb_user_profile['name'], 'username' => $username, 'email' => $fb_user_profile['email'], 'facebook_user_id' => $fb_user_profile['id'], 'password' => null, 'permission_key' => UserController::$permissionKey, 'ignore_password' => true));
         try {
             $res = UserController::apiCreate($r);
         } catch (ApiException $e) {
             self::$log->error('Unable to login via Facebook ' . $e);
             return false;
         }
         $vo_User = UsersDAO::getByPK($res['user_id']);
     }
     //since we got here, this user does not have
     //any auth token, lets give him one
     //so we dont have to call facebook to see
     //if he is still logged in, and he can call
     //the api
     $this->RegisterSession($vo_User);
 }
Beispiel #6
0
 /**
  * Returns ALL users participating in a contest
  *
  * @param Request $r
  * @return array
  * @throws InvalidDatabaseOperationException
  */
 public static function apiUsers(Request $r)
 {
     // Authenticate request
     self::authenticateRequest($r);
     Validators::isStringNonEmpty($r["contest_alias"], "contest_alias");
     try {
         $contest = ContestsDAO::getByAlias($r["contest_alias"]);
     } catch (Exception $e) {
         throw new InvalidDatabaseOperationException($e);
     }
     if (!Authorization::IsContestAdmin($r["current_user_id"], $contest)) {
         throw new ForbiddenAccessException();
     }
     // Get users from DB
     $contest_user_key = new ContestsUsers();
     $contest_user_key->setContestId($contest->getContestId());
     try {
         $db_results = ContestsUsersDAO::search($contest_user_key);
     } catch (Exception $e) {
         // Operation failed in the data layer
         throw new InvalidDatabaseOperationException($e);
     }
     $users = array();
     // Add all users to an array
     foreach ($db_results as $result) {
         $user_id = $result->getUserId();
         $user = UsersDAO::getByPK($user_id);
         $users[] = array("user_id" => $user_id, "username" => $user->getUsername(), 'access_time' => $result->access_time, 'country' => $user->getCountryId());
     }
     $response = array();
     $response["users"] = $users;
     $response["status"] = "ok";
     return $response;
 }
 /**
  * Entry point for Problem Details API
  *
  * @param Request $r
  * @throws InvalidFilesystemOperationException
  * @throws InvalidDatabaseOperationException
  */
 public static function apiDetails(Request $r)
 {
     // Get user.
     // Allow unauthenticated requests if we are not openning a problem
     // inside a contest.
     try {
         self::authenticateRequest($r);
     } catch (UnauthorizedException $e) {
         if (!is_null($r['contest_alias'])) {
             throw $e;
         }
     }
     // Validate request
     self::validateDetails($r);
     $response = array();
     // Create array of relevant columns
     $relevant_columns = array('title', 'alias', 'validator', 'time_limit', 'validator_time_limit', 'overall_wall_time_limit', 'extra_wall_time', 'memory_limit', 'output_limit', 'visits', 'submissions', 'accepted', 'difficulty', 'creation_date', 'source', 'order', 'points', 'public', 'languages', 'slow', 'stack_limit', 'email_clarifications');
     // Read the file that contains the source
     if (!ProblemController::isLanguageSupportedForProblem($r)) {
         // If there is no language file for the problem, return the spanish version.
         $r['lang'] = 'es';
     }
     $statement_type = ProblemController::getStatementType($r);
     Cache::getFromCacheOrSet(Cache::PROBLEM_STATEMENT, $r['problem']->getAlias() . '-' . $r['lang'] . '-' . $statement_type, $r, 'ProblemController::getProblemStatement', $file_content, APC_USER_CACHE_PROBLEM_STATEMENT_TIMEOUT);
     // Add problem statement to source
     $response['problem_statement'] = $file_content;
     $response['problem_statement_language'] = $r['lang'];
     // Add the example input.
     $sample_input = null;
     Cache::getFromCacheOrSet(Cache::PROBLEM_SAMPLE, $r['problem']->getAlias() . '-sample.in', $r, 'ProblemController::getSampleInput', $sample_input, APC_USER_CACHE_PROBLEM_STATEMENT_TIMEOUT);
     if (!empty($sample_input)) {
         $response['sample_input'] = $sample_input;
     }
     // Add the problem the response
     $response = array_merge($response, $r['problem']->asFilteredArray($relevant_columns));
     // If the problem is public or if the user has admin privileges, show the
     // problem source and alias of owner.
     if ($r['problem']->public || Authorization::IsProblemAdmin($r['current_user_id'], $r['problem'])) {
         $problemsetter = UsersDAO::getByPK($r['problem']->author_id);
         if (!is_null($problemsetter)) {
             $response['problemsetter'] = array('username' => $problemsetter->username, 'name' => is_null($problemsetter->name) ? $problemsetter->username : $problemsetter->name);
         }
     } else {
         unset($response['source']);
     }
     if (!is_null($r['current_user_id'])) {
         // Create array of relevant columns for list of runs
         $relevant_columns = array('guid', 'language', 'status', 'verdict', 'runtime', 'penalty', 'memory', 'score', 'contest_score', 'time', 'submit_delay');
         // Search the relevant runs from the DB
         $contest = ContestsDAO::getByAlias($r['contest_alias']);
         $keyrun = new Runs(array('user_id' => $r['current_user_id'], 'problem_id' => $r['problem']->getProblemId(), 'contest_id' => is_null($r['contest']) ? null : $r['contest']->getContestId()));
         // Get all the available runs done by the current_user
         try {
             $runs_array = RunsDAO::search($keyrun);
         } catch (Exception $e) {
             // Operation failed in the data layer
             throw new InvalidDatabaseOperationException($e);
         }
         // Add each filtered run to an array
         if (count($runs_array) >= 0) {
             $runs_filtered_array = array();
             foreach ($runs_array as $run) {
                 $filtered = $run->asFilteredArray($relevant_columns);
                 $filtered['alias'] = $r['problem']->alias;
                 $filtered['username'] = $r['current_user']->username;
                 $filtered['time'] = strtotime($filtered['time']);
                 array_push($runs_filtered_array, $filtered);
             }
         }
         $response['runs'] = $runs_filtered_array;
     }
     if (!is_null($r['contest'])) {
         // At this point, contestant_user relationship should be established.
         try {
             ContestsUsersDAO::CheckAndSaveFirstTimeAccess($r['current_user_id'], $r['contest']->contest_id);
         } catch (ApiException $e) {
             throw $e;
         } catch (Exception $e) {
             // Operation failed in the data layer
             throw new InvalidDatabaseOperationException($e);
         }
         // As last step, register the problem as opened
         if (!ContestProblemOpenedDAO::getByPK($r['contest']->getContestId(), $r['problem']->getProblemId(), $r['current_user_id'])) {
             //Create temp object
             $keyContestProblemOpened = new ContestProblemOpened(array('contest_id' => $r['contest']->getContestId(), 'problem_id' => $r['problem']->getProblemId(), 'user_id' => $r['current_user_id']));
             try {
                 // Save object in the DB
                 ContestProblemOpenedDAO::save($keyContestProblemOpened);
             } catch (Exception $e) {
                 // Operation failed in the data layer
                 throw new InvalidDatabaseOperationException($e);
             }
         }
     } elseif (isset($r['show_solvers']) && $r['show_solvers']) {
         $response['solvers'] = RunsDAO::GetBestSolvingRunsForProblem($r['problem']->problem_id);
     }
     if (!is_null($r['current_user_id'])) {
         ProblemViewedDAO::MarkProblemViewed($r['current_user_id'], $r['problem']->problem_id);
     }
     $response['score'] = self::bestScore($r);
     $response['status'] = 'ok';
     return $response;
 }
Beispiel #8
0
 /**
  * Details of a group (users in a group)
  * 
  * @param Request $r
  */
 public static function apiDetails(Request $r)
 {
     self::validateGroupAndOwner($r);
     $response = array();
     $response["group"] = array();
     $response["users"] = array();
     $response["scoreboards"] = array();
     try {
         $response["group"] = $r["group"]->asArray();
         $userGroups = GroupsUsersDAO::search(new GroupsUsers(array("group_id" => $r["group"]->group_id)));
         foreach ($userGroups as $userGroup) {
             $r["user"] = UsersDAO::getByPK($userGroup->user_id);
             $userProfile = UserController::getProfile($r);
             $response["users"][] = $userProfile;
         }
         $scoreboards = GroupsScoreboardsDAO::search(new GroupsScoreboards(array("group_id" => $r["group"]->group_id)));
         foreach ($scoreboards as $scoreboard) {
             $response["scoreboards"][] = $scoreboard->asArray();
         }
     } catch (Exception $ex) {
         throw new InvalidDatabaseOperationException($ex);
     }
     $response["status"] = "ok";
     return $response;
 }
Beispiel #9
0
 /**
  * Returns the list of coders of the month
  *
  * @param Request $r
  */
 public static function apiCoderOfTheMonthList(Request $r)
 {
     $response = array();
     $response["coders"] = array();
     try {
         $coders = CoderOfTheMonthDAO::getAll(null, null, "time", "DESC");
         foreach ($coders as $c) {
             $user = UsersDAO::getByPK($c->user_id);
             $email = EmailsDAO::getByPK($user->getMainEmailId());
             $response["coders"][] = array("username" => $user->getUsername(), "gravatar_32" => "https://secure.gravatar.com/avatar/" . md5($email->getEmail()) . "?s=32", "date" => $c->getTime());
         }
     } catch (Exception $ex) {
         throw new InvalidDatabaseOperationException($e);
     }
     $response["status"] = "ok";
     return $response;
 }
 /**
  * Details of a scoreboard. Returns a list with all contests that belong to
  * the given scoreboard_alias
  *
  * @param Request $r
  */
 public static function apiDetails(Request $r)
 {
     self::validateGroupScoreboard($r);
     $response = array();
     // Fill contests
     $response['contests'] = array();
     $response['ranking'] = array();
     try {
         $groupScoreboardContestKey = new GroupsScoreboardsContests(array('group_scoreboard_id' => $r['scoreboard']->group_scoreboard_id));
         $r['gscs'] = GroupsScoreboardsContestsDAO::search($groupScoreboardContestKey);
         $i = 0;
         $contest_params = array();
         foreach ($r['gscs'] as $gsc) {
             $contest = ContestsDAO::getByPK($gsc->contest_id);
             $response['contests'][$i] = $contest->asArray();
             $response['contests'][$i]['only_ac'] = $gsc->only_ac;
             $response['contests'][$i]['weight'] = $gsc->weight;
             // Fill contest params to pass to scoreboardMerge
             $contest_params[$contest->alias] = array('only_ac' => $gsc->only_ac == 0 ? false : true, 'weight' => $gsc->weight);
             $i++;
         }
     } catch (ApiException $ex) {
         throw $ex;
     } catch (Exception $ex) {
         throw new InvalidDatabaseOperationException($ex);
     }
     $r['contest_params'] = $contest_params;
     // Fill details of this scoreboard
     $response['scoreboard'] = $r['scoreboard']->asArray();
     // If we have contests, calculate merged&filtered scoreboard
     if (count($response['contests']) > 0) {
         // Get merged scoreboard
         $r['contest_aliases'] = '';
         foreach ($response['contests'] as $contest) {
             $r['contest_aliases'] .= $contest['alias'] . ',';
         }
         $r['contest_aliases'] = rtrim($r['contest_aliases'], ',');
         try {
             $groupUsers = GroupsUsersDAO::search(new GroupsUsers(array('group_id' => $r['scoreboard']->group_id)));
             $r['usernames_filter'] = '';
             foreach ($groupUsers as $groupUser) {
                 $user = UsersDAO::getByPK($groupUser->user_id);
                 $r['usernames_filter'] .= $user->username . ',';
             }
             $r['usernames_filter'] = rtrim($r['usernames_filter'], ',');
         } catch (Exception $ex) {
             throw new InvalidDatabaseOperationException($ex);
         }
         $mergedScoreboardResponse = ContestController::apiScoreboardMerge($r);
         $response['ranking'] = $mergedScoreboardResponse['ranking'];
     }
     $response['status'] = 'ok';
     return $response;
 }