예제 #1
0
파일: MainHandler.py 프로젝트: valiro21/mlc
    def get(self):
        """
        Get methods for the first page of the website
        """
        try:
            session = self.acquire_sql_session()
        except:
            raise HTTPError(500, 'Failed to acquire database session.')

        try:
            contests_running = ContestRepository.get_active_contests(session)
            contests_upcoming = ContestRepository.get_future_contests(session)
            contests_recent = ContestRepository.get_recent_contests(session)
            most_rated_users = UserRepository.get_most_rated(session)
            recent_blog_posts = BlogPostRepository\
                .get_by_latest_with_username(session)\

        except:
            raise HTTPError(500, 'A database error has occured.')
        finally:
            session.close()

        self.render("main.html",
                    contests_running=contests_running,
                    contests_upcoming=contests_upcoming,
                    contests_recent=contests_recent,
                    most_rated_users=most_rated_users,
                    recent_blog_posts=recent_blog_posts)
예제 #2
0
    def get_template_namespace(self):
        try:
            session2 = self.acquire_sql_session()
            sidebar_contests = ContestRepository.\
                get_all_contest_order_by_date(session2)
            sidebar_problems = ProblemRepository.get_all_problems(session2)
            sidebar_users = UserRepository.get_all(session2)
            session2.close()
        except:
            raise HTTPError(500)

        dict = super(BaseHandler, self).get_template_namespace()

        dict['sidebar_contests'] = sidebar_contests
        dict['sidebar_problems'] = sidebar_problems
        dict['sidebar_users'] = sidebar_users

        return dict
