def join_team(self, user, team_id):
        """Join a team will create a record on user_team_rel table which status will be 0.

        :type user: User

        :rtype: dict
        :return: if user already joined team or team not exist, return bad request. Else, return a dict of joined
            details.
        """
        if Team.objects(id=team_id, members__user=user.id).count():
            return ok("You already joined this team.")

        team = self.__get_team_by_id(team_id)
        if not team:
            return not_found()

        cur_team = self.__get_valid_team_by_user(user.id, team.hackathon.id)
        if cur_team and cur_team.members.count() > 1:
            return precondition_failed("Team leader cannot join another team for team member count greater than 1")

        if not self.register_manager.is_user_registered(user.id, team.hackathon):
            return precondition_failed("user not registerd")

        mem = TeamMember(
            join_time=self.util.get_now(),
            status=TEAM_MEMBER_STATUS.INIT,
            user=user)
        team.members.append(mem)

        team.save()

        return to_dic(mem)
    def join_team(self, user, team_id):
        """Join a team will create a record on user_team_rel table which status will be 0.

        :type user: User
        :param user: the user to join a team

        :rtype: dict
        :return: if user already joined team or team not exist, return bad request. Else, return a dict of joined
            details.
        """
        if self.db.find_first_object_by(UserTeamRel, user_id=user.id, team_id=team_id):
            return ok("You already joined this team.")

        team = self.__get_team_by_id(team_id)
        if not team:
            return not_found()

        cur_team = self.__get_valid_team_by_user(user.id, team.hackathon_id)
        if cur_team and cur_team.team.user_team_rels.count() > 1:
            return precondition_failed("Team leader cannot join another team for team member count greater than 1")

        if not self.register_manager.is_user_registered(user.id, team.hackathon):
            return precondition_failed("user not registerd")

        candidate = UserTeamRel(join_time=self.util.get_now(),
                                update_time=self.util.get_now(),
                                status=TeamMemberStatus.Init,
                                hackathon_id=team.hackathon.id,
                                user_id=user.id,
                                team_id=team.id)
        self.db.add_object(candidate)
        return candidate.dic()
    def promote_leader(self, hackathon_id, team_name, new_leader_id):
        """ team leader promote some one from team to become team leader

        :type hackathon_id: int
        :param hackathon_id: hackathon id

        :type team_name: str|unicode
        :param team_name: team name

        :type new_leader_id: int
        :param new_leader_id: id of user who will become new leader of the team

        :rtype: bool
        :return: if promote success, return ok. if not ,return bad request.
        """

        team = self.__get_team_by_name(hackathon_id, team_name)
        if not team:
            return not_found("team doesn't exist")

        self.__validate_team_permission(hackathon_id, team, g.user)

        # check new leader and old leader in same team
        member = team.user_team_rels.filter_by(user_id=new_leader_id).first()
        if not member:
            return precondition_failed("Please promote someone in the same team.")
        if member.status != TeamMemberStatus.Approved:
            return precondition_failed("The member is not approved yet")

        team.leader_id = new_leader_id
        self.db.commit()
        self.log.debug(team.leader.name + " has been promote to leader.")
        return team.dic()
    def create_registration(self, hackathon, user, args):
        """Register hackathon for user

        Will add a new record in table UserRegistrationRel if precondition fulfilled
        """
        self.log.debug("create_register: %r" % args)
        user_id = args['user_id']

        check_login_provider = self.__is_user_hackathon_login_provider(user, hackathon)
        if check_login_provider["fail"]:
            return login_provider_error(
                "hackathon registration not login provider",
                friendly_message="当前黑客松活动只是使用" + ",".join(check_login_provider["provides"]) + "账户才能报名",
                provides=",".join(check_login_provider["provides"]))

        if self.is_user_registered(user.id, hackathon):
            self.log.debug("user %s already registered on hackathon %s" % (user_id, hackathon.id))
            return self.get_registration_detail(user, hackathon)

        if self.admin_manager.is_hackathon_admin(hackathon.id, user.id):
            return precondition_failed("administrator cannot register the hackathon", friendly_message="管理员或裁判不能报名")

        if hackathon.registration_start_time and hackathon.registration_start_time > self.util.get_now():
            return precondition_failed("hackathon registration not opened", friendly_message="报名尚未开始")

        if hackathon.registration_end_time and hackathon.registration_end_time < self.util.get_now():
            return precondition_failed("hackathon registration has ended", friendly_message="报名已经结束")

        if self.__is_hackathon_filled_up(hackathon):
            return precondition_failed("hackathon registers reach the upper threshold",
                                       friendly_message="报名人数已满")

        try:
            is_auto_approve = hackathon.config.get(HACKATHON_CONFIG.AUTO_APPROVE, True)
            status = HACK_USER_STATUS.AUTO_PASSED if is_auto_approve else HACK_USER_STATUS.UNAUDIT
            args.pop("user_id")
            args.pop("hackathon_id")

            user_hackathon = UserHackathon.objects(user=user, hackathon=hackathon).first()
            if not user_hackathon:
                user_hackathon = UserHackathon.objects.create(
                    user=user,
                    hackathon=hackathon,
                    status=status,
                    **args)
            else:  # visitor -> competitor
                user_hackathon.role = HACK_USER_TYPE.COMPETITOR
                user_hackathon.status = status
                user_hackathon.save()

            # create a team as soon as user registration approved(auto or manually)
            if is_auto_approve:
                self.team_manager.create_default_team(hackathon, user)
                self.__ask_for_dev_plan(hackathon, user)

            self.__update_register_stat(hackathon)
            return user_hackathon.dic()
        except Exception as e:
            self.log.error(e)
            return internal_server_error("fail to create register")
    def create_default_team(self, hackathon, user):
        """Create a default new team for user after registration.

        Use user name as team name by default. Append user id in case user name is duplicate
        """
        user_team_rel = self.__get_valid_team_by_user(user.id, hackathon.id)
        if user_team_rel:
            self.log.debug("fail to create team since user is already in some team.")
            return precondition_failed("you must leave the current team first")

        team_name = self.__generate_team_name(hackathon, user)
        team = Team(name=team_name,
                    leader_id=user.id,
                    logo=user.avatar_url,
                    hackathon_id=hackathon.id)
        self.db.add_object(team)

        user_team_rel = UserTeamRel(join_time=self.util.get_now(),
                                    status=TeamMemberStatus.Approved,
                                    hackathon_id=hackathon.id,
                                    user_id=user.id,
                                    team_id=team.id)
        self.db.add_object(user_team_rel)

        return team.dic()
    def grant_award_to_team(self, hackathon, context):
        team = self.__get_team_by_id(context.team_id)
        if not team:
            return not_found("team not found")

        award = self.db.find_first_object_by(Award, id=context.award_id)
        if not award:
            return not_found("award not found")

        if team.hackathon_id != hackathon.id or award.hackathon_id != hackathon.id:
            return precondition_failed("hackathon doesn't match")

        exist = self.db.find_first_object_by(TeamAward, team_id=context.team_id, award_id=context.award_id)
        if not exist:
            exist = TeamAward(
                team_id=context.team_id,
                hackathon_id=hackathon.id,
                award_id=context.award_id,
                reason=context.get("reason"),
                level=award.level,
            )
            self.db.add_object(exist)
        else:
            exist.reason = context.get("reason", exist.reason)
            self.db.commit()

        return self.__award_with_detail(exist)
    def kick_or_leave(self, operator, team_id, user_id):
        try:
            team = Team.objects(id=team_id, members__user=user_id).first()
        except ValidationError:
            return not_found()

        if not team:
            return not_found()
        mem = filter(lambda x: str(x.user.id) == user_id, team.members)
        assert len(mem) < 2
        if not mem:
            return not_found()
        mem = mem[0]

        hackathon = team.hackathon
        user = mem.user
        if str(team.leader.id) == user_id:  # if the user to be leaved or kicked is team leader
            return precondition_failed("leader cannot leave team")

        if str(operator.id) == user_id:  # leave team
            team.members.remove(mem)
            team.save()
            self.create_default_team(hackathon, user)
        else:  # kick somebody else
            self.__validate_team_permission(hackathon.id, team, operator)
            team.members.remove(mem)
            team.save()
            self.create_default_team(hackathon, user)

        return ok()
 def test_create_hackathon_register_registration_not_begin(self, get_method):
     args = {'user_id': 1}
     hackathon = Hackathon(id=1, registration_start_time=self.get_now() + datetime.timedelta(seconds=30))
     get_method.retrun_value = None
     self.assertEqual(self.register_manager.create_registration(hackathon, args),
                      precondition_failed("hackathon registration not opened", friendly_message="报名尚未开始"))
     get_method.assert_called_once_with(1, 1)
    def update_team(self, kwargs):
        """Update existing team information

        :type kwargs: dict
        :param kwargs: a dict to store update information for team

        :rtype: dict
        :return: updated team information in a dict
        """
        team = self.__get_team_by_id(kwargs["id"])
        if not team:
            return not_found("team not exists")

        # avoid duplicate team with same names
        if "name" in kwargs and kwargs["name"] != team.name:
            if self.__get_team_by_name(g.hackathon.id, kwargs["name"]):
                return precondition_failed("team with the same name exists already")

        self.__validate_team_permission(g.hackathon.id, team, g.user)

        # hackathon.modify(**update_items)
        # team.name = kwargs.get("name", team.name)
        # team.description = kwargs.get("description", team.description)
        # team.logo = kwargs.get("logo", team.logo)

        kwargs.pop("id", None)  # id should not be included
        team.modify(**kwargs)
        team.update_time = self.util.get_now()

        team.save()

        return self.__team_detail(team)
