def presence(self, passwd_hash_string): """ Отправка сообщения о подключении к серверу :param passwd_hash_string: """ msg_presence = { "action": "presence", "time": int(time.time()), "type": "status", "user": { "account_name": self.username, "status": "Connect to server" } } with socket_lock: send_message(self.sock, msg_presence) try: response = self.sock.recv(1000000) ans = get_data_from_message(response) print('Начинаем авторизацию!', response) if 'response' in ans: if ans['response'] == 400: raise ServerError(ans['error']) elif ans['response'] == 511: # Если всё нормально, то продолжаем процедуру # авторизации. ans_data = ans['data'] hash = hmac.new(passwd_hash_string, ans_data.encode('utf-8'), 'MD5') digest = hash.digest() pubkey = self.keys.publickey().export_key().decode( 'ascii') print(pubkey) my_ans = { 'action': 'join', 'username': self.username, 'response': 511, 'data': binascii.b2a_base64(digest).decode('ascii'), 'keys': pubkey } send_message(self.sock, my_ans) response = self.sock.recv(1000000) ans = get_data_from_message(response) print(ans['response']) if ans['response'] != '200': print('Неверный пароль!') raise ServerError(ans['error']) else: print('Авторизация прошла успешно!') else: raise ServerError(ans['error']) except Exception: logger.exception('Ошибка при авторизации на сервере') self.connection_lost.emit() sys.exit(1)
def run(self): """ Запуск цикла основного потока. """ response_list = queue.Queue() self.connection_init() self.get_users(self.sock) print("Поехали") while self.work_flag: time.sleep(1) with socket_lock: try: self.sock.settimeout(1) response = self.sock.recv(1000000) except Exception as er: # print('timeout') pass else: response_list.put(response) finally: self.sock.settimeout(5) if not response_list.empty(): try: while not response_list.empty(): resp = response_list.get() print(resp) if resp: self.parse_answer(get_data_from_message(resp)) except Exception: self.logger.exception("Ошибка при конвертации ответа") self.connection_lost.emit() sys.exit(1)
def main(): SETTINGS = load_setting(is_server=False) parser = argparse.ArgumentParser(description='Server arguments') parser.add_argument('addr', type=str, nargs='*', default='', help='Clients address') parser.add_argument('port', type=int, nargs='*', default='', help='server port') args = parser.parse_args() if not args.port: server_port = SETTINGS["DEFAULT_PORT"] logger.warning("Успользуются порт сервера по умолчанию") else: server_port = args.port s = socket(AF_INET, SOCK_STREAM) s.bind((args.addr, server_port)) s.listen(SETTINGS['MAX_CONNECTION']) while True: client, addr = s.accept() try: data = get_data_from_message(client.recv(SETTINGS['MAX_PACKAGE_LENGTH'])) logger.debug(f'Сообщение: {data}, было отправлено клиентом: {addr}') except JSONDecodeError: logger.exception('Некорректный формат JSON файла') send_success_code(client) client.close()
def presence(s): msg_presence = { # Формируем presence-сообщение "action": "presence", "time": int(time.time()), "type": "status", "user": { "account_name": "Helik", "status": "connect" } } send_message(s, msg_presence ) # переходим в фукнцию и отправляем сообщение с параметрами data = get_data_from_message(s.recv(1000000)) print('Сообщение от сервера: ', data)
def presence(sock): msg_presence = { "action": "presence", "time": int(time.time()), "type": "status", "user": { "account_name": "Игорь", "status": "Connect to server" } } send_message(sock, msg_presence) try: response = sock.recv(1000000) except Exception: logger.exception('Ошибка при приеме ответа с сервера') sys.exit(1) return get_data_from_message(response)
def get_users(self, sock): """ Запрос списка пользователей с сервера """ msg_join = { "action": "get_users", "time": int(time.time()), "user_login": self.username } with socket_lock: send_message(sock, msg_join) try: response = sock.recv(1000000) except Exception: logger.exception('Ошибка при загрузке списка пользователей') self.connection_lost.emit() sys.exit(1) else: users = get_data_from_message(response) self.db.add_users_from_server(users["alert"])
def get_contacts(self, sock): """ Запрос списка контактов с сервера """ msg_join = { "action": "get_contacts", "time": int(time.time()), "user_login": self.username } with socket_lock: send_message(sock, msg_join) try: response = sock.recv(1000000) except Exception: self.logger.exception('Ошибка при приеме ответа с сервера') self.connection_lost.emit() sys.exit(1) else: contacts = get_data_from_message(response) self.db.add_users_from_server(contacts["alert"])
def key_request(self, user): """Метод запрашивающий с сервера публичный ключ пользователя.""" logger.debug(f'Запрос публичного ключа для {user}') msg = { "action": "public_key_request", "time": int(time.time()), "username": user } with socket_lock: send_message(self.sock, msg) try: response = self.sock.recv(1000000) ans = get_data_from_message(response) except Exception: self.logger.exception('Ошибка при приеме ответа с сервера') self.connection_lost.emit() sys.exit(1) else: if 'response' in ans and ans['response'] == '511': return ans['data'] else: logger.error( f'Не удалось получить ключ собеседника{user}.')
def test_empty_message_error(self): message = b'' with self.assertRaises(JSONDecodeError): get_data_from_message(message)
def test_get_correct_message(self): message = b'{"response": "200", "time": 1612953360}' self.assertEqual(get_data_from_message(message), { 'response': '200', 'time': 1612953360 })
from socket import * import time from common.utils import send_message, get_data_from_message def send_answer(client): msg_response = { "response": '200', 'time': int(time.time()) } send_message(client, msg_response) s = socket(AF_INET, SOCK_STREAM) # Создает сокет TCP s.bind(('', 7777)) # Присваивает порт 777 s.listen(5) # Переходит в режим ожидания запросов; while True: client, addr = s.accept() # принять установку на соединение data_client = get_data_from_message(client.recv(1000000)) # Идёт обращение в Json файл, где идёт расшифровка сообщения от клиента print('Сообщение: ', data_client, ', было отправлено клиентом: ', addr) send_answer(client) client.close()
from common.utils import get_settings, get_data_from_message, send_message # сервер создаёт сокет s = socket(AF_INET, SOCK_STREAM) # привязывает сокет к IP-адресу и порту машины s.bind(('', get_settings()['port'])) # готов принимать соединения s.listen(5) # параметры командной строки скрипта server.py -p <port>, -a <addr>: parser = argparse.ArgumentParser(description='command line server parameters') parser.add_argument('-a', '--addr', type=str, nargs='?', default='', help='ip address') parser.add_argument('-p', '--port', type=int, nargs='?', default=7777, help='tcp-port') args = parser.parse_args() print(args) while True: # принимает запрос на установку соединения client, addr = s.accept() # принимает сообщение клиента; print('Сообщение: ', get_data_from_message(client.recv(1000000)), ', было отправлено клиентом: ', addr) # формирует ответ клиенту; msg = { "response": '200', "alert": 'Привет, клиент!' } # отправляет ответ клиенту; send_message(client, msg) # закрывает соединение client.close()
# для реализации через configs.py # s.connect(HOST, PORT) # устанавливает соединение s.connect((get_settings()['host'], get_settings()['port'])) # параметры командной строки скрипта client.py <addr> [<port>]: parser = argparse.ArgumentParser(description='command line client parameters') parser.add_argument('addr', type=str, help='server ip address') parser.add_argument('port', type=int, nargs='?', default=7777, help='port') args = parser.parse_args() print(args) # формирует presence-сообщение msg = { "action": "presence", "time": time.ctime(time.time()), "type": "status", "user": { "account_name": "Samoryad", "status": "Привет, сервер!" } } # отправляет сообщение серверу; send_message(s, msg) # получает ответ сервера и разбирает сообщение сервера print('Сообщение от сервера: ', get_data_from_message(s.recv(1000000))) # закрывает соединение s.close()