Пример #1
0
def message_remove(token, message_id):
    '''
    Deletes a valid message based on message id
    '''
    check_token(token)
    channel_specific = get_channel_by_msg_id(message_id)
    message_specific = get_message_by_msg_id(message_id)
    if not is_channel_owner(token, channel_specific) and not is_message_owner(
            token, message_id) and not is_slackr_owner(token):
        raise AccessError(description='Not qualified to edit')
    channel_specific['messages'].remove(message_specific)
    return {}
Пример #2
0
def user_profile(token, user_id):
    '''finds and returns a user profile

    :param token: jwt token
    :type token: str
    :param user_id: id corresponding to the target user
    :type user_id: int
    :return: contains u_id, email, name_first, name_last, handle_str
    :rtype: dict
    '''
    check_token(token)
    return {'user': get_user_information(user_id)}
Пример #3
0
def channels_listall(token):
    '''
    loops through CHANNELS and generates a list of all channel_ids and
    their associated names.
    '''
    check_token(token)
    glob_channels = get_channels()

    return {
        'channels': [{
            'channel_id': channel_id,
            'name': glob_channels[channel_id]['name']
        } for channel_id in glob_channels]
    }
Пример #4
0
def message_edit(token, message_id, message):
    '''
    Changes a valid message. deletes message if the message is changed to be empty
    '''
    check_token(token)
    channel_specific = get_channel_by_msg_id(message_id)
    message_specific = get_message_by_msg_id(message_id)
    if not is_channel_owner(token, channel_specific):
        if not is_message_owner(token, message_id):
            if not is_slackr_owner(token):
                raise AccessError(description='Not qualified to edit')
    if len(message) == 0:
        channel_specific['messages'].remove(message_specific)
    else:
        message_specific['message'] = message
    return {}
Пример #5
0
def message_sendlater(token, channel_id, message, time_sent):
    '''
    sends a message at a given time_sent, where time_sent is a unix timestamp
    greater than the current time.
    '''
    u_id = check_token(token)
    if not is_valid_channel(channel_id):
        raise InputError(description="No channel exists with that ID")
    if not is_user_a_member(channel_id, u_id):
        raise AccessError(description='You are not a member of this channel')
    if len(message) > 1000 or len(message) < 1:
        raise InputError(
            description=
            'Your message should be less than 1000 characters and at least 1 character'
        )
    curr_time = get_current_timestamp()
    if curr_time >= time_sent:
        raise InputError(description="You can not send a message back in time")
    delay = time_sent - curr_time
    message_id = get_num_messages()
    set_num_messages(message_id + 1)
    message_template = create_message(u_id, message_id, time_sent, message)
    timer = Timer(delay, sendlater_end, args=[channel_id, message_template])
    timer.start()
    return {'message_id': message_id}
Пример #6
0
def is_message_owner(token, message_id):
    """
    Determine whether the user is the owner of the message
    """
    message = get_message_by_msg_id(message_id)
    u_id = check_token(token)
    return u_id == message['u_id']
Пример #7
0
def users_all(token):
    '''Returns a list of all users

    :param token: jwt token
    :type token: str
    :return: contains u_id, email, name_first, name_last, handle_str for each user
    :rtype: dict
    '''
    check_token(token)
    users = get_users()
    return {
        'users': [
            get_user_information(user_id) for user_id in users
            if not is_user_disabled(user_id)
        ],
    }
Пример #8
0
def is_slackr_owner(token):
    """
    Determine whether the user owns the slackr
    """
    owners = get_slackr_owners()
    u_id = check_token(token)
    return u_id in owners
Пример #9
0
def message_send(token, channel_id, message):
    '''
    adds message to a channels list of messages
    expects parameter types:
        token: str
        channel_id: int
        message: str
    returns dictionary
    '''
    user_id = check_token(token)

    if len(message) > 1000 or len(message) < 1:
        raise InputError(
            description=
            'Your message should be less than 1000 characters and at least 1 character'
        )
    if not is_valid_channel(channel_id):
        raise InputError
    if not is_user_a_member(channel_id, user_id):
        raise AccessError
    message_id = get_num_messages()
    glob_channels = get_channels()
    channel = glob_channels[channel_id]
    time_created = get_current_timestamp()

    if message.startswith('/hangman'):
        start_hangman(channel_id, user_id, time_created, message_id)
    elif message.startswith('/guess'):
        guess(message, channel_id, user_id, time_created, message_id)
    else:
        channel['messages'].insert(
            0, create_message(user_id, message_id, time_created, message))
    set_num_messages(message_id + 1)
    return {'message_id': message_id}