Exemple #10
0
    def add_admin(self, args):
        """Add a new administrator on a hackathon

        :type args: dict
        :param args: http request body in json format

        :return hackathon response 'ok' if successfully added.
            'not_found' if email is invalid or user not found.
            'internal_server_error' if any other unexpected exception caught
        """
        user = self.user_manager.get_user_by_email(args.get("email"))
        if user is None:
            return not_found("user not found")

        if self.register_manager.is_user_registered(user.id, g.hackathon):
            return precondition_failed("Cannot add a registered user as admin",
                                       friendly_message="该用户已报名参赛,不能再被选为裁判或管理员。请先取消其报名")

        try:
            ahl = self.db.find_first_object(AdminHackathonRel,
                                            AdminHackathonRel.user_id == user.id,
                                            AdminHackathonRel.hackathon_id == g.hackathon.id)
            if ahl is None:
                ahl = AdminHackathonRel(
                    user_id=user.id,
                    role_type=args.get("role_type", ADMIN_ROLE_TYPE.ADMIN),
                    hackathon_id=g.hackathon.id,
                    remarks=args.get("remarks"),
                    create_time=self.util.get_now()
                )
                self.db.add_object(ahl)
            return ok()
        except Exception as e:
            self.log.error(e)
            return internal_server_error("create admin failed")
    def leave_team(self, hackathon_id, team_name):
        """Leave a team by user

        :type hackathon_id: int
        :param hid: hackathon id

        :type team_name: str|unicode
        :param team_name: team name

        :rtype: bool
        :return: if leave_team success, return ok. if not ,return bad request.
        """

        team = self.__get_team_by_name(hackathon_id, team_name)
        if not team:
            # if team don't exist, do nothing
            return ok()

        # if user is not team leader
        if team.leader_id != g.user.id:
            self.db.delete_all_objects_by(UserTeamRel, hackathon_id=hackathon_id, user_id=g.user.id)
            return ok("You have left the team")

        # if user is team leader
        if len(self.__get_team_members(team)) >= 2:
            return precondition_failed("Please promote a new team leader, before leave team.")
        else:
            return self.dismiss_team(hackathon_id, team_name)
