示例#1
0
 def start_getting_messages(self):
     cached_messages = session.query(Message).filter(
         Message.chat_id == self.current_chat.chat_id).all()
     if cached_messages:
         self.on_messages_list_label.hide()
         self.add_messages(cached_messages, True)
     self.get_messages_thread.start()
示例#2
0
 def cache_messages(self, messages):
     session = db_session.create_session()
     for m in messages:
         m.chat_id = self.current_chat.chat_id
         cached_message = session.query(Message).filter(
             Message.unix_time == m.unix_time
             and Message.chat_id == m.chat_id).first()
         if not cached_message:
             session.add(m)
         session.commit()
示例#3
0
    def decrypt_data(self, data, key, signature, username):
        from constants import credentials, session, config
        from data.users import User
        unpadder = padding.PKCS7(128).unpadder()
        my_private = serialization.load_pem_private_key(open(hashlib.sha512(bytes(self.credentials["login"], "utf-8")).hexdigest() + ".pem", "rb").read(), password=bytes(self.credentials["password"], "utf-8"), backend=default_backend())
        if username == self.credentials["username"]:
            public_key = my_private.public_key()
        else:
            cached_user = session.query(User).filter(User.username == username).first()
            if cached_user:
                pub_response = {"status": "OK", "public_key": cached_user.public_key}
            else:
                pub_response = self.get_public_key(username)
                user = User()
                user.username = username
                user.public_key = pub_response["public_key"]
                session.add(user)
                session.commit()
            if pub_response["status"] == "OK":
                public_key = serialization.load_pem_public_key(bytes(pub_response["public_key"], "utf-8"), backend=default_backend())
            else:
                return {"status": "error", "error": "Error getting users public key"}
        key_iv = my_private.decrypt(
            bytes.fromhex(key),
            asymmetric_padding.OAEP(
                mgf=asymmetric_padding.MGF1(algorithm=hashes.SHA512()),
                algorithm=hashes.SHA512(),
                label=None
            )
        )
        key = key_iv[:32]
        iv = key_iv[32:]
        cipher = Cipher(algorithms.AES(key), modes.CBC(iv), backend=default_backend())
        decryptor = cipher.decryptor()
        decrypted_data = decryptor.update(bytes.fromhex(data)) + decryptor.finalize()
        decrypted_data = unpadder.update(decrypted_data) + unpadder.finalize()

        public_key.verify(
            bytes.fromhex(signature),
            hashlib.sha512(decrypted_data).digest(),
            asymmetric_padding.PSS(
                mgf=asymmetric_padding.MGF1(hashes.SHA512()),
                salt_length=asymmetric_padding.PSS.MAX_LENGTH
            ),
            hashes.SHA512()
        )
        payload = {
            "status": "OK",
            "data": decrypted_data,
            "sent_by": username,
            "key": key_iv.hex(),
            "signature": signature
        }

        return payload
示例#4
0
 def cache_chats(self, chats):
     session = db_session.create_session()
     for chat in chats:
         cached_chat = session.query(Chat).filter(Chat == chat).first()
         if not cached_chat:
             chat.last_message = json.dumps(chat.last_message)
             session.add(chat)
         elif cached_chat.unix_time != chat.unix_time:
             cached_chat.unix_time = chat.unix_time
             cached_chat.last_message = json.dumps(chat.last_message)
             session.merge(cached_chat)
     session.commit()
示例#5
0
 def update_contacts_list(self):
     result = session.query(Contact).all()
     self.contacts_list.clear()
     contacts = list()
     if result:
         for contact in result:
             contacts.append(contact)
             contact_widget = ContactWidget(contact, session)
             contact_item = QtWidgets.QListWidgetItem()
             contact_item.setSizeHint(QtCore.QSize(100, 70))
             self.contacts_list.addItem(contact_item)
             self.contacts_list.setItemWidget(contact_item, contact_widget)
     else:
         self.on_list_label.show()