Пример #10
0
def permission_change(token, u_id, permission_id):
    '''change a user's permissions on the server

    :param token: jwt token
    :type token: str
    :param u_id: User id corresponding to the target user
    :type u_id: int
    :param permission_id: ID of user new permissions
    :type permission_id: int
    :raises InputError: u_id does not correspond to a user
    :raises InputError: Invalid Permission ID
    :raises AccessError: User is not a slackr owner
    :return: empty dictionary
    :rtype: dict
    '''
    user_id = check_token(token)
    if not user_id in get_slackr_owners():
        raise AccessError(
            description='You are not permitted to perform this action')

    if not is_valid_user(u_id):
        raise InputError(description='User does not exist')
    if permission_id not in (1, 2):
        raise InputError(description='Invalid permission ID')
    # all possible errors raised.
    if permission_id == 1:
        get_users()[u_id]['is_owner'] = True
    elif permission_id == 2:
        get_users()[u_id]['is_owner'] = False

    return {}
Пример #11
0
def channel_details(token, channel_id):
    '''
        returns a dictionary of information about the channel and it's users
    '''
    user_id = check_token(token)
    if not is_valid_channel(channel_id):
        raise InputError(description="Invalid channel id")

    if not is_user_a_member(channel_id, user_id):
        raise AccessError(
            description="User does not have access to this channel")
    owner_members = []
    all_members = []
    for user_id in get_channel_owners(channel_id):
        member_info = get_member_information(user_id)
        owner_members.append(member_info)
        all_members.append(member_info)

    for user_id in get_channel_members(channel_id):
        member_info = get_member_information(user_id)
        all_members.append(member_info)
    return {
        'name': get_channels()[channel_id]['name'],
        'owner_members': owner_members,
        'all_members': all_members
    }
Пример #12
0
def message_pin(token, message_id):
    '''
    Pins a message in a channel
    '''
    u_id = check_token(token)
    channel_specific = get_channel_by_msg_id(message_id)
    message_specific = get_message_by_msg_id(message_id)

    if u_id not in channel_specific['members'] and not is_channel_owner(
            token, channel_specific):
        raise AccessError(
            description=
            'The authorised user is not a member of the channel that the message is within'
        )

    if not is_channel_owner(token, channel_specific):
        raise InputError(description='The authorised user is not an owner')

    if message_specific['is_pinned']:
        raise InputError(
            description='Message with ID message_id is already pinned')

    if is_channel_owner(token, channel_specific
                        ) is True and message_specific['is_pinned'] is False:
        message_specific['is_pinned'] = True

    return {}
Пример #13
0
def channel_messages(token, channel_id, start):
    '''
        returns a dictionary containing:
            messages: a list of messages starting with the most recent at index 0
            start: the index of the starting message
            end: the index of the last message
    '''
    user_id = check_token(token)

    if not is_valid_channel(channel_id):
        raise InputError

    if not is_user_a_member(channel_id, user_id):
        raise AccessError

    channel = get_channels()[channel_id]
    if start > len(channel['messages']):
        raise InputError

    end = start + 50
    if end > len(channel['messages']):
        end = -1
    set_reacted_messages(user_id, channel['messages'][start:start + 50])
    return {
        'messages': channel['messages'][start:start + 50],
        'start': start,
        'end': end,
    }
Пример #14
0
def user_in_channel_by_msg_id(message_id, token):
    """
    Determine whether or not the user is in that channel which contains message_id
    """

    u_id = check_token(token)
    channels = get_channel_by_msg_id(message_id)
    return u_id in channels['members'] or u_id in channels['owners']
Пример #15
0
def is_channel_owner(token, channel):
    """
    Determine whether the user is the owner of the channel
    """
    u_id = check_token(token)
    if u_id in channel['owners']:
        return True
    else:
        return False