예제 #3
0
    def post(self):
        path_elements = [x for x in self.request.path.split("/") if x]
        contest_id = path_elements[1]
        if len(path_elements) == 2 and contest_id == "create":
            # Create contest from request

            contest_name = self.get_argument('contest_name')
            start_date_string = self.get_argument('start_date')

            start_date = \
                datetime.strptime(start_date_string, '%m/%d/%Y %I:%M %p')

            start_date_utc = calendar.timegm(start_date.timetuple())

            end_date_string = self.get_argument('end_date')
            end_date = datetime.strptime(end_date_string, '%m/%d/%Y %I:%M %p')
            end_date_utc = calendar.timegm(end_date.timetuple())

            try:
                session = self.acquire_sql_session()
            except SQLAlchemyError:
                traceback.print_exc()
                raise HTTPError(500, 'Could not acquire database session.')

            try:
                new_contest = Contest(name=contest_name,
                                      description='',
                                      start_time=start_date_utc,
                                      end_time=end_date_utc)
                session.add(new_contest)
                session.commit()
            except SQLAlchemyError as e:
                self.redirect("create")
                print(e)
                return

            self.redirect_to_settings(self, contest_name + "/settings")
            session.close()
            return

        elif len(path_elements) == 3 and path_elements[2] == 'settings':
            """Changing settings"""

            contest_name = self.get_argument('contest_name')
            contest_description = self.get_argument('contest_description')
            contest_type = self.get_argument('contest_type')

            contest_dict = {'Open': 1, 'Public': 2, 'Private': 3}

            contest_type = contest_dict.get(contest_type, 1)

            try:
                self.get_argument('contest_virtual')
                contest_virtual = True
            except:
                contest_virtual = False
            try:
                self.get_argument('contest_allow_download')
                contest_allow_download = True
            except:
                contest_allow_download = False
            try:
                self.get_argument('contest_allow_questions')
                contest_allow_questions = True
            except:
                contest_allow_questions = False
            try:
                self.get_argument('contest_allow_usertest')
                contest_allow_usertest = True
            except:
                contest_allow_usertest = False

            contest_restricted_ip = \
                self.get_argument('contest_restricted_ip')

            contest_start_time_string = \
                self.get_argument('contest_start_time')

            contest_start_time_non_utc = \
                datetime.strptime(contest_start_time_string,
                                  '%m/%d/%Y %I:%M %p')

            contest_start_time = \
                calendar.timegm(contest_start_time_non_utc.timetuple())

            contest_end_time = \
                self.get_argument('contest_end_time')

            contest_end_time_non_utc = \
                datetime.strptime(contest_end_time, '%m/%d/%Y %I:%M %p')

            contest_end_time = \
                calendar.timegm(contest_end_time_non_utc.timetuple())

            # contest_timezone = \
            # self.get_argument('contest_timezone')# make date time picker boss
            contest_max_submissions = \
                self.get_argument('contest_max_submissions')
            contest_max_user_tests = \
                self.get_argument('contest_max_user_tests')
            contest_submission_delay = \
                self.get_argument('contest_min_submission_interval')
            contest_user_test_delay = \
                self.get_argument('contest_min_user_test_interval')

            try:
                session = self.acquire_sql_session()
            except:
                traceback.print_exc()
                # TODO: handle error
                return

            try:
                contest_old_name = path_elements[1]
                stmt = update(Contest). \
                    where(Contest.name == contest_old_name). \
                    values(name=contest_name,
                           description=contest_description,
                           type=contest_type,
                           virtual=contest_virtual,
                           submission_download_allowed=contest_allow_download,
                           allow_questions=contest_allow_questions,
                           allow_user_test=contest_allow_usertest,
                           restricted_ip=contest_restricted_ip,
                           start_time=contest_start_time,
                           end_time=contest_end_time,
                           max_submissions=contest_max_submissions,
                           max_user_test=contest_max_user_tests,
                           min_submission_interval=contest_submission_delay,
                           min_user_test_interval=contest_user_test_delay,
                           )
                session.execute(stmt)
                session.commit()
            except SQLAlchemyError as e:
                print(e)
                self.redirect_to_settings(self, "settings")
                return
            self.redirect("problems")
            session.close()

        elif len(path_elements) == 3 and path_elements[2] == 'add_problem':
            """Adding problem to contest"""

            contest_name = path_elements[1]
            problem_id = self.get_argument('problem', None)

            if problem_id is None:
                self.redirect('/contest/' + contest_name + '/problems')
                return

            try:
                session = self.acquire_sql_session()
            except SQLAlchemyError:
                self.send_custom_error(500, 'Could not acquire '
                                       'database session')
                return

            try:
                problem = ProblemRepository.get_by_name(session, problem_id)
                contest = ContestRepository.get_by_name(session, contest_name)
            except SQLAlchemyError:
                session.close()
                self.send_custom_error(500, 'Could not find problem.')
                return

            try:
                ContestRepository.add_problem(session, contest, problem)
            except SQLAlchemyError:
                session.close()
                self.send_custom_error(
                    500, 'Could not add problem. '
                    'It already exists in contest.')
                return

            self.write('Success! Refresh page to see changes.')
            session.close()

        elif len(path_elements) == 3 and path_elements[2] == 'remove_problem':
            """Removing problem from contest"""

            print('Entered "remove problem from contest"')

            contest_name = path_elements[1]
            problem_id = int(self.get_argument('id', None))

            if problem_id is None:
                self.send_custom_error(500, 'Problem name not specified')
                return

            try:
                session = self.acquire_sql_session()
            except SQLAlchemyError:
                self.send_custom_error(500, 'Could not acquire '
                                       'database session')
                return

            try:
                problem = ProblemRepository.get_by_id(session, problem_id)
                contest = ContestRepository.get_by_name(session, contest_name)
            except SQLAlchemyError:
                session.close()
                self.send_custom_error(500, 'Could not find '
                                       'problem or contest.')
                return

            try:
                ContestRepository.remove_problem(session, contest, problem)
            except SQLAlchemyError:
                session.close()
                self.send_custom_error(500, 'Could not remove problem...')
                return

            self.write('Success!')
            session.close()

        elif len(path_elements) == 3 and path_elements[2] == 'addusers':
            session = self.acquire_sql_session()
            contest_name = path_elements[1]
            user_name = self.get_argument('username')
            participation_type = self.get_argument('participation_type')
            delay_time = self.get_argument('delay_time')
            extra_time = self.get_argument('extra_time')
            s_password = self.get_argument('special_password')

            if s_password == '':
                s_password = None
            try:
                self.get_argument('unrestricted')
                unrestricted = True
            except:
                unrestricted = False

            try:
                self.get_argument('hidden')
                hidden = True
            except:
                hidden = False

            try:
                contest = ContestRepository.get_by_name(session, contest_name)
                user = UserRepository.get_by_name(session, user_name)
            except SQLAlchemyError as e:
                self.write('User or Contest not found!')
                print(e)
                return
            if contest is None:
                self.write('Contest is None!')
            if user is None:
                self.write('User is None!')

            ok = ParticipationRepository. \
                verif_participation(session, user.id, contest.id)

            if ok is False:
                participation = Participation(user_id=user.id,
                                              contest_id=contest.id,
                                              type=participation_type,
                                              unrestricted=unrestricted,
                                              hidden=hidden,
                                              delay_time=delay_time,
                                              extra_time=extra_time,
                                              special_password=s_password)
                session.add(participation)
                session.commit()
                message = 'registered'
            else:
                stmt = update(Participation). \
                    where(and_(Participation.user_id == user.id,
                               Participation.contest_id == contest.id)). \
                    values(type=participation_type,
                           unrestricted=unrestricted,
                           hidden=hidden,
                           delay_time=delay_time,
                           extra_time=extra_time,
                           special_password=s_password)
                session.execute(stmt)
                session.commit()
                message = 'registered'
            self.write(message)
            return
