def invite(token, channel_id, u_id): 'This is the function for channel_invite' auth_store = get_auth_data_store # User ID of person inviting user_id_inviter = user_id_from_token(token) # Check if channel exists using helper function channel = get_channel(channel_id) # Check if userID is valid, InputError if not if not is_valid_user_id(u_id): raise InputError(description='Invalid user_id') # InputError if channel_id does not refer to a valid channel if channel is None: raise InputError(description='Invalid channel_id') # Check if u_id is already in channel, InputError if not if test_in_channel(int(u_id), channel): raise InputError(description='User is already a part of the channel') # Check if authorised user is a member of the channel, AccessError if not if not test_in_channel(user_id_inviter, channel): raise AccessError(description='Authorised user is not a member of the channel') # User is added new_user = user_details(u_id) channel['members'].append(new_user) return {}
def start(payload): 'function to start a standup' user = get_user_token(payload['token']) channel = get_channel(payload['channel_id']) standup = channel['standup'] if standup['is_active'] is False: if test_in_channel(user['u_id'], channel) is True: if payload['length'] > 0: length = payload['length'] standup['is_active'] = True time_finish = (datetime.now() + timedelta(seconds=length)).strftime("%H:%M:%S") standup['time_finish'] = time_finish timer = threading.Timer(length, end_standup, args=[payload]) timer.start() else: raise InputError(description='Negative length is invalid') else: raise AccessError(description='User not in channel') else: raise InputError(description='An active standup is running') return time_finish
def send(payload): # pylint: disable=R1711 'sends a message to get buffered in the standup queue' user = get_user_token(payload['token']) channel = get_channel(payload['channel_id']) standup = channel['standup'] if not test_in_channel(user['u_id'], channel): raise AccessError(description='User is not part of channel') if standup['is_active'] is not True: raise InputError(description='Active standup is not running') message = payload['message'] if len(message) > 1000: raise InputError(description='Message too long') new_message = { 'Name_first': user['name_first'], 'Message': message } standup['messages'].append(new_message) return
def details(token, channel_id): 'This is the function for channel_details' user = get_user_token(token) u_id1 = user['u_id'] owner_members = [] all_members = [] # Check if channel exists using helper function channel = get_channel(channel_id) # If the channel is public, safe to display details # If not then raise error for owner in channel['owners']: owner_members.append(user_details(owner['u_id'])) all_members.append(user_details(owner['u_id'])) for member in channel['members']: all_members.append(user_details(member['u_id'])) ret_package = { "name": channel['name'], "owner_members": owner_members, "all_members": all_members } # Get details of owners and members in the channel #if channel['is_public']: # return ret_package #name = channel['name'] # AccessError when authorised user is not a member of the channel if test_in_channel(u_id1, channel): return ret_package else: raise AccessError(description='Authorised user is not a member of the channel')
def addowner(token, channel_id, u_id): 'This is the function for channel_addowner' auth_store = get_auth_data_store channels_store = get_channel_data_store channel = get_channel(channel_id) user_id_adder = user_id_from_token(token) adder_dets = user_details(user_id_adder) addee_dets = user_details(u_id) # Check if channel exists using helper function channel = get_channel(channel_id) # InputError when user with user id u_id is already an owner of the channel if addee_dets in channel['owners']: raise InputError(description='Cannot add if user is already an owner of the channel') # InputError if user isn't even a member of the channel if not test_in_channel(u_id, channel): raise InputError(description='User is not a member of channel') # AccessError when the authorised user is not an owner of the slackr, or an owner of this # channel # Can't add someone as an owner if you're not an owner yourself if not check_owner(adder_dets, channel): raise AccessError(description='User is not an owner of the slackr, or an owner of this channel') # Otherwise user is added as an owner else: channel['owners'].append(addee_dets) channel['members'].remove(addee_dets) #channel['members'].remove(addee_dets) return {}
def leave(token, channel_id): 'This is the function for channel_leave' auth_store = get_auth_data_store channels_store = get_channel_data_store user = get_user_token(token) # Check if channel exists using helper function channel = get_channel(channel_id) # Check if authorised user is a member of the channel, AccessError if not if not test_in_channel(user['u_id'], channel): raise AccessError(description='Cannot leave channel when user is not a member in the first place') # User leaving channel user_det = user_details(user['u_id']) print(user_det) print(channel['owners']) if user_det in channel['owners']: channel['owners'].remove(user_det) print(channel['members']) if user_det in channel['members']: channel['members'].remove(user_det) return {}
def send(payload): ''' function to take a payload, create a new mesaage, fill in the parameters and append it to the channels messages store as well as the gloabal message_store ''' user = get_user_from('token', payload['token']) channel = get_channel(payload['channel_id']) if not test_in_channel(user['u_id'], channel): raise AccessError(description='User is not in channel') # create a message data type, and fill in details # then append to the channels list of messages txt = payload['message'] if len(txt) > 1000: raise InputError(description='Message is more than 1000 characters') # create the message dictionary new_message = create_message() new_message['u_id'] = user['u_id'] new_message['message'] = txt new_message['channel_id'] = payload['channel_id'] channel['messages'].append(new_message) if txt == '/hangman': if not channel['hangman_active']: hangman.start(channel) channel['hangman_active'] = True else: hangman.message(channel, 'There is already an active game running') hangman.message(channel, hangman.display_hangman()) if txt.split()[0] == '/guess': if not channel['hangman_active']: hangman.message( channel, 'There is not a current game of hangman running.\n' + r'If you would like to start one, type \hangman into the chat') else: if len(txt.split()) == 2: new_guess = txt.split()[1] if new_guess in r'!@#$%^&*()_+-=[]\;<>?/~`:': hangman.message(channel, 'Invalid guess, guess again') else: hangman.guess(channel, new_guess) else: hangman.message(channel, 'Invalid guess, guess again') # append it to the messages_store messages = get_messages_store() messages.append(new_message) save_messages_store() # append it to the channels file save_channel_store() return new_message
def sendlater(payload): ''' Function to create a message and have it be sent at a ''' user = get_user_from('token', payload['token']) channel = get_channel(payload['channel_id']) messages = get_messages_store() if not test_in_channel(user['u_id'], channel): raise InputError(description='User is not in channel') # create a message data type, and fill in details # then append to the channels list of messages txt = payload['message'] if len(txt) > 1000: raise InputError(description='Message is more than 1000 characters') # create the message dictionary time = payload['time_sent'] print(type(time)) if time < int(datetime.now().timestamp()): raise InputError(description='Unable to send as ' + 'time sent is a time in the past') new_message = create_message() new_message['time_created'] = time new_message['u_id'] = user['u_id'] new_message['message'] = txt new_message['channel_id'] = payload['channel_id'] # append it to the messages_store first messages.append(new_message) save_messages_store() interval = (time - datetime.now().timestamp()) # append to the channel message store at a later time timer = threading.Timer(interval, append_later, args=[new_message['message_id']]) timer.start() # debugging purposes for msg in channel['messages']: print(msg['message']) return new_message['message_id']
def pin(payload): # pylint: disable=R1711 'testing functionability for message pin' user = get_user_from('token', payload['token']) message = find_message(payload['message_id']) channel = get_channel(message['channel_id']) if message['is_pinned'] is True: raise InputError(description='Message is already pinned') if not test_in_channel(user['u_id'], channel): raise AccessError( description='You do not have permission to pin this message') if not check_owner(user, channel): raise InputError(description='You do not have permission') message['is_pinned'] = True return
def List(token): # pylint: disable=C0103 'implementations of channels all functions' channel_store = get_channel_data_store() channels = [] channel_info = {} user = get_user_token(token) u_id = user['u_id'] for channel in channel_store: if test_in_channel(u_id, channel): channel_info = { 'channel_id': channel['channel_id'], 'name': channel['name'], } channels.append(channel_info) print(channels) return channels
def react(payload): ''' Function to add a react to a given message ''' global REACT_IDS # pylint: disable=W0603 user = get_user_from('token', payload['token']) message = find_message(int(payload['message_id'])) channel = get_channel(message['channel_id']) if int(payload['react_id']) not in REACT_IDS: raise InputError(description='Unable to react with react_id ' + str(payload['react_id'])) if not test_in_channel(user['u_id'], channel): raise InputError(description='Unable to react as you are ' + 'not a part of that channel') for i in message['reacts']: if i['react_id'] == payload['react_id']: # this react is already present in the message # just add another u_id if user['u_id'] in i['u_ids']: # if the user has reacted, unreact them unreact(payload) i['u_ids'].append(user['u_id']) return # no previous react wih react_id new_react = { 'react_id': payload['react_id'], 'u_ids': [], 'is_user_reacted': False } new_react['u_ids'].append(user['u_id']) message['reacts'].append(new_react) return
def search(payload): ''' Given a query string, return a collection of messages in all of the channels that the user has joined that match the query. Results are sorted from most recent message to least recent message ''' channel_store = get_channel_data_store() return_message = [] user = get_user_token(payload['token']) query_str = payload['query_str'] # if the query is nothing if query_str == '': return [] for channel in channel_store: if test_in_channel(user['u_id'], channel): print("searching in channel: " + channel['name']) for msg in channel['messages']: if re.search(payload['query_str'].lower(), msg['message'].lower()): result = { 'message_id': msg['message_id'], 'u_id': msg['u_id'], 'message': msg['message'], 'time_created': msg['time_created'], 'reacts': msg['reacts'], 'is_pinned': msg['is_pinned'] } return_message.append(result) print(return_message) return return_message
def Listall(token): # pylint: disable=W0613, C0103 'implementations of channels listall function' channel_store = get_channel_data_store() user = get_user_from('token', token) channels_return = [] channel_info = {} if len(channel_store) == 0: # pylint: disable=C1801 # the channel store is empty return channels_return for channel in channel_store: channel_info = { 'channel_id': channel['channel_id'], 'name': channel['name'] } if channel['is_public']: channels_return.append(channel_info) elif test_in_channel(user['u_id'], channel): channels_return.append(channel_info) return channels_return
def unreact(payload): ''' Function to remove a react from a message ''' global REACT_IDS # pylint: disable=W0603 user = get_user_from('token', payload['token']) message = find_message(payload['message_id']) channel = get_channel(message['channel_id']) if int(payload['react_id']) not in REACT_IDS: raise InputError(description='Unable to react with react_id ' + str(payload['react_id'])) if not test_in_channel(user['u_id'], channel): raise InputError(description='Unable to react as you are ' + 'not a part of that channel') for i in message['reacts']: if i['react_id'] == payload['react_id']: # this react is already present in the message # just remove u_id if user['u_id'] not in i['u_ids']: raise InputError(description='Attempting to uncreact ' + 'a message you have not reacted to') i['u_ids'].remove(user['u_id']) if len(i['u_ids']) == 0: # pylint: disable=C1801 # no one else has reacted, so remove react message['reacts'].remove(i) print(message['reacts']) return # unable to find react of react_id in messages raise InputError(description='Message with ID message_id ' + 'does not contain an active react with with ID react_id')
def messages(token, channel_id, start): 'This is the function for channel_messages' auth_store = get_auth_data_store u_id = user_id_from_token(token) # Check if channel exists using helper function channel = get_channel(channel_id) # Check if authorised user is a member of the channel, AccessError if not if not test_in_channel(u_id, channel): raise AccessError(description='Authorised user is not a member of the channel') # InputError if start is not of type int if not isinstance(start, int): raise InputError(description='Start is not of type integer') # InputError when start is greater than or equal to the total number of messages in the channel if start > len(channel['messages']): raise InputError(description='Start is greater than or equal to the total number of messages in the channel') # Incorrect indexing if start < 0: raise InputError(description='Incorrect indexing') # When there are 0 messages if (len(channel['messages'])) == 0: return { "messages": [], "start": start, "end": -1 } messages_list = [] messages_dict = {} if start + 50 > len(channel['messages']): interval = start + 50 else: interval = len(channel['messages']) for msgs in channel['messages'][start: interval]: messages_dict = { 'message_id': msgs['message_id'], 'u_id': msgs['u_id'], 'message': msgs['message'], 'time_created': msgs['time_created'], 'reacts': msgs['reacts'], 'is_pinned': msgs['is_pinned'] } for reacts in msgs['reacts']: for users_reacted in reacts['u_ids']: if u_id in reacts['u_ids']: reacts['is_user_reacted'] = True messages_list.append(messages_dict) messages_list.reverse() if start < len(channel['messages']): if len(channel['messages'][start:]) > 50: end = start + 50 return { "messages": messages_list, "start": start, "end": end } if len(channel['messages'][start:]) < 50: return { "messages": messages_list, "start": start, "end": -1 }