如何在Qt中使用JSON正文发送POST请求

时间:2020-02-07 05:29:36

标签: json qt post content-type qnetworkaccessmanager

我正在尝试从Qt发送POST请求,其中正文为JSON格式。首先,我断言该请求可以在curl中工作:

curl -i -H "Content-Type: application/json" -d '{"key1": "value1", "key2": "value2"}' -X POST http://myserver.com/api

那工作正常,我正在从服务器收到预期的响应。在Python中也是如此。现在,我需要从C ++ / Qt发送此请求:

QNetworkAccessManager *mgr = new QNetworkAccessManager(this);
QHttpMultiPart *httpMultiPart = new QHttpMultiPart(mgr);
QHttpPart *httpPart = new QHttpPart();
httpPart->setHeader(QNetworkRequest::ContentTypeHeader, QVariant("application/json"));
httpPart->setBody("{\"key1\":\"value1\", \"key2\":\"value2\"}");

httpMultiPart->append(*httpPart);

QNetworkReply *reply = mgr->post(QNetworkRequest(QUrl("http://myserver.com/api")), httpMultiPart);
QObject::connect(reply, &QNetworkReply::finished, [=]()
        {
            QString err = reply->errorString();
            QString contents = QString::fromUtf8(reply->readAll());
        });

现在我收到一个错误,其中errorString返回:`

"Error downloading http://myserver.com/api - server replied: Unsupported Media Type"`

可能是什么原因?我应该如何发送POST请求,就像我用curl发送的那样?

2 个答案:

答案 0 :(得分:1)

QHttpMultiPart用于发送MIME分段消息,但是在这种情况下,不需要发送该类型的信息。相反,您应该使用QJsonDocument创建json并将其转换为QByteArray:

QNetworkAccessManager *mgr = new QNetworkAccessManager(this);
const QUrl url(QStringLiteral("http://myserver.com/api"));
QNetworkRequest request(url);
request.setHeader(QNetworkRequest::ContentTypeHeader, "application/json");

QJsonObject obj;
obj["key1"] = "value1";
obj["key2"] = "value2";
QJsonDocument doc(obj);
QByteArray data = doc.toJson();
// or
// QByteArray data("{\"key1\":\"value1\",\"key2\":\"value2\"}");
QNetworkReply *reply = mgr->post(request, data);

QObject::connect(reply, &QNetworkReply::finished, [=](){
    if(reply->error() == QNetworkReply::NoError){
        QString contents = QString::fromUtf8(reply->readAll());
        qDebug() << contents;
    }
    else{
        QString err = reply->errorString();
        qDebug() << err;
    }
    reply->deleteLater();
});

答案 1 :(得分:0)

QNetworkAccessManager *mgr = new QNetworkAccessManager(this);

QUrl url = QUrl("http://myserver.com/api");

QJsonObject param;
param.insert("key1", QJsonValue::fromVariant("value1"));
param.insert("key2", QJsonValue::fromVariant("value2"));

QNetworkRequest request(url);

request.setHeader(QNetworkRequest::ContentTypeHeader, "application/x-www-form-urlencoded");

QNetworkReply* reply = mgr->post(request, QJsonDocument(param).toJson(QJsonDocument::Compact));

/*Реализуем ожидание конца загрузки с таймаутом*/
QTimer timer;
timer.setSingleShot(true);

QEventLoop loop;
connect(&timer, SIGNAL(timeout()), &loop, SLOT(quit()));
connect(reply, SIGNAL(finished()), &loop, SLOT(quit()));
timer.start(10000);   // 10 secs. timeout
loop.exec();

if(timer.isActive())
{
    timer.stop();
    if(reply->error() == QNetworkReply::NoError)
    {
        // Success
        QByteArray buffer = reply->readAll();

        qDebug()<<buffer;
    }
    else
    {
        // handle error
        QString error = reply->errorString();
        qDebug()<< "reply->errorString() " << error;
    }
}
else
{
    disconnect(reply, SIGNAL(finished()), &loop, SLOT(quit()));
    reply->abort();
}

reply->deleteLater();
相关问题