예제 #4
0
    def post(self):
        """
        Handle for the post methods done on /contest/*
        Accepted operations:
            1. register: registers the current user to the current contest
            2. creatv: creates a virtual contest for the current user
            3. settingsv: provides setting for the contest if the user
                        has permission
        """
        path_elements = [x for x in self.request.path.split("/") if x]
        if len(path_elements) == 2:
            operation_type = path_elements[1]
        else:
            operation_type = path_elements[2]

        if operation_type == 'register':
            try:
                self.get_argument('agree')
            except:
                self.write('You did not accept the terms!')
                return

            participation_type = self.get_argument('participation_type')
            contest_name = path_elements[1].replace('%20', ' ')
            user_name = self.get_current_user()
            session = self.acquire_sql_session()

            try:
                contest = ContestRepository.get_by_name(session, contest_name)
                user = UserRepository.get_by_name(session, user_name)
            except SQLAlchemyError as e:
                self.redirect("register")
                print(e)
                return

            if contest.type == 3:
                self.write('Contest is private')
                return
            elif contest.type == 2:
                self.write('Contest is public but not open')
                return

            ok = ParticipationRepository. \
                verif_participation(session, user.id, contest.id)

            if ok:
                self.write('You are already registered for this contest')
                return

            participation = Participation(user_id=user.id,
                                          contest_id=contest.id,
                                          type=participation_type)

            try:
                session.add(participation)
                session.commit()
            except SQLAlchemyError as e:
                self.redirect("register")
                print(e)
                return
        elif operation_type == 'createv':
            contest_name = self.get_argument('contest_name')
            start_date_string = self.get_argument('start_date')

            start_date = \
                datetime.strptime(start_date_string, '%m/%d/%Y %I:%M %p')

            start_date_utc = calendar.timegm(start_date.timetuple())

            end_date_string = self.get_argument('end_date')
            end_date = datetime.strptime(end_date_string, '%m/%d/%Y %I:%M %p')
            end_date_utc = calendar.timegm(end_date.timetuple())

            try:
                session = self.acquire_sql_session()
            except SQLAlchemyError:
                traceback.print_exc()
                raise HTTPError(500, 'Could not acquire database session.')

            try:
                new_contest = Contest(name=contest_name,
                                      description='',
                                      start_time=start_date_utc,
                                      end_time=end_date_utc,
                                      virtual=True)
                session.add(new_contest)
                session.commit()
                user_name = self.get_current_user()

                if user_name is None:
                    self.render('you_must_be_logged.html')
                    return

                user = UserRepository.get_by_name(session, user_name)
                contest = ContestRepository.get_by_name(session, contest_name)
                new_permission = ContestPermissions(user_id=user.id,
                                                    contest_id=contest.id)
                session.add(new_permission)
                session.commit()
            except SQLAlchemyError as e:
                self.redirect("create")
                print(e)
                return

            self.redirect(contest_name + "/settingsv")
            session.close()
            return
        elif operation_type == 'settingsv':
            contest_name = self.get_argument('contest_name')
            contest_description = self.get_argument('contest_description')
            contest_type = self.get_argument('contest_type')

            contest_dict = {
                'Open': 1,
                'Public': 2,
                'Private': 3
            }

            contest_type = contest_dict.get(contest_type, 1)

            try:
                self.get_argument('contest_virtual')
                contest_virtual = True
            except:
                contest_virtual = False
            try:
                self.get_argument('contest_allow_download')
                contest_allow_download = True
            except:
                contest_allow_download = False
            try:
                self.get_argument('contest_allow_questions')
                contest_allow_questions = True
            except:
                contest_allow_questions = False
            try:
                self.get_argument('contest_allow_usertest')
                contest_allow_usertest = True
            except:
                contest_allow_usertest = False

            contest_restricted_ip = \
                self.get_argument('contest_restricted_ip')

            contest_start_time_string = \
                self.get_argument('contest_start_time')

            contest_start_time_non_utc = \
                datetime.strptime(contest_start_time_string,
                                  '%m/%d/%Y %I:%M %p')

            contest_start_time = \
                calendar.timegm(contest_start_time_non_utc.timetuple())

            contest_end_time = \
                self.get_argument('contest_end_time')

            contest_end_time_non_utc = \
                datetime.strptime(contest_end_time, '%m/%d/%Y %I:%M %p')

            contest_end_time = \
                calendar.timegm(contest_end_time_non_utc.timetuple())

            # contest_timezone = \
            # self.get_argument('contest_timezone')# make date time picker boss
            contest_max_submissions = \
                self.get_argument('contest_max_submissions')
            contest_max_user_tests = \
                self.get_argument('contest_max_user_tests')
            contest_submission_delay = \
                self.get_argument('contest_min_submission_interval')
            contest_user_test_delay = \
                self.get_argument('contest_min_user_test_interval')

            try:
                session = self.acquire_sql_session()
            except:
                traceback.print_exc()
                # TODO: handle error
                return

            try:
                contest_old_name = path_elements[1]
                stmt = update(Contest). \
                    where(Contest.name == contest_old_name). \
                    values(name=contest_name,
                           description=contest_description,
                           type=contest_type,
                           virtual=contest_virtual,
                           submission_download_allowed=contest_allow_download,
                           allow_questions=contest_allow_questions,
                           allow_user_test=contest_allow_usertest,
                           restricted_ip=contest_restricted_ip,
                           start_time=contest_start_time,
                           end_time=contest_end_time,
                           max_submissions=contest_max_submissions,
                           max_user_test=contest_max_user_tests,
                           min_submission_interval=contest_submission_delay,
                           min_user_test_interval=contest_user_test_delay,
                           )
                session.execute(stmt)
                session.commit()
            except SQLAlchemyError as e:
                print(e)
                self.redirect_to_settings(self, "settingsv")
                return
            self.redirect("problems")
            session.close()

        self.redirect("contest_done_register")
