def get_election(request):
    """
    GET -- Gets the current election
        Required Keys: None

    :param request:
    :return:
    """

    election_query = Election.objects.raw(
        "SELECT * FROM api_election WHERE endDate IS NULL OR endDate >= %s",
        [datetime.date.today()])

    if len(list(election_query)) == 0:
        return HttpResponse(json.dumps({
            "message": "No current election available",
            "status": "down"
        }),
                            content_type="application/json")

    current_election = election_query[0]

    with connection.cursor() as cursor:
        query = '''
        SELECT api_campaign.election_id AS current_election, 
            api_campaign.campaigner_id AS campaigner, api_campaign.id AS id, job, pitch, 
            api_interested.first_name AS first_name, api_interested.last_name AS last_name
        FROM api_campaign 
        JOIN api_interested ON api_campaign.campaigner_id = api_interested.id
        WHERE election_id = %s
        '''
        cursor.execute(query, [current_election.id])
        campaigns = dictfetchall(cursor)
        query = '''
        SELECT campaign_id
        FROM api_vote
        JOIN api_campaign ON api_campaign.id = api_vote.campaign_id
        WHERE api_campaign.election_id = %s AND api_vote.voter_id = %s
        '''
        cursor.execute(
            query, [current_election.id,
                    id_for_member(request.user.email)])
        my_votes = [x['campaign_id'] for x in dictfetchall(cursor)]

    campaign_info = []
    for campaign in campaigns:
        # Get the number of votes
        votes = Vote.objects.raw(
            "SELECT * FROM api_vote WHERE campaign_id = %s", [campaign['id']])
        vote_count = len(list(votes))
        context = {'campaign': campaign, 'vote_count': vote_count}
        campaign_info.append(context)

    context = {
        'election': (serializeModel(current_election)),
        'campaigns': campaign_info,
        "order": [x[0] for x in JOBS],
    }
    print(context)
    return http_response(context)
def settingsRouter(request):
    """
    Allow members to get and edit their own settings.
    Expect input/output dictionary to be of the form
    {
        'private': _,
        'bio': _
    }
    :param request:
    :return:
    """

    session_id = id_for_member(request.user.email)
    if request.method == "GET":
        if session_id is None:
            return HttpResponse(json.dumps({"message": "No such member"}),
                                content_type="application/json")
        return member_config(session_id)
    elif request.method == "POST":
        dict_post = dict(request.POST.items())
        if not validate_keys(["private", "bio"], dict_post):
            HttpResponse(json.dumps(
                {'message': 'Missing parameters private or bio'}),
                         content_type='application/json',
                         status=400)
        if session_id is None:
            return HttpResponse(json.dumps({"message": "No such member"}),
                                content_type="application/json")
        return member_config_edit(session_id, dict_post)
def settingsBoardMemberRouter(request):
    """
    Allow board members to get/edit list of boardmembers.
    Expect input/output dictionary to be of the form
    {
        'boardmembers': [
            {
                'member_id': _
                'first_name': _
                'last_name': _
                'email': _
                'job': _
            },
            ...
        ]
    }
    :param request:
    :return:
    """

    session_id = id_for_member(request.user.email)

    if request.method == "GET":
        return boardmembers_config()
    elif request.method == "POST":
        # Can only change their jobs
        json_post_data = json.loads(request.body)
        if not validate_keys(["boardmembers"], json_post_data):
            HttpResponse(json.dumps(
                {'message': 'Missing parameters member_id or job'}),
                         content_type='application/json',
                         status=400)
        return boardmembers_config_edit(json_post_data)