Exemple #12
0
    def start_expr(self, hackathon_name, template_name, user_id):
        """
        A user uses a template to start a experiment under a hackathon
        :param hackathon_name:
        :param template_name:
        :param user_id:
        :return:
        """
        hack_temp = self.__check_template_status(hackathon_name, template_name)
        if hack_temp is None:
            return not_found('hackathon or template is not existed')

        hackathon = hack_temp[0]
        # if not self.register_manager.is_user_registered(user_id, hackathon):
        #     return forbidden("user not registered or not approved")

        if hackathon.event_end_time < self.util.get_now():
            self.log.warn("hackathon is ended. The expr starting process will be stopped")
            return precondition_failed('hackathen is ended')

        template = hack_temp[1]

        if user_id > 0:
            expr = self.__check_expr_status(user_id, hackathon, template)
            if expr is not None:
                return self.__report_expr_status(expr)

        # new expr
        return self.__start_new_expr(hackathon, template, user_id)
    def join_team(self, hackathon_id, team_name, user):
        """Join a team will create a record on user_team_rel table which status will be 0.

        :type hackathon_id: int
        :param hackathon_id: hackathon id

        :type team_name: str | unicode
        :param team_name: team name

        :type user: User
        :param user: the user to join a team

        :rtype: dict
        :return: if user already joined team or team not exist, return bad request. Else, return a dict of joined
            details.
        """
        if self.db.find_first_object_by(UserTeamRel, hackathon_id=hackathon_id, user_id=g.user.id):
            return precondition_failed("You have joined another team, please quit first.")

        team = self.__get_team_by_name(hackathon_id, team_name)
        if team:
            candidate = UserTeamRel(join_time=self.util.get_now(),
                                    update_time=self.util.get_now(),
                                    status=TeamMemberStatus.Init,
                                    hackathon_id=hackathon_id,
                                    user_id=user.id,
                                    team_id=team.id)
            self.db.add_object(candidate)
            return candidate.dic()
        else:
            return not_found("team not found !")
    def update_team(self, kwargs):
        """Update existing team information

        :type kwargs: dict
        :param kwargs: a dict to store update information for team

        :rtype: dict
        :return: updated team information in a dict
        """
        if "id" not in kwargs:
            return bad_request("Please choose a team to update")

        team = self.__get_team_by_id(kwargs["id"])
        if not team:
            return not_found("team not exists")

        # avoid duplicate team with same names
        if "team_name" in kwargs and kwargs["team_name"] != team.name:
            if self.__get_team_by_name(g.hackathon.id, kwargs["team_name"]):
                return precondition_failed("team with the same name exists already")

        self.__validate_team_permission(g.hackathon.id, team, g.user)
        self.db.update_object(team,
                              name=kwargs.get("team_name", team.name),
                              description=kwargs.get("description", team.description),
                              git_project=kwargs.get("git_project", team.git_project),
                              logo=kwargs.get("logo", team.logo),
                              update_time=self.util.get_now())
        return team.dic()
    def update_team_member_status(self, operator, user_team_rel_id, status):
        """ update user's status on selected team. if current user doesn't have permission, return bad request.
        Else, update user's status

        :type status: int
        :param status: the status of the team member, see TeamMemberStatus in constants.py

        :rtype: bool
        :return: if update success, return ok. if not , return bad request.
        """
        rel = self.db.find_first_object_by(UserTeamRel, id=user_team_rel_id)
        if not rel:
            return not_found()

        team = rel.team
        self.__validate_team_permission(rel.hackathon_id, team, operator)

        if rel.user_id == team.leader_id:
            return precondition_failed("cannot update status of team leader")

        if status == TeamMemberStatus.Approved:
            # disable previous team first
            self.db.delete_all_objects_by(UserTeamRel,
                                          hackathon_id=rel.hackathon_id,
                                          user_id=rel.user_id,
                                          status=TeamMemberStatus.Approved)
            self.db.delete_all_objects_by(Team, hackathon_id=rel.hackathon_id, leader_id=rel.user_id)

            rel.status = TeamMemberStatus.Approved
            rel.update_time = self.util.get_now()
            self.db.commit()
            return ok("approved")
        if status == TeamMemberStatus.Denied:
            self.db.delete_object(rel)
            return ok("Your request has been denied, please rejoin another team.")
    def create_registration(self, hackathon, user, args):
        """Register hackathon for user

        Will add a new record in table UserRegistrationRel if precondition fulfilled
        """
        self.log.debug("create_register: %r" % args)
        user_id = args['user_id']

        check_login_provider = self.__is_user_hackathon_login_provider(user, hackathon)
        if check_login_provider["fail"]:
            return login_provider_error("hackathon registration not login provider",
                                        friendly_message="当前黑客松活动只是使用"+",".join(check_login_provider["provides"])+"账户才能报名",
                                        provides=",".join(check_login_provider["provides"]))

        if self.is_user_registered(user.id, hackathon):
            self.log.debug("user %d already registered on hackathon %d" % (user_id, hackathon.id))
            return self.get_registration_detail(user, hackathon)

        if self.admin_manager.is_hackathon_admin(hackathon.id, user.id):
            return precondition_failed("administrator cannot register the hackathon", friendly_message="管理员或裁判不能报名")

        if hackathon.registration_start_time and hackathon.registration_start_time > self.util.get_now():
            return precondition_failed("hackathon registration not opened", friendly_message="报名尚未开始")

        if hackathon.registration_end_time and hackathon.registration_end_time < self.util.get_now():
            return precondition_failed("hackathon registration has ended", friendly_message="报名已经结束")

        if self.__is_hackathon_filled_up(hackathon):
            return precondition_failed("hackathon registers reach the upper threshold",
                                       friendly_message="报名人数已满")

        try:
            args["status"] = RGStatus.AUTO_PASSED if hackathon.is_auto_approve() else RGStatus.UNAUDIT
            args['create_time'] = self.util.get_now()
            user_hackathon_rel = self.db.add_object_kwargs(UserHackathonRel, **args).dic()

            # create a team as soon as user registration approved(auto or manually)
            if hackathon.is_auto_approve():
                self.team_manager.create_default_team(hackathon, user)

            self.__update_register_stat(hackathon)
            return user_hackathon_rel
        except Exception as e:
            self.log.error(e)
            return internal_server_error("fail to create register")
    def validate_created_args(self, hackathon, args):
        self.log.debug("create_register: %r" % args)
        user_id = args['user_id']
        register = self.get_registration_by_user_and_hackathon(user_id, hackathon.id)
        if register is not None and register.deleted == 0:
            self.log.debug("user %d already registered on hackathon %d" % (user_id, hackathon.id))
            return False, register.dic()

        if hackathon.registration_start_time > self.util.get_now():
            return False, precondition_failed("hackathon registration not opened", friendly_message="报名尚未开始")

        if hackathon.registration_end_time < self.util.get_now():
            return False, precondition_failed("hackathon registration has ended", friendly_message="报名已经结束")

        if not self.check_register_enrollment(hackathon):
            return False, precondition_failed("hackathon registers reach the upper threshold",
                                              friendly_message="报名人数已满")
        return True, ""
 def test_create_hackathon_register_registration_already_finished(self, get_method):
     get_method.retrun_value = None
     args = {'user_id': 1}
     hackathon = Hackathon(id=1,
                           registration_start_time=self.get_now() - datetime.timedelta(seconds=30),
                           registration_end_time=self.get_now() - datetime.timedelta(seconds=30))
     self.assertEqual(self.register_manager.create_registration(hackathon, args),
                      precondition_failed("hackathon registration has ended", friendly_message="报名已经结束"))
     get_method.assert_called_once_with(1, 1)
    def create_team(self, kwargs):
        """Create new team by given args.

        user only allow to join or create 1 team. So if user joined or created team before, will be get failed
        when creating new team.

        :type kwargs: dict
        :param kwargs: a dict of required information to create new team

        :rtype: dict
        :return: created team information
        """
        user_team_rel = self.__get_team_by_user(g.user.id, g.hackathon.id)
        if user_team_rel:
            self.log.debug("fail to create team since user is already in some team.")
            return precondition_failed("you must leave the current team first")

        if "team_name" not in kwargs:
            return bad_request("Please provide a team name")

        # check team name to avoid duplicate name
        team_name = kwargs["team_name"]
        if self.__get_team_by_name(g.hackathon.id, team_name):
            return precondition_failed("The team name is existed, please provide a new name")

        team = Team(name=team_name,
                    description=kwargs.get("description"),
                    git_project=kwargs.get("git_project"),
                    logo=kwargs.get("logo"),
                    create_time=self.util.get_now(),
                    update_time=self.util.get_now(),
                    leader_id=g.user.id,
                    hackathon_id=g.hackathon.id)
        self.db.add_object(team)

        user_team_rel = UserTeamRel(join_time=self.util.get_now(),
                                    update_time=self.util.get_now(),
                                    status=TeamMemberStatus.Approved,
                                    hackathon_id=g.hackathon.id,
                                    user_id=g.user.id,
                                    team_id=team.id)
        self.db.add_object(user_team_rel)

        return team.dic()
    def test_validate_deleted_args_delete_creator(self):
        ahl = AdminHackathonRel(id=7, user_id=7, hackathon_id=7)
        hackathon = Hackathon(id=7, creator_id=7)

        db_adapter = Mock()
        db_adapter.find_first_object.side_effect = [ahl, hackathon]
        am = AdminManager(db_adapter)

        status, return_info = am.validate_deleted_args(1)
        self.assertFalse(status)
        self.assertEqual(return_info, precondition_failed("hackathon creator can not be deleted"))
        self.assertEqual(db_adapter.find_first_object.call_count, 2)
    def delete_template_from_team(self, template_id):
        """Delete template from current user's team

        Team should exist and current login user must be the leader
        """
        team = self.__get_valid_team_by_user(g.user.id, g.hackathon.id)
        if not team:
            return precondition_failed("you don't join any team so you cannot add teamplate")

        if team.leader.id != g.user.id:
            return forbidden("team leader required")
        else:
            return self.hackathon_template_manager.delete_template_from_hackathon(template_id)
    def add_template_for_team(self, args):
        """Add template to team of the current user by template name

        template_id must be included in args. Current login user must have a team and HE must be its leader
        """
        if "template_id" not in args:
            return bad_request("template id invalid")

        team = self.__get_valid_team_by_user(g.user.id, g.hackathon.id)
        if not team:
            return precondition_failed("you don't join any team so you cannot add teamplate")

        if team.leader.id != g.user.id:
            return forbidden("team leader required")
        else:
            return self.hackathon_template_manager.add_template_to_hackathon(args["template_id"])