예제 #5
0
    def get(self):
        """
        Handle for the get methods done on /contest/*
        Accepted pages:
            "problems", "submit", "mysubmissions", "submissions",
            "standings", "createv", "problemsv", "settingsv"
        """
        path_elements = [x for x in self.request.path.split("/") if x]
        contest_name = path_elements[1].replace('%20', ' ')

        if path_elements[1] == "createv":
            self.render("contest_" +
                        path_elements[1] + ".html")
            return
        session = self.acquire_sql_session()
        contest = ContestRepository.get_by_name(session, contest_name)

        problems = ContestRepository.get_all_problems(session, contest.id)

        for problem in problems:
            print(problem)

        if contest.type == 3:
            user_name = self.get_current_user()

            if user_name is None:
                self.render('you_must_be_logged.html')
                return

            user = UserRepository.get_by_name(session, user_name)

            ok = ParticipationRepository. \
                verif_participation(session, user.id, contest.id)

            if ok is False:
                self.redirect('..')
                return

        if len(path_elements) <= 2:
            self.redirect(os.path.join(self.request.path, "problems"))
            return

        if path_elements[2] == 'settingsv':
            session = self.acquire_sql_session()
            contest = ContestRepository.get_by_name(session, contest_name)
            user_name = self.get_current_user()

            if user_name is None:
                self.render('you_must_be_logged.html')
                return

            user = UserRepository.get_by_name(session, user_name)
            ok = ContestPermissionsRepository\
                .check_permission(session, contest.id, user.id)
            if ok is False:
                self.render("contest_no_privileges.html",
                            contest_id=contest_name,
                            problems=problems
                            )
                return
            self.render("contest_" +
                        path_elements[2] + ".html",
                        last_path=path_elements[2],
                        contest_id=contest_name,
                        contest_name=contest.name,
                        contest_description=contest.description,
                        contest_type=self.type_format(contest.type),
                        allow_download=self
                        .checkbox_format(contest.
                                         submission_download_allowed),
                        allow_questions=self
                        .checkbox_format(contest.allow_questions),
                        allow_usertest=self
                        .checkbox_format(contest.allow_user_test),
                        start_time=self.time_format(contest.
                                                    start_time),
                        end_time=self.time_format(contest.end_time),
                        restricted_ip=contest.restricted_ip,
                        max_submissions=contest.max_submissions,
                        max_user_tests=contest.max_user_test,
                        submission_delay=contest.min_submission_interval,
                        user_test_delay=contest.min_user_test_interval,
                        )
            return

        if path_elements[2] == 'register':
            self.render("contest_register.html",
                        contest_name=contest_name,
                        contest_id=contest.id)
            return

        if len(path_elements) >= 4:
            self.redirect("..")
            return

        if path_elements[2] == 'submit' or path_elements[2] == 'mysubmissions':

            user_name = self.get_current_user()

            if user_name is None:
                self.render('you_must_be_logged.html')
                return

            user = UserRepository.get_by_name(session, user_name)

            ok = ParticipationRepository. \
                verif_participation(session, user.id, contest.id)

            if ok is False:
                self.render('contest_fail_non_registered.html')
                return

        if path_elements[2] not in ["problems",
                                    "submit",
                                    "mysubmissions",
                                    "submissions",
                                    "standings",
                                    "createv",
                                    "problemsv",
                                    "settingsv"]:
            self.redirect("problems")

        if path_elements[2] in ['submissions', 'mysubmissions']:
            query = session.query(Submission, Contest, Problem, User) \
                .join(Participation,
                      Submission.participation_id == Participation.id) \
                .join(User, User.id == Participation.user_id) \
                .join(Contest, Contest.id == Participation.contest_id) \
                .join(Problem, Problem.id == Submission.problem_id)

            if path_elements[2] == 'mysubmissions':
                query = query.filter(User.id == user.id)

            if contest.id is not None:
                query = query.filter(Contest.id == contest.id)

            query.order_by(desc(Submission.created_timestamp))

            results = query.all()
            return_list = []
            for row in results:
                submission, contest, problem, user = row
                score = SubmissionRepository.get_status(session, submission.id)

                wrapper = PrettyWrap(submission,
                                     contest,
                                     problem,
                                     user,
                                     score[0],  # Message to show
                                     score[1],  # Cpu used
                                     score[2])  # Memory used
                return_list.append(wrapper)

            session.close()

            self.render('contest_' + path_elements[2] + '.html',
                        contest_name=contest.name,
                        contest_id=contest.id,
                        submissions=return_list)
            return

        self.render("contest_" +
                    path_elements[2] + ".html",
                    contest_name=contest.name,
                    contest_id=contest.id,
                    problems=problems)