def settingsInterestedCreateRouter(request):
    """
    Allows board members to add people to the club.
    Expect input dictionary to be of the form
    {
        'first_name': _,
        'last_name': _,
        'formerBoardMember': _,
        'email': _
    }
    :param request:
    :return:
    """
    session_id = id_for_member(request.user.email)
    json_post_data = json.loads(request.body)
    p_first_name = json_post_data.get('first_name', '')
    p_last_name = json_post_data.get('last_name', '')
    p_formerBoardMember = json_post_data.get('formerBoardMember', False)
    p_email = json_post_data.get('email', None)
    if p_email is None:
        return HttpResponse(json.dumps(
            {"message": "Missing required param email"}),
                            status=400,
                            content_type='application/json')
    interested = Interested(p_first_name, p_last_name, p_formerBoardMember,
                            p_email)
    return add_interested(interested)
Ejemplo n.º 5
0
def leave_party(request):
    session_email = request.user.username

    member_id = id_for_member(request.user.email)
    party = party_for_member(member_id)
    party_id = party.id

    return party_remove_member(party_id, member_id)
Ejemplo n.º 6
0
def member_party(request):
    """
    GET -- The logged in user's party
    :param request:
    :return:
    """
    member_id = id_for_member(request.user.email)
    return get_member_party(member_id)
Ejemplo n.º 7
0
def get_free_members(request):
    """
    GET -- "free members" in this context mean members who are not currently in a party or an ongoing match.
        This will represent the members who are available to invite to a party.
        The returned members will exclude the logged in user who made the request.
    :param request:
    :return:
    """
    member_id = id_for_member(request.user.email)
    return get_free_members_call(member_id)
def settingsQueueRouter(request):
    """
    Allows boardmembers to get all the current queues in db or add more queue types
    Expect the input/output dictionary to be of the form
    {
        'queues': [
            {
                'queue_id': _,
                'queue_type': _
            },
            ...
        ]
    }
    :param request:
    :return:
    """
    session_id = id_for_member(request.user.email)
    if not is_board_member(session_id):
        return HttpResponse(json.dumps(
            {"message": "You are not a board member."}),
                            content_type="application/json")
    if request.method == "GET":
        return get_all_queues_formatted()
    elif request.method == "POST":
        # Used to add more queue types to the db
        # dict_post = dict(request.POST.items()) <- For some reason, can't read POST dictionary from PostMan like this
        json_post_data = json.loads(request.body)
        if not validate_keys('queues', json_post_data):
            HttpResponse(json.dumps({'message': 'Missing parameter queues'}),
                         content_type='application/json',
                         status=400)
        return add_queues_formatted(json_post_data)
    elif request.method == "DELETE":
        # The input dictionary should hold information ONLY for the queues to be deleted
        json_delete_data = json.loads(request.body)
        if not validate_keys('queues', json_delete_data):
            HttpResponse(json.dumps({'message': 'Missing parameter queues'}),
                         content_type='application/json',
                         status=400)
        return delete_queues_formatted(json_delete_data)
def settingsSchedulesRouter(request):
    """
    POST/DELETE -- Allows board members to get the whole schedule and add to/edit/delete from schedule
    Expect input/output dictionary to be of the form
    {
        'schedule': [
            {
                'date': _,
                'number_of_courts': _
            },
            ...
        ]
    }
    :param request:
    :return:
    """
    session_id = id_for_member(request.user.email)
    if not is_board_member(session_id):
        return HttpResponse(json.dumps(
            {"message": "You are not a board member."}),
                            content_type="application/json")
    if request.method == "POST":
        # INSERT or UPDATE
        # dict_post = dict(request.POST.items())
        print(request.body)
        json_post_data = json.loads(request.body.decode('utf8'))
        if not validate_keys(["schedule"], json_post_data):
            HttpResponse(json.dumps({'message': 'Missing parameter schedule'}),
                         content_type='application/json',
                         status=400)
        return addto_edit_schedule(json_post_data)
    elif request.method == "DELETE":
        # The provided dictionary should ONLY contain information on the entries that are
        # intended to be deleted.
        dict_delete = json.loads(request.body.decode('utf8').replace("'", '"'))
        if not validate_keys(["schedule"], dict_delete):
            HttpResponse(json.dumps({'message': 'Missing parameter schedule'}),
                         content_type='application/json',
                         status=400)
        return delete_multiple_from_schedule(dict_delete)