Пример #16
0
def test_invalidation():
    '''
    A token that has been invalidated should raise an error
    '''
    for user_id in range(100):
        new_token = generate_token(user_id)
        invalidate_token(new_token)
        with pytest.raises(AccessError):
            assert check_token(new_token)
    assert len(get_users()) == 0
Пример #17
0
def standup_active(token, channel_id):
    '''
    if there is an active standup in the channel, returns unix timestamp of when standup will finish
    otherwise, returns None
    '''
    u_id = check_token(token)
    check_standup_inputs(channel_id, u_id)
    is_active = is_standup_active(channel_id)

    try:
        time_finish = get_standups()[channel_id]['time_created']
    except KeyError:
        time_finish = None
    return {'is_active': is_active, 'time_finish': time_finish}
Пример #18
0
def channel_join(token, channel_id):
    '''
    Adds a user to a channel if they are authorised to join it
    '''
    user_id = check_token(token)

    if not is_valid_channel(channel_id):
        raise InputError(description="No channel found with that ID")

    if not is_channel_public(
            channel_id) and not user_id in get_slackr_owners():
        raise AccessError(description="This channel is private")
    get_channel_members(channel_id).append(user_id)

    return {}
Пример #19
0
def channels_list(token):
    '''
    Loops through CHANNELS and generates a list of only the channels which
    contain the user as a member or as an owner
    '''
    u_id = check_token(token)
    glob_channels = get_channels()

    return {
        'channels': [{
            'channel_id': channel_id,
            'name': glob_channels[channel_id]['name']
        } for channel_id in glob_channels
                     if is_user_a_member(channel_id, u_id)]
    }
Пример #20
0
def channel_leave(token, channel_id):
    '''
    Removes a user from a channel
    '''
    user_id = check_token(token)

    if not is_valid_channel(channel_id):
        raise InputError

    if is_user_a_owner(channel_id, user_id):
        get_channel_owners(channel_id).remove(user_id)
    elif is_user_a_member(channel_id, user_id):
        get_channel_members(channel_id).remove(user_id)
    else:
        raise AccessError

    return {}
Пример #21
0
def search(token, query_str):
    ''' finds all messages containing the query str '''
    user_id = check_token(token)

    search_results = []
    channels = get_channels()
    for channel_id in channels:
        if not is_user_a_member(channel_id, user_id):
            continue
        for message in channels[channel_id]['messages']:
            if query_str in message['message']:
                search_results.append(message)
    sorted(search_results,
           key=lambda message: message['time_created'],
           reverse=True)
    set_reacted_messages(user_id, search_results)
    return {'messages': search_results}
Пример #22
0
def standup_send(token, channel_id, message):
    '''
    adds a given message to the buffer of messages to be sent when the standup ends.
    message is saved as 'handle_str: message', to be ready to be printed
    '''
    u_id = check_token(token)
    check_standup_inputs(channel_id, u_id)
    if len(message) > 1000:
        raise InputError(
            description='Message must be less than 1000 characters')
    if not is_standup_active(channel_id):
        raise InputError(
            description='There is no standup active in this channel')

    get_standups()[channel_id]['message'].append(
        f'{find_handle(u_id)}: {message}')

    return {}
Пример #23
0
def user_profile_setemail(token, email):
    '''Given a valid token and new email, updates a user's email address

    :param token: jwt token
    :type token: str
    :param email: new email
    :type email: str
    :raises InputError: If email is invalid according to is_new_email()
    :return: empty dictionary
    :rtype: dict
    '''
    user_id = check_token(token)
    if not is_new_email(user_id, email):
        raise InputError(description='Email invalid or already being used')

    user = get_users()[user_id]
    user['email'] = email
    return {}
Пример #24
0
def user_profile_sethandle(token, handle_str):
    '''Given a valid new handle_str and token, updates a user's handle_str

    :param token: jwt token
    :type token: str
    :param handle_str: new handle
    :type handle_str: str
    :raises InputError: If handle_str is invalid according to is_valid_handle()
    :return: empty dictionary
    :rtype: dict
    '''
    user_id = check_token(token)
    if not is_valid_handle(user_id, handle_str):
        raise InputError(description='Handle invalid or already being used')

    user = get_users()[user_id]
    user['handle_str'] = handle_str
    return {}