예제 #6
0
    def get(self):

        path_elements = [x for x in self.request.path.split("/") if x]
        username = path_elements[1]

        if len(path_elements) <= 2:
            self.redirect(os.path.join(self.request.path, "profile"))
            return
        if len(path_elements) >= 4:
            self.redirect("..")
            return

        if path_elements[2] not in [
                "profile", "settings", "user_submissions", "user_contests",
                "user_statistics"
        ]:
            self.redirect("profile")

        if path_elements[2] == 'user_submissions':
            # Get all user submissions for the user

            session = self.acquire_sql_session()

            pg_nr = int(self.get_argument("page_number", "1"))  # Page number
            pg_size = 20  # Defaults to 20 submissions per page

            # Create multiple part query
            query = session.query(Submission, Contest, Problem, User) \
                .join(Participation,
                      Submission.participation_id == Participation.id) \
                .join(User, User.id == Participation.user_id) \
                .join(Contest, Contest.id == Participation.contest_id) \
                .join(Problem, Problem.id == Submission.problem_id)

            if username is not None:
                query = query.filter(User.username == username)

                user = session.query(User)\
                    .filter(User.username == username).one_or_none()
                if user is None:
                    self.render('profile_not_found.html')
                try:
                    db_user = UserRepository.get_by_name(session, username)
                except:
                    raise HTTPError(404, 'Could not find requested user.')

            query.order_by(desc(Submission.created_timestamp)) \
                .limit(pg_nr * pg_size) \
                .offset((pg_nr - 1) * pg_size) \
                .limit(pg_size)

            results = query.all()
            return_list = []
            for row in results:
                submission, contest, problem, user = row
                score = SubmissionRepository.get_status(session, submission.id)

                wrapper = PrettyWrap(
                    submission,
                    contest,
                    problem,
                    user,
                    score[0],  # Message to show
                    score[1],  # Cpu used
                    score[2])  # Memory used
                return_list.append(wrapper)

            session.close()

            self.render("user_submissions.html",
                        user=db_user,
                        submissions=return_list)
            return

        session = self.acquire_sql_session()
        user = session.query(User)\
            .filter(User.username == username).one_or_none()

        if user is None:
            self.render("profile_not_found.html")

        else:
            self.render(path_elements[2] + ".html",
                        user=user,
                        user_id=user.username)