Exemple #23
0
    def create_default_team(self, hackathon, user):
        """Create a default new team for user after registration.

        Use user name as team name by default. Append user id in case user name is duplicate
        """
        user_team = self.__get_valid_team_by_user(user.id, hackathon.id)
        if user_team:
            self.log.debug("fail to create team since user is already in some team.")
            return precondition_failed("you must leave the current team first")

        team_name = self.__generate_team_name(hackathon, user)
        team_member = TeamMember(join_time=self.util.get_now(), status=TEAM_MEMBER_STATUS.APPROVED, user=user)
        team = Team(name=team_name, leader=user, logo=user.avatar_url, hackathon=hackathon, members=[team_member])
        team.save()

        return team.dic()
    def delete_admin(self, ahl_id):
        """Delete admin on a hackathon

        creator of the hackathon cannot be deleted.

        :returns ok() if succeeds or it's deleted before.
                 precondition_failed if try to delete the creator
        """
        ahl = self.db.find_first_object(AdminHackathonRel, AdminHackathonRel.id == ahl_id)
        if not ahl:
            return ok()

        hackathon = self.hackathon_manager.get_hackathon_by_id(ahl.hackathon_id)
        if hackathon and hackathon.creator_id == ahl.user_id:
            return precondition_failed("hackathon creator can not be deleted")

        self.db.delete_all_objects(AdminHackathonRel, AdminHackathonRel.id == ahl_id)
        return ok()
    def delete_admin(self, user_hackathon_id):
        """Delete admin on a hackathon

        creator of the hackathon cannot be deleted.

        :returns ok() if succeeds or it's deleted before.
                 precondition_failed if try to delete the creator
        """
        user_hackathon = UserHackathon.objects(id=user_hackathon_id).first()
        if not user_hackathon:
            return ok()

        hackathon = user_hackathon.hackathon
        if hackathon and hackathon.creator == user_hackathon.user:
            return precondition_failed("hackathon creator can not be deleted")

        user_hackathon.delete()
        return ok()
    def delete_host_server(self, host_server_id):
        """
        delete a docker host_server for a hackathon.

        :param hackathon_id: the id of a hackathon in DB
        :type hackathon_id: Integer

        :param host_server_id: the id of host_server in DB
        :type host_server_id: Integer

        :return: ok() if succeeds or this host_server doesn't exist
                 precondition_failed() if there are still some containers running
        """
        vm = self.db.find_first_object_by(DockerHostServer, id=host_server_id)
        if vm is None:
            self.log.warn('delete docker_host fail, not find hostserver_id:' + host_server_id)
            return ok()
        if not vm.container_count == 0:
            return precondition_failed("", "fail to delete: there are some containers running in this server")
        self.db.delete_object(vm)
        return ok()
    def kick_or_leave(self, operator, team_id, user_id):
        rel = self.db.find_first_object_by(UserTeamRel, team_id=team_id, user_id=user_id)
        if not rel:
            return not_found()

        team = rel.team
        hackathon = rel.hackathon
        user = rel.user
        if team.leader_id == rel.user_id:  # if the user to be leaved or kicked is team leader
            return precondition_failed("leader cannot leave team")

        if operator.id == rel.user_id:  # leave team
            self.db.delete_object(rel)
            self.db.commit()
            self.create_default_team(rel.hackathon, rel.user)
        else:  # kick somebody else
            self.__validate_team_permission(hackathon.id, team, operator)
            self.db.delete_object(rel)
            self.create_default_team(hackathon, user)

        return ok()
    def grant_award_to_team(self, hackathon, context):
        team = self.__get_team_by_id(context.team_id)
        if not team:
            return not_found("team not found")

        award = filter(lambda a: str(a.id) == context.award_id, hackathon.awards)
        assert len(award) < 2
        if not award:
            return not_found("award not found")
        award = award[0]

        if team.hackathon.id != hackathon.id:
            return precondition_failed("hackathon doesn't match")

        team_award = filter(lambda a: str(a) == context.award_id, team.awards)
        assert len(team_award) < 2

        if not team_award:
            team.awards.append(uuid.UUID(context.award_id))
            team.save()

        return self.__award_with_detail(context.award_id)
    def add_admin(self, args):
        """Add a new administrator on a hackathon

        :type args: dict
        :param args: http request body in json format

        :return hackathon response 'ok' if successfully added.
            'not_found' if email is invalid or user not found.
            'internal_server_error' if any other unexpected exception caught
        """
        user = self.user_manager.get_user_by_id(args.get("id"))
        if user is None:
            return not_found("user not found")

        if self.register_manager.is_user_registered(user.id, g.hackathon):
            return precondition_failed("Cannot add a registered user as admin",
                                       friendly_message="该用户已报名参赛,不能再被选为裁判或管理员。请先取消其报名")

        try:
            user_hackathon = UserHackathon.objects(user=user.id, hackathon=g.hackathon.id).first()

            if user_hackathon is None:
                uhl = UserHackathon(
                    user=user,
                    hackathon=g.hackathon,
                    role=args.get("role"),
                    status=HACK_USER_STATUS.AUTO_PASSED,
                    remark=args.get("remark")
                )
                uhl.save()
            else:
                user_hackathon.role = args.get("role")
                user_hackathon.remark = args.get("remark")
                user_hackathon.save()

            return ok()
        except Exception as e:
            self.log.error(e)
            return internal_server_error("create admin failed")
    def update_team(self, kwargs):
        """Update existing team information

        :type kwargs: dict
        :param kwargs: a dict to store update information for team

        :rtype: dict
        :return: updated team information in a dict
        """
        team = self.__get_team_by_id(kwargs["id"])
        if not team:
            return not_found("team not exists")

        # avoid duplicate team with same names
        if "name" in kwargs and kwargs["name"] != team.name:
            if self.__get_team_by_name(g.hackathon.id, kwargs["name"]):
                return precondition_failed("team with the same name exists already")

        self.__validate_team_permission(g.hackathon.id, team, g.user)

        # hackathon.modify(**update_items)
        # team.name = kwargs.get("name", team.name)
        # team.description = kwargs.get("description", team.description)
        # team.logo = kwargs.get("logo", team.logo)

        kwargs.pop('id', None)  # id should not be included
        team.modify(**kwargs)
        team.update_time = self.util.get_now()
        team.save()

        if "dev_plan" in kwargs and kwargs["dev_plan"] and not kwargs["dev_plan"] == "" \
                and team.hackathon.config.get(HACKATHON_CONFIG.DEV_PLAN_REQUIRED, False):
            t = threading.Thread(target=self.__email_notify_dev_plan_submitted, args=(team,))
            t.setDaemon(True)
            t.start()

        return self.__team_detail(team)