Ejemplo n.º 10
0
def remove_member(request):
    """
        POST -- Removes a member from the logged in user's party
            Required Keys: member_id
        :param request:
        :return:
    """
    post_dict = dict(request.POST.items())

    my_id = id_for_member(request.user.email)
    party = party_for_member(my_id)

    if party is None:
        return http_response(message='You are not part of a party', code=400)

    party_id = party.id
    member_id = int(post_dict['member_id'])
    member = Member.objects.get(id=member_id)
    if member.party_id != party_id:
        return http_response(
            message='The specified member is not in your party!', code=400)
    return party_remove_member(party_id, member_id)
Ejemplo n.º 11
0
def add_member(request):
    """
        POST -- Adds a member to the logged in user's party
            Required Keys: id, delete
            Optional Keys: queue_id, add_members, remove_members
                NOTE: `add_members` and `remove_members` are comma separated lists of
                    member id's to add or remove from the party respectively

        :param request:
        :return:
    """

    post_dict = dict(request.POST.items())
    if not validate_keys(['member_id'], post_dict):
        return http_response({}, message="Keys not found", code=400)

    member_id = post_dict['member_id']
    my_id = id_for_member(request.user.email)
    party = party_for_member(my_id)
    party_id = party.id

    rawquery = Member.objects.raw(
        "SELECT * FROM api_member WHERE interested_ptr_id=%s AND party_id NOT NULL",
        [member_id])
    member_is_in_party = len(list(rawquery)) > 0
    if member_is_in_party:
        return http_response(message="Member is already in a party", code=400)

    members = Member.objects.raw(
        "SELECT * FROM api_member WHERE party_id NOT NULL AND party_id = %s AND interested_ptr_id = %s",
        [party_id, member_id])
    if len(list(members)) > 0:
        return http_response(message="Member is already part of party")

    response = run_connection(
        "UPDATE api_member SET party_id = %s WHERE interested_ptr_id = %s",
        party_id, member_id)
    return response
Ejemplo n.º 12
0
def _bypass_template_server(request, template, ensure_cookie=True):
    """
        This function takes the template string and renders
        and serves the template that has the same name.

        The function does forward any request.GET parameters.
        request.POST params are not considered because ideally
        we want all front end applications to be reversible,
        meaning that users' back function works. i.e. we shouldn't
        be rendering sensitive data but letting the api validate it
        asynchronously.

        :param request: HttpRequest Standard django request object
        :param data: str Template to render
    """

    # Forward all query params to the template
    # Flatten lists because django gives you query params
    # in lists regardless
    context = dict()
    if request.method == "GET":
        context = {'member_id': request.GET.get('member_id')}
        if context["member_id"] is None:
            context = dict()
    for key, value in context.items():
        if isinstance(value, list) and len(value) == 1:
            context[key] = value[0]
    is_board_bool = get_member_class(
        request.user.email) == MemberClass.BOARD_MEMBER if hasattr(
            request.user, 'email') else False
    context['is_board_member'] = is_board_bool
    response = render(request, template, context=context)
    if ensure_cookie:
        email = request.user.email
        response.set_cookie('member_id', str(id_for_member(email)))
        is_board = "true" if is_board_bool else "false"
        response.set_cookie('is_board_member', is_board)
    return response