예제 #7
0
    def get(self):
        """
        Render page with submissions. Parameters:
         * required pg_number: The page number to show
         * user: The name of the username to show submissions of
         * problem: The name of the problem to show submission for
         * contest: The name of the contest where the contest was submitted
        """
        contest_name = self.get_argument("contest", None)  # Contest name
        problem_name = self.get_argument("problem", None)  # Problem name
        user_name = self.get_argument("user", None)  # Problem name
        pg_nr = self.get_argument("page_number", "1")  # Page number
        pg_size = 20  # Defaults to 20 submissions per page

        try:  # Try to fetch page number. Should be integer.
            pg_nr = int(pg_nr)
        except ValueError:
            self.render("submissions.html",
                        submissions=None,
                        error="Invalid page number, "
                              "should be a valid integer")

        try:
            session = self.acquire_sql_session()
        except SQLAlchemyError as err:
            print(str(err))
            self.render("submissions.html",
                        submissions=None,
                        error="Database is down!")
            return

        try:
            # Get problem or None if not required
            if problem_name is not None:
                problem = ProblemRepository.get_by_name(session, problem_name)
                problem_id = problem.id
            else:
                problem_id = None

            # Get contest or None if not required
            if contest_name is not None:
                contest = ContestRepository.get_by_name(session, contest_name)
                contest_id = contest.id
            else:
                contest_id = None

            # Get user or None if not required
            if user_name is not None:
                user = UserRepository.get_by_name(session, user_name)
                user_id = user.id
            else:
                user_id = None
        except MultipleResultsFound:
            session.close()
            self.render("submissions.html",
                        submissions=None,
                        error="Invalid database!")
            return
        except NoResultFound:
            session.close()
            self.render("submissions.html",
                        submissions=None,
                        error="Invalid contest or problem parameters")
            return

        # Done handling errors

        # Create multiple part query
        query = session.query(Submission, Contest, Problem, User) \
            .join(Participation,
                  Submission.participation_id == Participation.id)\
            .join(User, User.id == Participation.user_id)\
            .join(Contest, Contest.id == Participation.contest_id)\
            .join(Problem, Problem.id == Submission.problem_id)

        if user_id is not None:
            query = query.filter(User.id == user_id)

        if contest_id is not None:
            query = query.filter(Contest.id == contest_id)

        if problem_id is not None:
            query = query.filter(Problem.id == problem_id)

        query.order_by(Submission.created_timestamp.desc())\
            .limit(pg_nr * pg_size)\
            .offset((pg_nr - 1) * pg_size)\
            .limit(pg_size)

        results = query.all()
        return_list = []

        results.sort(key=lambda a: a[0].created_timestamp, reverse=True)

        for row in results:
            submission, contest, problem, user = row
            score = SubmissionRepository.get_status(session, submission.id)

            wrapper = PrettyWrap(submission,
                                 contest,
                                 problem,
                                 user,
                                 score[0],  # Message to show
                                 score[1],  # Cpu used
                                 score[2])  # Memory used
            return_list.append(wrapper)

        session.close()

        self.render("submissions.html", submissions=return_list)