File indexing completed on 2024-12-15 03:45:02

0001 /*
0002     SPDX-FileCopyrightText: 2016 Volker Krause <vkrause@kde.org>
0003 
0004     SPDX-License-Identifier: MIT
0005 */
0006 
0007 #include <kuserfeedback_version.h>
0008 #include "restclient.h"
0009 
0010 #include <QDebug>
0011 #include <QNetworkAccessManager>
0012 #include <QNetworkReply>
0013 #include <QNetworkRequest>
0014 
0015 using namespace KUserFeedback::Console;
0016 
0017 RESTClient::RESTClient(QObject *parent) :
0018     QObject(parent),
0019     m_networkAccessManager(new QNetworkAccessManager(this))
0020 {
0021 }
0022 
0023 RESTClient::~RESTClient() = default;
0024 
0025 ServerInfo RESTClient::serverInfo() const
0026 {
0027     return m_serverInfo;
0028 }
0029 
0030 void RESTClient::setServerInfo(const ServerInfo& info)
0031 {
0032     m_isConnected = false;
0033     m_serverInfo = info;
0034 }
0035 
0036 void RESTClient::setConnected(bool connected)
0037 {
0038     if (m_isConnected == connected)
0039         return;
0040     m_isConnected = connected;
0041     if (isConnected())
0042         Q_EMIT clientConnected();
0043 }
0044 
0045 bool RESTClient::isConnected() const
0046 {
0047     return m_serverInfo.url().isValid() && m_isConnected;
0048 }
0049 
0050 QNetworkReply* RESTClient::get(const QString& command)
0051 {
0052     const auto request = makeRequest(command);
0053     auto reply = m_networkAccessManager->get(request);
0054     setupMessageHandler(reply);
0055     return reply;
0056 }
0057 
0058 QNetworkReply* RESTClient::post(const QString& command, const QByteArray& data)
0059 {
0060     auto request = makeRequest(command);
0061     request.setHeader(QNetworkRequest::ContentTypeHeader, QStringLiteral("application/json"));
0062     auto reply = m_networkAccessManager->post(request, data);
0063     setupMessageHandler(reply);
0064     return reply;
0065 }
0066 
0067 QNetworkReply* RESTClient::put(const QString &command, const QByteArray &data)
0068 {
0069     const auto request = makeRequest(command);
0070     auto reply = m_networkAccessManager->put(request, data);
0071     setupMessageHandler(reply);
0072     return reply;
0073 }
0074 
0075 QNetworkReply* RESTClient::deleteResource(const QString& command)
0076 {
0077     const auto request = makeRequest(command);
0078     auto reply = m_networkAccessManager->deleteResource(request);
0079     setupMessageHandler(reply);
0080     return reply;
0081 }
0082 
0083 QNetworkAccessManager* RESTClient::networkAccessManager() const
0084 {
0085     return m_networkAccessManager;
0086 }
0087 
0088 QNetworkRequest RESTClient::makeRequest(const QString& command)
0089 {
0090     Q_ASSERT(m_serverInfo.url().isValid());
0091     auto url = m_serverInfo.url();
0092     auto path = url.path();
0093     if (!path.endsWith(QLatin1Char('/')))
0094         path += QLatin1Char('/');
0095     path += command;
0096     url.setPath(path);
0097     QNetworkRequest request(url);
0098     const QByteArray authToken = m_serverInfo.userName().toUtf8() + ':' + m_serverInfo.password().toUtf8();
0099     request.setRawHeader("Authorization", QByteArray("Basic " + authToken.toBase64()));
0100     request.setHeader(QNetworkRequest::UserAgentHeader, QString(QStringLiteral("UserFeedbackConsole/") + QStringLiteral(KUSERFEEDBACK_VERSION_STRING)));
0101 #if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
0102     request.setAttribute(QNetworkRequest::FollowRedirectsAttribute, true);
0103 #endif
0104     return request;
0105 }
0106 
0107 void RESTClient::setupMessageHandler(QNetworkReply* reply)
0108 {
0109     connect(reply, &QNetworkReply::finished, this, [this, reply]() {
0110         if (reply->error() == QNetworkReply::NoError)
0111             return;
0112         Q_EMIT errorMessage(reply->errorString());
0113         const auto d = reply->readAll();
0114         if (!d.isEmpty())
0115             Q_EMIT errorMessage(QString::fromUtf8(d));
0116     });
0117 }
0118 
0119 #include "moc_restclient.cpp"