示例#6
0
 def start_getting_chats(self):
     cached_chats = session.query(Chat).order_by(
         Chat.unix_time.desc()).all()
     for chat in cached_chats:
         chat_obj = Chat(chat.username, chat.chat_id, chat.last_message,
                         None)
         image = None
         self.chats.append(chat_obj)
         # payload = {"status": "OK", "data": chat.last_message, "type": MessageTypes.Text, "sent_by": "@8025a412", "viewed": True}
         chat_obj.last_message = json.loads(chat.last_message)
         chat_widget = ChatWidget(chat_obj, image, credentials["username"])
         chat_item = QtWidgets.QListWidgetItem()
         chat_item.setSizeHint(QtCore.QSize(100, 70))
         self.chats_list.addItem(chat_item)
         self.chats_list.setItemWidget(chat_item, chat_widget)
     self.get_chats_thread.start()
示例#7
0
 def signin_finished(self, response):
     global api, credentials, session, contacts
     login = self.login_line.text()
     password = self.password_line.text()
     if response["status"] == "OK":
         with open("credentials.json", "w", encoding="utf-8") as f:
             response["data"]["login"] = login
             response["data"]["password"] = password
             json.dump(response["data"], f)
         api = RocketAPI(login, password)
         api.credentials = response["data"]
         credentials = json.load(
             open("credentials.json", "r", encoding="utf-8"))
         db_session.global_init(f"""db/{hashlib.sha512(credentials['login'].
                                encode('utf-8')).hexdigest()}.db""")
         session = db_session.create_session()
         contacts = session.query(Contact).all()
         ChatsWindow().show()
         self.close()
     else:
         QtWidgets.QMessageBox.critical(self, "", response["error"])
示例#8
0
 def update_statuses(self, messages):
     try:
         session = db_session.create_session()
         for n, message in enumerate(messages):
             cached_message = session.query(Message).filter(
                 Message.unix_time == message.unix_time
                 and Message.chat_id == message.chat_id).first()
             if cached_message is not None:
                 if cached_message.viewed != message.viewed:
                     self.messages_list.itemWidget(
                         self.messages_list.item(n)
                     ).message_status_label.setPixmap(
                         QtGui.QPixmap("img/message_delivered.png").scaled(
                             20,
                             20,
                             transformMode=QtCore.Qt.SmoothTransformation))
                     cached_message.viewed = message.viewed
                     if cached_message.type == MessageTypes.Document:
                         cached_message.data = message.data
                     session.commit()
     except Exception as e:
         logging.warning(e)
示例#9
0
    def encrypt_data(self, data, username):
        from constants import session, config
        from data.users import User
        cached_user = session.query(User).filter(User.username == username).first()
        if cached_user:
            response = {"status": "OK", "public_key": cached_user.public_key}
        else:
            response = self.get_public_key(username)
            if response["status"] == "OK":
                user = User()
                user.username = username
                user.public_key = response["public_key"]
                session.add(user)
                session.commit()
            else:
                print(response["error"])
                return {"status": "error", "error": response["error"]}
        if response["status"] == "OK":
            # Pad data
            padder = padding.PKCS7(128).padder()
            padded_data = padder.update(data) + padder.finalize()

            # Define backend and key + iv
            backend = default_backend()
            key = os.urandom(32)
            iv = os.urandom(16)
            key_iv = key + iv

            # Encrypt all data
            cipher = Cipher(algorithms.AES(key), modes.CBC(iv), backend=backend)
            encryptor = cipher.encryptor()
            encrypted_data = encryptor.update(padded_data) + encryptor.finalize()

            # Get public key of user
            users_pub = serialization.load_pem_public_key(bytes(response["public_key"], "utf-8"), backend=default_backend())

            # Get your private and public keys
            my_private = serialization.load_pem_private_key(open(hashlib.sha512(bytes(self.credentials["login"], "utf-8")).hexdigest() + ".pem", "rb").read(), password=bytes(self.credentials["password"], "utf-8"), backend=default_backend())
            my_pub = my_private.public_key()

            # Encrypt keys
            user_encrypted_key = users_pub.encrypt(
                key_iv,
                asymmetric_padding.OAEP(
                    mgf=asymmetric_padding.MGF1(algorithm=hashes.SHA512()),
                    algorithm=hashes.SHA512(),
                    label=None
                )
            )
            my_encrypted_key = my_pub.encrypt(
                key_iv,
                asymmetric_padding.OAEP(
                    mgf=asymmetric_padding.MGF1(algorithm=hashes.SHA512()),
                    algorithm=hashes.SHA512(),
                    label=None
                )
            )

            # Sign hash of data
            signature = my_private.sign(
                hashlib.sha512(data).digest(),
                asymmetric_padding.PSS(
                    mgf=asymmetric_padding.MGF1(hashes.SHA512()),
                    salt_length=asymmetric_padding.PSS.MAX_LENGTH
                ),
                hashes.SHA512()
            )

            users_keys = {username: user_encrypted_key.hex(), self.credentials["username"]: my_encrypted_key.hex()}

            payload = {
                "status": "OK",
                "data": encrypted_data.hex(),
                "signature": signature.hex(),
                "keys": users_keys
            }
            return payload
        else:
            return {"status": "error", "error": response["error"]}
