{"action":"created","comment":{"url":"https://api.github.com/repos/omegaup/omegaup/pulls/comments/69378875","id":69378875,"diff_hunk":"@@ -0,0 +1,277 @@\n+<?php\n+\n+class InterviewController extends Controller {\n+    private static function validateCreateOrUpdate(Request $r, $is_update = false) {\n+        // Interview specific validations. Everything else is validated in ContestController::apiCreate\n+        $is_required = !$is_update;\n+\n+        Validators::isStringNonEmpty($r['title'], 'title', $is_required);\n+        Validators::isStringNonEmpty($r['description'], 'description', false);\n+        Validators::isNumberInRange($r['duration'], 'duration', 60, 60 * 5, false);\n+        Validators::isValidAlias($r['alias'], 'alias', $is_required);\n+    }\n+\n+    public static function apiCreate(Request $r) {\n+        if (OMEGAUP_LOCKDOWN) {\n+            throw new ForbiddenAccessException('lockdown');\n+        }\n+\n+        self::authenticateRequest($r);\n+\n+        self::validateCreateOrUpdate($r, false);\n+\n+        // Create the contest that will back this interview\n+        $r['public'] = false;\n+        $r['title'] = $r['title'];\n+        $r['description'] = array_key_exists('description', $r) ? $r['description'] : $r['title'];\n+        $r['start_time'] = time();\n+        $r['finish_time'] = strtotime('+1 year');\n+        $r['window_length'] = $r['duration'];\n+        $r['scoreboard'] = 0;\n+        $r['points_decay_factor'] = 0;\n+        $r['partial_score'] = 0;\n+        $r['submissions_gap'] = 0;\n+        $r['feedback'] = 'no';\n+        $r['penalty'] = 0;\n+        $r['penalty_type'] = 'none';\n+        $r['penalty_calc_policy'] = 'sum';\n+        $r['languages'] = null;\n+        $r['interview'] = true;\n+        $r['contestant_must_register'] = 0;\n+\n+        $createdContest = ContestController::apiCreate($r);\n+\n+        self::$log->info('Created new interview ' . $r['alias']);\n+\n+        return array('status' => 'ok');\n+    }\n+\n+    private static function userFromEmail($email) {\n+        $newUsername = substr($email, 0, strpos($email, '@'));\n+        $newUsername = str_replace('-', '_', $newUsername);\n+        return $newUsername . time();\n+    }\n+\n+    private static function addUserInternal($r) {\n+        // Does the user exist ?\n+        try {\n+            $r['user'] = UserController::resolveUser($r['usernameOrEmail']);\n+        } catch (NotFoundException $e) {\n+            // this is fine\n+        }\n+\n+        if (is_null($r['user'])) {\n+            // user does not exist, create a new user\n+            self::$log->info('Could not find user, this must be a new email, register: ' . $r['usernameOrEmail']);\n+\n+            $newUserRequest = $r;\n+            $newUserRequest['email'] = $r['usernameOrEmail'];\n+            $newUserRequest['username'] = self::userFromEmail($r['usernameOrEmail']);\n+            $newUserRequest['password'] = self::randomString(8);\n+            $newUser = UserController::apiCreate($newUserRequest);\n+\n+            $r['user'] = $newUserRequest['username'];\n+        }\n+\n+        self::validateAddUser($r);\n+\n+        // add the user to the interview (contest)\n+        $contestUser = new ContestsUsers();\n+        $contestUser->setContestId($r['contest']->getContestId());\n+        $contestUser->setUserId($r['user']->getUserId());\n+        $contestUser->setAccessTime('0000-00-00 00:00:00');\n+        $contestUser->setScore('0');\n+        $contestUser->setTime('0');\n+\n+        // Save the contest to the DB\n+        try {\n+            ContestsUsersDAO::save($contestUser);\n+        } catch (Exception $e) {\n+            // Operation failed in the data layer\n+            self::$log->error('Failed to create new ContestUser: ' . $e->getMessage());\n+            throw new InvalidDatabaseOperationException($e);\n+        }\n+\n+        self::$log->info('Added ' . $newUserRequest['username'] . ' to interview.');\n+\n+        return true;\n+    }\n+\n+    public static function apiAddUsers(Request $r) {\n+        if (OMEGAUP_LOCKDOWN) {\n+            throw new ForbiddenAccessException('lockdown');\n+        }\n+\n+        // Authenticate logged user\n+        self::authenticateRequest($r);\n+\n+        Validators::isStringNonEmpty($r['usernameOrEmailsCSV'], 'usernameOrEmailsCSV', true);\n+        $usersToAdd = explode(',', $r['usernameOrEmailsCSV']);\n+\n+        foreach ($usersToAdd as $addThisUser) {\n+            $requestToInternal = new Request($r);\n+            $requestToInternal['usernameOrEmail'] = $addThisUser;\n+\n+            self::addUserInternal($requestToInternal);\n+        }\n+\n+        return array ('status' => 'ok');\n+    }\n+\n+    private static function userOpenedContest($contest_id, $user_id) {\n+        // You already started the contest.\n+        $contestOpened = ContestsUsersDAO::getByPK(\n+            $user_id,\n+            $contest_id\n+        );\n+\n+        if (!is_null($contestOpened) && $contestOpened->access_time != '0000-00-00 00:00:00') {\n+            return true;\n+        }\n+\n+        return false;\n+    }\n+\n+    public static function apiDetails(Request $r) {","path":"frontend/server/controllers/InterviewController.php","position":135,"original_position":135,"commit_id":"08907c8d3ad46e622ab53f777c2abcdecf7a89ad","original_commit_id":"08907c8d3ad46e622ab53f777c2abcdecf7a89ad","user":{"login":"joemmanuel","id":207097,"avatar_url":"https://avatars.githubusercontent.com/u/207097?v=3","gravatar_id":"","url":"https://api.github.com/users/joemmanuel","html_url":"https://github.com/joemmanuel","followers_url":"https://api.github.com/users/joemmanuel/followers","following_url":"https://api.github.com/users/joemmanuel/following{/other_user}","gists_url":"https://api.github.com/users/joemmanuel/gists{/gist_id}","starred_url":"https://api.github.com/users/joemmanuel/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/joemmanuel/subscriptions","organizations_url":"https://api.github.com/users/joemmanuel/orgs","repos_url":"https://api.github.com/users/joemmanuel/repos","events_url":"https://api.github.com/users/joemmanuel/events{/privacy}","received_events_url":"https://api.github.com/users/joemmanuel/received_events","type":"User","site_admin":false},"body":"Está bien que dejemos a cualquiera ver esta api? no debería ser sólo para contest/interview admins?","created_at":"2016-07-02T14:51:23Z","updated_at":"2016-07-02T14:51:23Z","html_url":"https://github.com/omegaup/omegaup/pull/819#discussion_r69378875","pull_request_url":"https://api.github.com/repos/omegaup/omegaup/pulls/819","_links":{"self":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/comments/69378875"},"html":{"href":"https://github.com/omegaup/omegaup/pull/819#discussion_r69378875"},"pull_request":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/819"}}},"pull_request":{"url":"https://api.github.com/repos/omegaup/omegaup/pulls/819","id":76061546,"html_url":"https://github.com/omegaup/omegaup/pull/819","diff_url":"https://github.com/omegaup/omegaup/pull/819.diff","patch_url":"https://github.com/omegaup/omegaup/pull/819.patch","issue_url":"https://api.github.com/repos/omegaup/omegaup/issues/819","number":819,"state":"open","locked":false,"title":"OmegaUp for Work","user":{"login":"alanboy","id":527987,"avatar_url":"https://avatars.githubusercontent.com/u/527987?v=3","gravatar_id":"","url":"https://api.github.com/users/alanboy","html_url":"https://github.com/alanboy","followers_url":"https://api.github.com/users/alanboy/followers","following_url":"https://api.github.com/users/alanboy/following{/other_user}","gists_url":"https://api.github.com/users/alanboy/gists{/gist_id}","starred_url":"https://api.github.com/users/alanboy/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/alanboy/subscriptions","organizations_url":"https://api.github.com/users/alanboy/orgs","repos_url":"https://api.github.com/users/alanboy/repos","events_url":"https://api.github.com/users/alanboy/events{/privacy}","received_events_url":"https://api.github.com/users/alanboy/received_events","type":"User","site_admin":false},"body":"","created_at":"2016-07-02T10:15:15Z","updated_at":"2016-07-02T14:51:24Z","closed_at":null,"merged_at":null,"merge_commit_sha":"e6c3db44f52d8591dde0e15d40f1bb1164526007","assignee":null,"assignees":[],"milestone":null,"commits_url":"https://api.github.com/repos/omegaup/omegaup/pulls/819/commits","review_comments_url":"https://api.github.com/repos/omegaup/omegaup/pulls/819/comments","review_comment_url":"https://api.github.com/repos/omegaup/omegaup/pulls/comments{/number}","comments_url":"https://api.github.com/repos/omegaup/omegaup/issues/819/comments","statuses_url":"https://api.github.com/repos/omegaup/omegaup/statuses/08907c8d3ad46e622ab53f777c2abcdecf7a89ad","head":{"label":"omegaup:omegaup-for-work","ref":"omegaup-for-work","sha":"08907c8d3ad46e622ab53f777c2abcdecf7a89ad","user":{"login":"omegaup","id":558429,"avatar_url":"https://avatars.githubusercontent.com/u/558429?v=3","gravatar_id":"","url":"https://api.github.com/users/omegaup","html_url":"https://github.com/omegaup","followers_url":"https://api.github.com/users/omegaup/followers","following_url":"https://api.github.com/users/omegaup/following{/other_user}","gists_url":"https://api.github.com/users/omegaup/gists{/gist_id}","starred_url":"https://api.github.com/users/omegaup/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/omegaup/subscriptions","organizations_url":"https://api.github.com/users/omegaup/orgs","repos_url":"https://api.github.com/users/omegaup/repos","events_url":"https://api.github.com/users/omegaup/events{/privacy}","received_events_url":"https://api.github.com/users/omegaup/received_events","type":"Organization","site_admin":false},"repo":{"id":1243685,"name":"omegaup","full_name":"omegaup/omegaup","owner":{"login":"omegaup","id":558429,"avatar_url":"https://avatars.githubusercontent.com/u/558429?v=3","gravatar_id":"","url":"https://api.github.com/users/omegaup","html_url":"https://github.com/omegaup","followers_url":"https://api.github.com/users/omegaup/followers","following_url":"https://api.github.com/users/omegaup/following{/other_user}","gists_url":"https://api.github.com/users/omegaup/gists{/gist_id}","starred_url":"https://api.github.com/users/omegaup/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/omegaup/subscriptions","organizations_url":"https://api.github.com/users/omegaup/orgs","repos_url":"https://api.github.com/users/omegaup/repos","events_url":"https://api.github.com/users/omegaup/events{/privacy}","received_events_url":"https://api.github.com/users/omegaup/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/omegaup/omegaup","description":"omegaUp automatic programming contest evaluator & arena","fork":false,"url":"https://api.github.com/repos/omegaup/omegaup","forks_url":"https://api.github.com/repos/omegaup/omegaup/forks","keys_url":"https://api.github.com/repos/omegaup/omegaup/keys{/key_id}","collaborators_url":"https://api.github.com/repos/omegaup/omegaup/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/omegaup/omegaup/teams","hooks_url":"https://api.github.com/repos/omegaup/omegaup/hooks","issue_events_url":"https://api.github.com/repos/omegaup/omegaup/issues/events{/number}","events_url":"https://api.github.com/repos/omegaup/omegaup/events","assignees_url":"https://api.github.com/repos/omegaup/omegaup/assignees{/user}","branches_url":"https://api.github.com/repos/omegaup/omegaup/branches{/branch}","tags_url":"https://api.github.com/repos/omegaup/omegaup/tags","blobs_url":"https://api.github.com/repos/omegaup/omegaup/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/omegaup/omegaup/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/omegaup/omegaup/git/refs{/sha}","trees_url":"https://api.github.com/repos/omegaup/omegaup/git/trees{/sha}","statuses_url":"https://api.github.com/repos/omegaup/omegaup/statuses/{sha}","languages_url":"https://api.github.com/repos/omegaup/omegaup/languages","stargazers_url":"https://api.github.com/repos/omegaup/omegaup/stargazers","contributors_url":"https://api.github.com/repos/omegaup/omegaup/contributors","subscribers_url":"https://api.github.com/repos/omegaup/omegaup/subscribers","subscription_url":"https://api.github.com/repos/omegaup/omegaup/subscription","commits_url":"https://api.github.com/repos/omegaup/omegaup/commits{/sha}","git_commits_url":"https://api.github.com/repos/omegaup/omegaup/git/commits{/sha}","comments_url":"https://api.github.com/repos/omegaup/omegaup/comments{/number}","issue_comment_url":"https://api.github.com/repos/omegaup/omegaup/issues/comments{/number}","contents_url":"https://api.github.com/repos/omegaup/omegaup/contents/{+path}","compare_url":"https://api.github.com/repos/omegaup/omegaup/compare/{base}...{head}","merges_url":"https://api.github.com/repos/omegaup/omegaup/merges","archive_url":"https://api.github.com/repos/omegaup/omegaup/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/omegaup/omegaup/downloads","issues_url":"https://api.github.com/repos/omegaup/omegaup/issues{/number}","pulls_url":"https://api.github.com/repos/omegaup/omegaup/pulls{/number}","milestones_url":"https://api.github.com/repos/omegaup/omegaup/milestones{/number}","notifications_url":"https://api.github.com/repos/omegaup/omegaup/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/omegaup/omegaup/labels{/name}","releases_url":"https://api.github.com/repos/omegaup/omegaup/releases{/id}","deployments_url":"https://api.github.com/repos/omegaup/omegaup/deployments","created_at":"2011-01-12T00:11:21Z","updated_at":"2016-05-30T15:16:36Z","pushed_at":"2016-07-02T14:23:21Z","git_url":"git://github.com/omegaup/omegaup.git","ssh_url":"git@github.com:omegaup/omegaup.git","clone_url":"https://github.com/omegaup/omegaup.git","svn_url":"https://github.com/omegaup/omegaup","homepage":"https://omegaup.com","size":217609,"stargazers_count":30,"watchers_count":30,"language":"PHP","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":29,"mirror_url":null,"open_issues_count":116,"forks":29,"open_issues":116,"watchers":30,"default_branch":"master"}},"base":{"label":"omegaup:master","ref":"master","sha":"fa40fe16dea70269607f3d68d6a7504e7e075e8b","user":{"login":"omegaup","id":558429,"avatar_url":"https://avatars.githubusercontent.com/u/558429?v=3","gravatar_id":"","url":"https://api.github.com/users/omegaup","html_url":"https://github.com/omegaup","followers_url":"https://api.github.com/users/omegaup/followers","following_url":"https://api.github.com/users/omegaup/following{/other_user}","gists_url":"https://api.github.com/users/omegaup/gists{/gist_id}","starred_url":"https://api.github.com/users/omegaup/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/omegaup/subscriptions","organizations_url":"https://api.github.com/users/omegaup/orgs","repos_url":"https://api.github.com/users/omegaup/repos","events_url":"https://api.github.com/users/omegaup/events{/privacy}","received_events_url":"https://api.github.com/users/omegaup/received_events","type":"Organization","site_admin":false},"repo":{"id":1243685,"name":"omegaup","full_name":"omegaup/omegaup","owner":{"login":"omegaup","id":558429,"avatar_url":"https://avatars.githubusercontent.com/u/558429?v=3","gravatar_id":"","url":"https://api.github.com/users/omegaup","html_url":"https://github.com/omegaup","followers_url":"https://api.github.com/users/omegaup/followers","following_url":"https://api.github.com/users/omegaup/following{/other_user}","gists_url":"https://api.github.com/users/omegaup/gists{/gist_id}","starred_url":"https://api.github.com/users/omegaup/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/omegaup/subscriptions","organizations_url":"https://api.github.com/users/omegaup/orgs","repos_url":"https://api.github.com/users/omegaup/repos","events_url":"https://api.github.com/users/omegaup/events{/privacy}","received_events_url":"https://api.github.com/users/omegaup/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/omegaup/omegaup","description":"omegaUp automatic programming contest evaluator & arena","fork":false,"url":"https://api.github.com/repos/omegaup/omegaup","forks_url":"https://api.github.com/repos/omegaup/omegaup/forks","keys_url":"https://api.github.com/repos/omegaup/omegaup/keys{/key_id}","collaborators_url":"https://api.github.com/repos/omegaup/omegaup/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/omegaup/omegaup/teams","hooks_url":"https://api.github.com/repos/omegaup/omegaup/hooks","issue_events_url":"https://api.github.com/repos/omegaup/omegaup/issues/events{/number}","events_url":"https://api.github.com/repos/omegaup/omegaup/events","assignees_url":"https://api.github.com/repos/omegaup/omegaup/assignees{/user}","branches_url":"https://api.github.com/repos/omegaup/omegaup/branches{/branch}","tags_url":"https://api.github.com/repos/omegaup/omegaup/tags","blobs_url":"https://api.github.com/repos/omegaup/omegaup/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/omegaup/omegaup/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/omegaup/omegaup/git/refs{/sha}","trees_url":"https://api.github.com/repos/omegaup/omegaup/git/trees{/sha}","statuses_url":"https://api.github.com/repos/omegaup/omegaup/statuses/{sha}","languages_url":"https://api.github.com/repos/omegaup/omegaup/languages","stargazers_url":"https://api.github.com/repos/omegaup/omegaup/stargazers","contributors_url":"https://api.github.com/repos/omegaup/omegaup/contributors","subscribers_url":"https://api.github.com/repos/omegaup/omegaup/subscribers","subscription_url":"https://api.github.com/repos/omegaup/omegaup/subscription","commits_url":"https://api.github.com/repos/omegaup/omegaup/commits{/sha}","git_commits_url":"https://api.github.com/repos/omegaup/omegaup/git/commits{/sha}","comments_url":"https://api.github.com/repos/omegaup/omegaup/comments{/number}","issue_comment_url":"https://api.github.com/repos/omegaup/omegaup/issues/comments{/number}","contents_url":"https://api.github.com/repos/omegaup/omegaup/contents/{+path}","compare_url":"https://api.github.com/repos/omegaup/omegaup/compare/{base}...{head}","merges_url":"https://api.github.com/repos/omegaup/omegaup/merges","archive_url":"https://api.github.com/repos/omegaup/omegaup/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/omegaup/omegaup/downloads","issues_url":"https://api.github.com/repos/omegaup/omegaup/issues{/number}","pulls_url":"https://api.github.com/repos/omegaup/omegaup/pulls{/number}","milestones_url":"https://api.github.com/repos/omegaup/omegaup/milestones{/number}","notifications_url":"https://api.github.com/repos/omegaup/omegaup/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/omegaup/omegaup/labels{/name}","releases_url":"https://api.github.com/repos/omegaup/omegaup/releases{/id}","deployments_url":"https://api.github.com/repos/omegaup/omegaup/deployments","created_at":"2011-01-12T00:11:21Z","updated_at":"2016-05-30T15:16:36Z","pushed_at":"2016-07-02T14:23:21Z","git_url":"git://github.com/omegaup/omegaup.git","ssh_url":"git@github.com:omegaup/omegaup.git","clone_url":"https://github.com/omegaup/omegaup.git","svn_url":"https://github.com/omegaup/omegaup","homepage":"https://omegaup.com","size":217609,"stargazers_count":30,"watchers_count":30,"language":"PHP","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":29,"mirror_url":null,"open_issues_count":116,"forks":29,"open_issues":116,"watchers":30,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/819"},"html":{"href":"https://github.com/omegaup/omegaup/pull/819"},"issue":{"href":"https://api.github.com/repos/omegaup/omegaup/issues/819"},"comments":{"href":"https://api.github.com/repos/omegaup/omegaup/issues/819/comments"},"review_comments":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/819/comments"},"review_comment":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/omegaup/omegaup/pulls/819/commits"},"statuses":{"href":"https://api.github.com/repos/omegaup/omegaup/statuses/08907c8d3ad46e622ab53f777c2abcdecf7a89ad"}}}}
{"actor":{"display_login":"joemmanuel"}}