def settingsCourtRouter(request):
    """
    Allows board members to get the info on all courts and add/edit courts.
    Expect the input/output dictionary to be of the form
    {
        'courts': [
            {
                'court_id': _,
                'queue_id': _
            },
            ...
        ]
        'court_types': [str, ...]
    }
    :param request:
    :return:
    """
    session_id = id_for_member(request.user.email)
    if request.method == "GET":
        return get_all_courts_formmated()
    elif request.method == "POST":
        # Used to add new courts OR change the queue types for the courts
        json_post_data = request.POST
        if not validate_keys('courts', json_post_data):
            HttpResponse(json.dumps({'message': 'Missing parameter courts'}),
                         content_type='application/json',
                         status=400)
        return addto_edit_courts_formatted(json_post_data)
    elif request.method == "DELETE":
        # The input dictionary should hold information ONLY for the courts to be deleted
        json_delete_data = json.loads(request.body.decode('utf8'))
        if not validate_keys('courts', json_delete_data):
            HttpResponse(json.dumps({'message': 'Missing parameter courts'}),
                         content_type='application/json',
                         status=400)
        return delete_courts_formatted(json_delete_data)
Ejemplo n.º 14
0
def create_party(request):
    """
    POST -- Creates a party. Anyone with Member permission or above can do this.
        Required Keys: queue_type, member_ids
            NOTE: member_ids is a comma separated list of ids to add to the party (EXCLUDES the user themselves)
    :param request:
    :return:
    """
    post_dict = dict(request.POST.items())
    print(post_dict)
    if not validate_keys(['queue_id', 'member_ids'], post_dict):
        return http_response({}, message="Keys not found", code=400)

    queue_id = post_dict['queue_id']
    queues = Queue.objects.raw("SELECT * FROM api_queue WHERE id = %s",
                               [queue_id])
    if len(list(queues)) <= 0:
        return http_response(message='Queue does not exist', code=400)

    queue = queues[0]

    queue_id = queue.id
    user_id = id_for_member(request.user.email)
    member_ids = post_dict['member_ids']
    member_ids = member_ids.split(",")  # list of ids to add to the party
    if user_id not in member_ids:
        member_ids.append(
            str(user_id))  # add self to the party, if not already specified

    # Check if the user is already in a party
    rawquery = Member.objects.raw(
        "SELECT * FROM api_member WHERE interested_ptr_id=%s AND party_id NOT NULL",
        [user_id])
    member_is_in_party = len(list(rawquery)) > 0
    if member_is_in_party:
        return http_response(message="User is already in a party", code=400)

    parties_with_max_id = Party.objects.raw(
        "SELECT * FROM api_party WHERE id = (SELECT MAX(id) FROM api_party)")
    if len(list(parties_with_max_id)) == 0:
        new_id = 0
    else:
        party_with_max_id = parties_with_max_id[0]
        new_id = party_with_max_id.id + 1

    # Check if there are other parties on this queue. If not, for each court associated with
    # this queue, check if there are matches with NULL endDateTime with the court id. If for a court_id, there
    # are no matches with a NULL endDateTime, that means there is no ongoing match on that court. In that case,
    # skip creating a party and just throw this group into a match on that empty court.
    open_court_id = queue_is_empty_with_open_court(queue_id)
    if open_court_id:
        # Create match
        # Randomize the member_id's into two teams (preferably equal numbers on each team)
        a_players = []
        b_players = []
        num_players = len(member_ids)
        for member_id in member_ids:
            choice = random.choice([True, False])
            if choice and len(a_players) < num_players / 2:
                # Add to a_players, if half of players aren't already on there
                a_players.append(member_id)
            else:
                if len(b_players) < num_players / 2:
                    b_players.append(member_id)
                else:
                    a_players.append(member_id)

        create_match(a_players=a_players,
                     b_players=b_players,
                     court_id=open_court_id)
        return http_response(message="OK", code=200)
    else:
        # Create party on the queue
        response = run_connection(
            "INSERT INTO api_party(id, queue_id) VALUES (%s, %s)", new_id,
            queue_id)
        if response.status_code != 200:
            return response

        # response = run_connection("UPDATE api_member SET party_id = %s WHERE interested_ptr_id = %s", new_id, member_id)
        # if response.status_code != 200:
        #     return response
        add_members_to_party(new_id, member_ids)

        return response