Пример #25
0
def channel_invite(token, channel_id, user_id):
    '''
    invites a user (with user id u_id) to join a channel with ID channel_id.
    Once invited the user is added to the channel immediately
    An input error is thrown when the user_id/channel_id  is invalid
    Access error when the user is not a member of the channel
    '''
    host_user_id = check_token(token)
    if not is_valid_user(user_id):
        raise InputError

    if not is_valid_channel(channel_id):
        raise InputError

    if not is_user_a_member(channel_id, host_user_id):
        raise AccessError

    get_channels()[channel_id]['members'].append(user_id)
    return {}
Пример #26
0
def user_remove(token, u_id):
    '''
    Removes a user from a channel, only a slackr Owner can use this function
    '''
    host_user_id = check_token(token)

    if not is_valid_user(u_id):
        raise InputError

    if not host_user_id in get_slackr_owners():
        raise AccessError

    for channel_id in get_channels():
        if is_user_a_owner(channel_id, u_id):
            get_channel_owners(channel_id).remove(u_id)
        elif is_user_a_member(channel_id, u_id):
            get_channel_members(channel_id).remove(u_id)

    glob_users = get_users()
    glob_users[u_id]['disabled'] = True
    return {}
Пример #27
0
def channel_removeowner(token, channel_id, user_id):
    '''
        Makes a channel owner a regular channel member
        the token must be one of the channel owners or the slackr owner
    '''
    owner_id = check_token(token)

    if not is_valid_channel(channel_id):
        raise InputError

    if not is_user_a_owner(channel_id,
                           owner_id) and not owner_id in get_slackr_owners():
        raise AccessError

    if not is_user_a_owner(channel_id, user_id):
        raise InputError

    if is_user_a_owner(channel_id, user_id):
        get_channel_owners(channel_id).remove(user_id)
    get_channel_members(channel_id).append(user_id)

    return {}
Пример #28
0
def standup_start(token, channel_id, length):
    '''
    starts a standup in a given channel for length amount of time
    creates blank message with time_finish timestamp, placeholder message_id,
    and stores it in glob_standups
    '''
    u_id = check_token(token)
    check_standup_inputs(channel_id, u_id)
    if is_standup_active(channel_id):
        raise InputError(
            description='A standup is already active in this channel')

    glob_standups = get_standups()
    time_finish = get_current_timestamp(length)

    message_template = create_message(u_id, -1, time_finish, [])
    glob_standups[channel_id] = message_template

    standup = Timer(length, standup_end, args=[channel_id])
    standup.start()

    return {'time_finish': time_finish}
Пример #29
0
def message_react(token, message_id, react_id):
    '''
    adds a reaction to a messages list of reactions
    expects parameter types:
        token: str
        message_id: int
        react_id: int
    returns empty dictionary
    '''
    u_id = check_token(token)
    message = get_message_by_msg_id(message_id)

    if react_id not in VALID_REACTS:
        raise InputError(description='Invalid react id')
    if not user_in_channel_by_msg_id(message_id, token):
        raise InputError(description='User is not in channel')
    for react in message['reacts']:
        if react['react_id'] == react_id:
            if u_id in react['u_ids']:
                raise InputError(description='Already reacted')
            react['u_ids'].append(u_id)
    return {}
Пример #30
0
def user_profile_setname(token, name_first, name_last):
    '''Given a valid token, name_first, name_last, updates a users name_first, name_last

    :param token: jwt token
    :type token: str
    :param name_first: new first name
    :type name_first: str
    :param name_last: new last name
    :type name_last: str
    :raises InputError: if either name_first or name_last is invalid
    :return: empty dictionary
    :rtype: dict
    '''
    user_id = check_token(token)
    if not (is_name_valid(name_first) and is_name_valid(name_last)):
        raise InputError(
            description='Names must be between 1 and 50 characters')

    user = get_users()[user_id]
    user['name_first'] = name_first
    user['name_last'] = name_last

    return {}