diff options
Diffstat (limited to 'src/ui/KeyServerImportDialog.cpp')
-rw-r--r-- | src/ui/KeyServerImportDialog.cpp | 607 |
1 files changed, 0 insertions, 607 deletions
diff --git a/src/ui/KeyServerImportDialog.cpp b/src/ui/KeyServerImportDialog.cpp deleted file mode 100644 index 0cc3d195..00000000 --- a/src/ui/KeyServerImportDialog.cpp +++ /dev/null @@ -1,607 +0,0 @@ -/** - * Copyright (C) 2021 Saturneric - * - * This file is part of GpgFrontend. - * - * GpgFrontend is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GpgFrontend is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GpgFrontend. If not, see <https://www.gnu.org/licenses/>. - * - * The initial version of the source code is inherited from - * the gpg4usb project, which is under GPL-3.0-or-later. - * - * All the source code of GpgFrontend was modified and released by - * Saturneric<[email protected]> starting on May 12, 2021. - * - * SPDX-License-Identifier: GPL-3.0-or-later - * - */ - -#include "ui/KeyServerImportDialog.h" - -#include <utility> - -#include "gpg/function/GpgKeyImportExporter.h" -#include "ui/SignalStation.h" -#include "ui/settings/GlobalSettingStation.h" - -namespace GpgFrontend::UI { - -KeyServerImportDialog::KeyServerImportDialog(bool automatic, QWidget* parent) - : QDialog(parent), m_automatic_(automatic) { - // Layout for messagebox - auto* messageLayout = new QHBoxLayout; - - if (automatic) { - setWindowFlags(Qt::Window | Qt::WindowTitleHint | Qt::CustomizeWindowHint); - } else { - // Buttons - close_button_ = create_button(_("Close"), SLOT(close())); - import_button_ = create_button(_("Import ALL"), SLOT(slot_import())); - import_button_->setDisabled(true); - search_button_ = create_button(_("Search"), SLOT(slot_search())); - - // Line edit for search string - search_label_ = new QLabel(QString(_("Search String")) + _(": ")); - search_line_edit_ = new QLineEdit(); - - // combobox for keyserverlist - key_server_label_ = new QLabel(QString(_("Key Server")) + _(": ")); - key_server_combo_box_ = create_comboBox(); - - // table containing the keys found - create_keys_table(); - message_ = new QLabel; - message_->setFixedHeight(24); - icon_ = new QLabel; - icon_->setFixedHeight(24); - - messageLayout->addWidget(icon_); - messageLayout->addWidget(message_); - messageLayout->addStretch(); - } - - // Network Waiting - waiting_bar_ = new QProgressBar(); - waiting_bar_->setVisible(false); - waiting_bar_->setRange(0, 0); - waiting_bar_->setFixedWidth(200); - messageLayout->addWidget(waiting_bar_); - - auto* mainLayout = new QGridLayout; - - // 自动化调用界面布局 - if (automatic) { - mainLayout->addLayout(messageLayout, 0, 0, 1, 3); - } else { - mainLayout->addWidget(search_label_, 1, 0); - mainLayout->addWidget(search_line_edit_, 1, 1); - mainLayout->addWidget(search_button_, 1, 2); - mainLayout->addWidget(key_server_label_, 2, 0); - mainLayout->addWidget(key_server_combo_box_, 2, 1); - mainLayout->addWidget(keys_table_, 3, 0, 1, 3); - mainLayout->addLayout(messageLayout, 4, 0, 1, 3); - - // Layout for import and close button - auto* buttonsLayout = new QHBoxLayout; - buttonsLayout->addStretch(); - buttonsLayout->addWidget(import_button_); - buttonsLayout->addWidget(close_button_); - mainLayout->addLayout(buttonsLayout, 6, 0, 1, 3); - } - - this->setLayout(mainLayout); - if (automatic) - this->setWindowTitle(_("Update Keys from Keyserver")); - else - this->setWindowTitle(_("Import Keys from Keyserver")); - - if (automatic) { - this->setFixedSize(240, 42); - } else { - auto pos = QPoint(150, 150); - LOG(INFO) << "parent" << parent; - if (parent) pos += parent->pos(); - LOG(INFO) << "pos default" << pos.x() << pos.y(); - auto size = QSize(800, 500); - - try { - auto& settings = GlobalSettingStation::GetInstance().GetUISettings(); - - int x, y, width, height; - x = settings.lookup("window.import_from_keyserver.position.x"); - y = settings.lookup("window.import_from_keyserver.position.y"); - width = settings.lookup("window.import_from_keyserver.size.width"); - height = settings.lookup("window.import_from_keyserver.size.height"); - pos = QPoint(x, y); - size = QSize(width, height); - - } catch (...) { - LOG(WARNING) << "cannot read pos or size from settings"; - } - - this->resize(size); - this->move(pos); - } - - this->setModal(true); - - connect(this, SIGNAL(SignalKeyImported()), SignalStation::GetInstance(), - SIGNAL(KeyDatabaseRefresh())); - - // save window pos and size to configure file - connect(this, SIGNAL(finished(int)), this, SLOT(slot_save_window_state())); -} - -QPushButton* KeyServerImportDialog::create_button(const QString& text, - const char* member) { - auto* button = new QPushButton(text); - connect(button, SIGNAL(clicked()), this, member); - return button; -} - -QComboBox* KeyServerImportDialog::create_comboBox() { - auto* comboBox = new QComboBox; - comboBox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); - - auto& settings = GlobalSettingStation::GetInstance().GetUISettings(); - - try { - auto& server_list = settings.lookup("keyserver.server_list"); - const auto server_list_size = server_list.getLength(); - for (int i = 0; i < server_list_size; i++) { - std::string server_url = server_list[i]; - comboBox->addItem(server_url.c_str()); - } - } catch (...) { - LOG(ERROR) << _("Setting Operation Error") << _("server_list"); - } - - // set default keyserver in combobox - try { - std::string default_server = settings.lookup("keyserver.default_server"); - comboBox->setCurrentText(default_server.c_str()); - } catch (...) { - LOG(ERROR) << _("Setting Operation Error") << _("default_server"); - } - - return comboBox; -} - -void KeyServerImportDialog::create_keys_table() { - keys_table_ = new QTableWidget(); - keys_table_->setColumnCount(4); - - // always a whole row is marked - keys_table_->setSelectionBehavior(QAbstractItemView::SelectRows); - keys_table_->setEditTriggers(QAbstractItemView::NoEditTriggers); - - // Make just one row selectable - keys_table_->setSelectionMode(QAbstractItemView::SingleSelection); - - QStringList labels; - labels << _("UID") << _("Creation date") << _("KeyID") << _("Tag"); - keys_table_->horizontalHeader()->setSectionResizeMode( - 0, QHeaderView::ResizeToContents); - keys_table_->setHorizontalHeaderLabels(labels); - keys_table_->verticalHeader()->hide(); - - connect(keys_table_, SIGNAL(cellActivated(int, int)), this, - SLOT(slot_import())); -} - -void KeyServerImportDialog::set_message(const QString& text, bool error) { - if (m_automatic_) return; - - message_->setText(text); - if (error) { - icon_->setPixmap( - QPixmap(":error.png").scaled(QSize(24, 24), Qt::KeepAspectRatio)); - } else { - icon_->setPixmap( - QPixmap(":info.png").scaled(QSize(24, 24), Qt::KeepAspectRatio)); - } -} - -void KeyServerImportDialog::slot_search() { - if (search_line_edit_->text().isEmpty()) { - set_message("<h4>" + QString(_("Text is empty.")) + "</h4>", false); - return; - } - - QUrl url_from_remote = key_server_combo_box_->currentText() + - "/pks/lookup?search=" + search_line_edit_->text() + - "&op=index&options=mr"; - network_access_manager_ = new QNetworkAccessManager(this); - QNetworkReply* reply = - network_access_manager_->get(QNetworkRequest(url_from_remote)); - - connect(reply, SIGNAL(finished()), this, SLOT(slot_search_finished())); - - set_loading(true); - this->search_button_->setDisabled(true); - this->key_server_combo_box_->setDisabled(true); - this->search_line_edit_->setReadOnly(true); - this->import_button_->setDisabled(true); - - while (reply->isRunning()) { - QApplication::processEvents(); - } - - this->search_button_->setDisabled(false); - this->key_server_combo_box_->setDisabled(false); - this->search_line_edit_->setReadOnly(false); - this->import_button_->setDisabled(false); - set_loading(false); -} - -void KeyServerImportDialog::slot_search_finished() { - LOG(INFO) << "KeyServerImportDialog::slot_search_finished Called"; - - auto* reply = qobject_cast<QNetworkReply*>(sender()); - - keys_table_->clearContents(); - keys_table_->setRowCount(0); - QString first_line = QString(reply->readLine(1024)); - - auto error = reply->error(); - if (error != QNetworkReply::NoError) { - qDebug() << "Error From Reply" << reply->errorString(); - switch (error) { - case QNetworkReply::ContentNotFoundError: - set_message(_("Not Key Found"), true); - break; - case QNetworkReply::TimeoutError: - set_message(_("Timeout"), true); - break; - case QNetworkReply::HostNotFoundError: - set_message(_("Key Server Not Found"), true); - break; - default: - set_message(_("Connection Error"), true); - } - return; - } - - if (first_line.contains("Error")) { - QString text = QString(reply->readLine(1024)); - if (text.contains("Too many responses")) { - set_message( - "<h4>" + QString(_("Too many responses from keyserver!")) + "</h4>", - true); - return; - } else if (text.contains("No keys found")) { - // if string looks like hex string, search again with 0x prepended - QRegExp rx("[0-9A-Fa-f]*"); - QString query = search_line_edit_->text(); - if (rx.exactMatch(query)) { - set_message( - "<h4>" + - QString(_("No keys found, input may be kexId, retrying search " - "with 0x.")) + - "</h4>", - true); - search_line_edit_->setText(query.prepend("0x")); - this->slot_search(); - return; - } else { - set_message( - "<h4>" + QString(_("No keys found containing the search string!")) + - "</h4>", - true); - return; - } - } else if (text.contains("Insufficiently specific words")) { - set_message("<h4>" + - QString(_("Insufficiently specific search string!")) + - "</h4>", - true); - return; - } else { - set_message(text, true); - return; - } - } else { - int row = 0; - bool strikeout = false; - while (reply->canReadLine()) { - auto line_buff = reply->readLine().trimmed(); - QString decoded = - QString::fromUtf8(line_buff.constData(), line_buff.size()); - QStringList line = decoded.split(":"); - // TODO: have a look at two following pub lines - if (line[0] == "pub") { - strikeout = false; - - QString flags = line[line.size() - 1]; - keys_table_->setRowCount(row + 1); - - // flags can be "d" for disabled, "r" for revoked - // or "e" for expired - if (flags.contains("r") or flags.contains("d") or flags.contains("e")) { - strikeout = true; - if (flags.contains("e")) { - keys_table_->setItem(row, 3, - new QTableWidgetItem(QString("expired"))); - } - if (flags.contains("r")) { - keys_table_->setItem(row, 3, - new QTableWidgetItem(QString(_("revoked")))); - } - if (flags.contains("d")) { - keys_table_->setItem(row, 3, - new QTableWidgetItem(QString(_("disabled")))); - } - } - - QStringList line2 = QString(reply->readLine()).split(":"); - - auto* uid = new QTableWidgetItem(); - if (line2.size() > 1) { - uid->setText(line2[1]); - keys_table_->setItem(row, 0, uid); - } - auto* creation_date = new QTableWidgetItem( - QDateTime::fromTime_t(line[4].toInt()).toString("dd. MMM. yyyy")); - keys_table_->setItem(row, 1, creation_date); - auto* keyid = new QTableWidgetItem(line[1]); - keys_table_->setItem(row, 2, keyid); - if (strikeout) { - QFont strike = uid->font(); - strike.setStrikeOut(true); - uid->setFont(strike); - creation_date->setFont(strike); - keyid->setFont(strike); - } - row++; - } else { - if (line[0] == "uid") { - QStringList l; - int height = keys_table_->rowHeight(row - 1); - keys_table_->setRowHeight(row - 1, height + 16); - QString tmp = keys_table_->item(row - 1, 0)->text(); - tmp.append(QString("\n") + line[1]); - auto* tmp1 = new QTableWidgetItem(tmp); - keys_table_->setItem(row - 1, 0, tmp1); - if (strikeout) { - QFont strike = tmp1->font(); - strike.setStrikeOut(true); - tmp1->setFont(strike); - } - } - } - set_message( - QString("<h4>") + - QString(_("%1 keys found. Double click a key to import it.")) - .arg(row) + - "</h4>", - false); - } - keys_table_->resizeColumnsToContents(); - import_button_->setDisabled(keys_table_->size().isEmpty()); - } - reply->deleteLater(); -} - -void KeyServerImportDialog::slot_import() { - LOG(INFO) << _("Current Row") << keys_table_->currentRow(); - if (keys_table_->currentRow() > -1) { - QString keyid = keys_table_->item(keys_table_->currentRow(), 2)->text(); - SlotImport(QStringList(keyid), key_server_combo_box_->currentText()); - } -} - -void KeyServerImportDialog::SlotImport(const KeyIdArgsListPtr& keys) { - std::string target_keyserver; - if (key_server_combo_box_ != nullptr) { - target_keyserver = key_server_combo_box_->currentText().toStdString(); - } - if (target_keyserver.empty()) { - try { - auto& settings = GlobalSettingStation::GetInstance().GetUISettings(); - - target_keyserver = settings.lookup("keyserver.default_server").c_str(); - - LOG(INFO) << _("Set target Key Server to default Key Server") - << target_keyserver; - } catch (...) { - LOG(ERROR) << _("Cannot read default_keyserver From Settings"); - QMessageBox::critical( - nullptr, _("Default Keyserver Not Found"), - _("Cannot read default keyserver from your settings, " - "please set a default keyserver first")); - return; - } - } - auto key_ids = QStringList(); - for (const auto& key_id : *keys) - key_ids.append(QString::fromStdString(key_id)); - SlotImport(key_ids, QUrl(target_keyserver.c_str())); -} - -void KeyServerImportDialog::SlotImport(const QStringList& keyIds, - const QUrl& keyserverUrl) { - for (const auto& keyId : keyIds) { - QUrl req_url(keyserverUrl.scheme() + "://" + keyserverUrl.host() + - "/pks/lookup?op=get&search=0x" + keyId + "&options=mr"); - - LOG(INFO) << "request url" << req_url.toString().toStdString(); - auto manager = new QNetworkAccessManager(this); - - QNetworkReply* reply = manager->get(QNetworkRequest(req_url)); - connect(reply, &QNetworkReply::finished, this, - [&, keyId]() { this->slot_import_finished(keyId); }); - LOG(INFO) << "loading start"; - set_loading(true); - while (reply->isRunning()) QApplication::processEvents(); - set_loading(false); - LOG(INFO) << "loading done"; - } -} - -void KeyServerImportDialog::slot_import_finished(const QString& keyid) { - LOG(INFO) << _("Called"); - - auto* reply = qobject_cast<QNetworkReply*>(sender()); - - QByteArray key = reply->readAll(); - - auto error = reply->error(); - if (error != QNetworkReply::NoError) { - LOG(ERROR) << "Error From Reply" << reply->errorString().toStdString(); - if (!m_automatic_) { - switch (error) { - case QNetworkReply::ContentNotFoundError: - set_message(_("Key Not Found"), true); - break; - case QNetworkReply::TimeoutError: - set_message(_("Timeout"), true); - break; - case QNetworkReply::HostNotFoundError: - set_message(_("Key Server Not Found"), true); - break; - default: - set_message(_("Connection Error"), true); - } - } else { - switch (error) { - case QNetworkReply::ContentNotFoundError: - QMessageBox::critical( - nullptr, _("Public key Not Found"), - QString(_("Public key fingerprint %1 not found in the Keyserver")) - .arg(keyid)); - break; - case QNetworkReply::TimeoutError: - QMessageBox::critical(nullptr, _("Timeout"), "Connection timeout"); - break; - case QNetworkReply::HostNotFoundError: - QMessageBox::critical(nullptr, _("Host Not Found"), - "cannot resolve the default Keyserver"); - break; - default: - QMessageBox::critical(nullptr, _("Connection Error"), - _("General Connection Error")); - } - } - if (m_automatic_) { - setWindowFlags(Qt::Window | Qt::WindowTitleHint | - Qt::CustomizeWindowHint | Qt::WindowCloseButtonHint); - } - return; - } - - reply->deleteLater(); - - this->import_keys(std::make_unique<ByteArray>(key.constData(), key.length())); - - if (!m_automatic_) { - set_message(QString("<h4>") + _("Key Imported") + "</h4>", false); - } -} - -void KeyServerImportDialog::import_keys(ByteArrayPtr in_data) { - GpgImportInformation result = - GpgKeyImportExporter::GetInstance().ImportKey(std::move(in_data)); - emit SignalKeyImported(); - QWidget* _parent = qobject_cast<QWidget*>(parent()); - if (m_automatic_) { - auto dialog = new KeyImportDetailDialog(result, true, _parent); - dialog->show(); - this->accept(); - } else { - auto dialog = new KeyImportDetailDialog(result, false, _parent); - dialog->exec(); - } -} - -void KeyServerImportDialog::set_loading(bool status) { - waiting_bar_->setVisible(status); - if (!m_automatic_) { - icon_->setVisible(!status); - message_->setVisible(!status); - } -} - -KeyServerImportDialog::KeyServerImportDialog(QWidget* parent) - : QDialog(parent), m_automatic_(true) { - setWindowFlags(Qt::Window | Qt::WindowTitleHint | Qt::CustomizeWindowHint); - - // Network Waiting - waiting_bar_ = new QProgressBar(); - waiting_bar_->setVisible(false); - waiting_bar_->setRange(0, 0); - waiting_bar_->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred); - waiting_bar_->setTextVisible(false); - - // Layout for messagebox - auto* layout = new QHBoxLayout(); - layout->setContentsMargins(0, 0, 0, 0); - layout->setSpacing(0); - layout->addWidget(waiting_bar_); - - key_server_combo_box_ = create_comboBox(); - - this->setLayout(layout); - this->setWindowTitle(_("Update Keys from Keyserver")); - this->setFixedSize(240, 42); - this->setModal(true); -} - -void KeyServerImportDialog::slot_save_window_state() { - LOG(INFO) << _("Called"); - - if (m_automatic_) return; - - auto& settings = - GpgFrontend::UI::GlobalSettingStation::GetInstance().GetUISettings(); - - if (!settings.exists("window") || - settings.lookup("window").getType() != libconfig::Setting::TypeGroup) - settings.add("window", libconfig::Setting::TypeGroup); - - auto& window = settings["window"]; - - if (!window.exists("import_from_keyserver") || - window.lookup("import_from_keyserver").getType() != - libconfig::Setting::TypeGroup) - window.add("import_from_keyserver", libconfig::Setting::TypeGroup); - - auto& import_from_keyserver = window["import_from_keyserver"]; - - if (!import_from_keyserver.exists("position") || - import_from_keyserver.lookup("position").getType() != - libconfig::Setting::TypeGroup) { - auto& position = - import_from_keyserver.add("position", libconfig::Setting::TypeGroup); - position.add("x", libconfig::Setting::TypeInt) = pos().x(); - position.add("y", libconfig::Setting::TypeInt) = pos().y(); - } else { - import_from_keyserver["position"]["x"] = pos().x(); - import_from_keyserver["position"]["y"] = pos().y(); - } - - if (!import_from_keyserver.exists("size") || - import_from_keyserver.lookup("size").getType() != - libconfig::Setting::TypeGroup) { - auto& size = - import_from_keyserver.add("size", libconfig::Setting::TypeGroup); - size.add("width", libconfig::Setting::TypeInt) = QWidget::width(); - size.add("height", libconfig::Setting::TypeInt) = QWidget::height(); - } else { - import_from_keyserver["size"]["width"] = QWidget::width(); - import_from_keyserver["size"]["height"] = QWidget::height(); - } - - GlobalSettingStation::GetInstance().SyncSettings(); -} - -} // namespace GpgFrontend::UI |