示例#10
0
    def __init__(self, parent=None):
        super().__init__(parent=parent)
        self.parent = parent
        self.resize(800, 576)
        self.setStyleSheet(f"QLabel {{ color: {config['text_color']} }}")
        self.centralwidget = QtWidgets.QWidget(self)
        self.gridLayout = QtWidgets.QGridLayout(self.centralwidget)
        self.setWindowTitle("Rocket Sender")

        self.current_chat = None

        self.messages_list = QtWidgets.QListWidget(self.centralwidget)
        self.messages_list.setStyleSheet(
            "QListWidget {border: 1px solid lightgrey}")

        self.chats_list = QtWidgets.QListWidget(self.centralwidget)
        self.chats_list.setStyleSheet(
            "QListWidget::item { border-bottom: 1px solid lightgray; } QListWidget {border: 1px solid lightgrey}"
        )
        self.chats_list.itemClicked.connect(self.chat_selected)
        self.chats_list.setMinimumWidth(270)

        self.contacts_list = QtWidgets.QListWidget(self.centralwidget)
        self.contacts_list.setStyleSheet(
            "QListWidget::item { border-bottom: 1px solid lightgray; }; QListWidget {border: 1px solid lightgrey}"
        )
        self.contacts_list.itemClicked.connect(self.contact_selected)
        self.contacts_list.setMinimumWidth(270)

        self.on_list_label = QtWidgets.QLabel("You have no chats")
        self.on_list_label.setStyleSheet("color: gray")
        self.on_list_label.setAlignment(QtCore.Qt.AlignCenter)
        self.on_list_label.setMinimumWidth(270)

        self.on_messages_list_label = QtWidgets.QLabel("You have no messages")
        self.on_messages_list_label.setStyleSheet("color: gray")
        self.on_messages_list_label.setAlignment(QtCore.Qt.AlignCenter)
        self.on_messages_list_label.setText("Select a chat")

        self.obtain_chats = QtCore.QTimer(self)
        self.obtain_chats.timeout.connect(self.timeout)
        self.obtain_chats.start(5000)

        self.loading_label = QtWidgets.QLabel(self.centralwidget)
        self.loading_label.resize(15, 15)
        self.loading_label.setAlignment(QtCore.Qt.AlignCenter)
        self.loading_movie = QtGui.QMovie("img/spinner.gif")
        self.loading_movie.setScaledSize(QtCore.QSize(30, 30))
        self.loading_movie.setCacheMode(QtGui.QMovie.CacheAll)
        self.loading_movie.setSpeed(100)
        self.loading_label.setMovie(self.loading_movie)

        self.create_button = QtWidgets.QPushButton(self.centralwidget)
        self.create_button.setText("Create")
        self.create_button.clicked.connect(self.create_button_clicked)

        self.pin_file_button = QtWidgets.QPushButton(self.centralwidget)
        self.pin_file_button.setText("+")
        self.pin_file_button.clicked.connect(self.send_file)

        self.message_text_edit = GrowingTextEdit()
        self.message_text_edit.setPlaceholderText("Message")
        self.message_text_edit.setMinimumHeight(28)
        self.message_text_edit.signal.connect(
            self.message_text_edit_key_press_event)

        self.send_message_button = QtWidgets.QPushButton(self.centralwidget)
        self.send_message_button.clicked.connect(self.start_sending_message)
        self.send_message_button.setText("Send")

        self.current_chat_label = QtWidgets.QLabel()
        self.current_chat_label.setAlignment(QtCore.Qt.AlignLeft)
        self.current_chat_label.setStyleSheet(
            "font-weight: bold; font-size:15px;")

        self.settings_widget = SettingsWidget()

        self.buttons_bar = BottomButtonsBar(self)

        self.get_chats_thread = RocketAPIThread()
        self.get_chats_thread.function = api.get_user_chats
        self.get_chats_thread.signal.connect(self.complete_getting_chats)
        self.loading_movie.start()
        self.get_chats_thread.start()

        self.get_messages_thread = RocketAPIThread()
        self.get_messages_thread.function = api.get_all_messages
        self.get_messages_thread.signal.connect(self.complete_getting_messages)

        self.cache_messages_thread = RocketAPIThread()
        self.cache_messages_thread.function = self.cache_messages

        self.cache_chats_thread = RocketAPIThread()
        self.cache_chats_thread.function = self.cache_chats

        self.send_message_thread = RocketAPIThread()
        self.send_message_thread.function = api.send_message
        self.send_message_thread.signal.connect(self.complete_sending_message)

        self.update_statuses_thread = RocketAPIThread()
        self.update_statuses_thread.function = self.update_statuses

        self.upload_file_thread = RocketAPIThread()
        self.upload_file_thread.function = api.upload_file
        self.upload_file_thread.signal.connect(self.complete_file_upload)

        self.chats = session.query(Chat).order_by(Chat.unix_time.desc()).all()
        self.messages = list()
        self.message_cache = defaultdict()
        for message in session.query(Message).order_by(
                Message.unix_time).all():
            if message.chat_id in self.message_cache:
                self.message_cache[message.chat_id].append(message)
            else:
                self.message_cache[message.chat_id] = [message]

        self.gridLayout.addWidget(self.loading_label,
                                  0,
                                  0,
                                  1,
                                  1,
                                  alignment=QtCore.Qt.AlignLeft)
        self.gridLayout.addWidget(self.create_button, 0, 1, 1, 1)
        self.gridLayout.addWidget(self.chats_list,
                                  1,
                                  0,
                                  1,
                                  2,
                                  alignment=QtCore.Qt.AlignLeft)
        self.gridLayout.addWidget(self.contacts_list,
                                  1,
                                  0,
                                  1,
                                  2,
                                  alignment=QtCore.Qt.AlignLeft)
        self.gridLayout.addWidget(self.buttons_bar, 2, 0, 1, 2)
        self.gridLayout.addWidget(self.messages_list, 1, 2, 1, 3)
        self.gridLayout.addWidget(self.pin_file_button, 2, 2, 1, 1)
        self.gridLayout.addWidget(self.message_text_edit,
                                  2,
                                  3,
                                  1,
                                  1,
                                  alignment=QtCore.Qt.AlignBottom)
        self.gridLayout.addWidget(self.send_message_button, 2, 4, 1, 1)
        self.gridLayout.addWidget(self.on_list_label, 1, 0, 1, 2)
        self.gridLayout.addWidget(self.on_messages_list_label, 1, 2, 1, 3)
        self.gridLayout.addWidget(self.settings_widget, 1, 0, 1, 2)
        self.gridLayout.addWidget(self.current_chat_label, 0, 2, 1, 3)

        self.gridLayout.setRowStretch(1, 2)
        self.gridLayout.setRowStretch(2, 1)
        self.gridLayout.setSpacing(5)

        if self.chats:
            self.on_list_label.hide()
        self.contacts_list.hide()
        self.settings_widget.hide()
        self.start_getting_chats()

        self.setCentralWidget(self.centralwidget)