QUrl and QNetworkReply errors - qt

Using Qt 5.4 32-bit on Windows 8.1 (64-bit) with MingW.
I am experiencing a weird problem. Consider this:
//QString m_sUrl = "cloud.mysystem.info/";
//QString m_sFileName = "results.html";
//QNetworkAccessManager m_Manager;
QUrl url(m_sURL + m_sFileName);
url.setScheme("ftp");
url.setUserName(m_sLogin);
url.setPassword(m_sPassword);
QFile *file = new QFile(m_sFileName);
if(file->open(QIODevice::ReadOnly))
{
QNetworkReply *reply = m_Manager.put(QNetworkRequest(url), file);
connect(reply, static_cast<void (QNetworkReply::*)(QNetworkReply::NetworkError)>(&QNetworkReply::error), this, &OCMResults::error);
connect(reply, &QNetworkReply::finished, reply, &QObject::deleteLater);
connect(reply, &QNetworkReply::finished, file, &QObject::deleteLater);
}
else
file->deleteLater();
At first my code worked fine but then it stopped working (possibly due to my change, not sure what was it) and only workaround is when I write the url explicitely:
QNetworkReply(QUrl("ftp://" + m_sLogin + ":" + m_sPassword + "#" + m_sURL + m_sFileName)), file);
The resulting URL is exactly the same but for some reason when I create it beforehand and pass it to the QNetworkReply it does not take it:
reply.url().host()
yields nothing if that is the case for example. I feel like I am missing something really obvious here...
The errors are either:
3 (host not found) when ftp is specified in the url string
301 (unknown protocol) when I do not specify it in the url but specify it as setScheme("ftp") instead
Thanks!

Related

QNetworkAccessManager sends GET two times

I've got some class to interfere with HTTP-server.
Here is meaningfull code parts:
const QString someClass::BASEURL = QString("http://127.0.0.1:8000/?");
someClass::someClass():
manager(new QNetworkAccessManager(this))
{
}
QNetworkReply *someClass::run(QString request)
{
qDebug() << request;
QEventLoop loop;
QObject::connect(manager, SIGNAL(finished(QNetworkReply*)), &loop, SLOT(quit()));
QNetworkReply *res = manager->get(QNetworkRequest(QUrl(BASEURL + request)));
loop.exec();
return res;
}
When I call method run(), sometimes (not every time) the are two identical GET-requests
(I looked with tcpdump). qDebug() executes 1 time.
Is there some error in my code? I can't see any possible explanation.
UPDATE:
After some tcpdump ouptut research.
After second request it sends packet with RST flag as an answer to FIN.
But I still can see no difference in TCP-streams that triggers the problem and that doesn't.
F.e. here is wireshark's output. Stream 8 went well. Stream 11 was duplicated with Stream 12.
I'm stuck with this. Maybe it's some protocol errors from server-size, I'm not sure. Or maybe it's a bug in QNetworkAccessManager.
Have you tried rewriting you code to be more asynchronous without using QEventLoop in a local scope? Your code looks good to me, but there might be some weird QT bug that you running into in the way it queues up requests for processing and using QEventLoop in the local scope. I usually use QNetworkAccessManager in the following manner to send GET and POST requests:
void someClass::run(QString request)
{
qDebug() << request;
QObject::connect(manager, SIGNAL(finished(QNetworkReply*)), this, SLOT(on_request_complete(QNetworkReply*)));
QNetworkReply *res = manager->get(QNetworkRequest(QUrl(BASEURL + request)));
}
void someClass::on_request_complete(QNetworkReply* response)
{
// Do stuff with your response here
}

upload .txt file to server using HttpRequest in Qt

I hava a problem of uploading .txt file to my java servlet server using Qt.
I spent 5 days on that and tried a lot of solutions. But none of them worked. Does anyone can help me?
The problem is that the Qt code can work without error. But the server didn't receive anything by the httprequest from Qt.
This is one solution in Qt:
QFile file("dataToSend.txt");
nam = new QNetworkAccessManager(this);
QObject::connect(nam, SIGNAL(finished(QNetworkReply*)),
this, SLOT(finishedSlot(QNetworkReply*)));
QNetworkRequest r(QUrl("http://localhost:9999/server"));
QString bound="---------------------------723690991551375881941828858";
QByteArray data(QString("--"+bound+"\r\n").toAscii());
data += QString("--" + bound + "\r\n").toAscii();
data += "Content-Disposition: form-data; name=\"file\"; filename=\""+file.fileName()+"\"\r\n";
data += "Content-Type: text/plain\r\n\r\n";
file.open(QIODevice::ReadOnly);
data += file.readAll();
data += "\r\n";
data += QString("--" + bound + "\r\n").toAscii();
r.setRawHeader(QString("Content-Type").toAscii(),QString("multipart/form-data; boundary=" + bound).toAscii());
r.setRawHeader(QString("Content-Length").toAscii(), QString::number(data.length()).toAscii());
reply = nam->post(r,data);
reply=nam->get(r);
This is another solution, it is not wokring neither:
nam = new QNetworkAccessManager(this);
QObject::connect(nam, SIGNAL(finished(QNetworkReply*)),
this, SLOT(finishedSlot(QNetworkReply*)));
QFile *file=new QFile("dataToSend.txt");
QNetworkRequest request(QUrl("http://localhost:9999/server"));
request.setHeader(QNetworkRequest::ContentTypeHeader, "application/octet-streamd");
if(!file->open(QIODevice::ReadOnly)){
qDebug("%s\n",qPrintable("can't open the file!"));
return;
}
// post data to server
reply= nam->post(request,file);
file->setParent(reply);
reply=nam->get(request);
you cannot post() something to a server and a line below do a get() expecting to see the file.
Usually you have to post, wait until post is finished, and than you can see modification..
here there are lots of link you can use to do things right

Trying to upload more than 600mb file to server using Qt app

I am trying to develop file uploader using Qt. Here is my code :
QNetworkAccessManager * manager = new QNetworkAccessManager(this);
QNetworkRequest request(url);
QByteArray line;
QFile file(//path);
while(!file.atEnd())
{
line.append(file.readLine());
}
file.close();
QObject::connect(manager,SIGNAL(finished(QNetworkReply *)), this, SLOT(error_On_File_Send(QNetworkReply *)));
manager->post(request, line);
it works ok for small files. But it is not working in large file and gives std:bad_alloc error. What should i do
Use QNetworkAccessManager::post ( const QNetworkRequest & request, QIODevice * data ). It will automaticly read data when it is needed from any QIODevice. QFile is QIODevice so you should only slightly change your code. Note that you have to manage attached QIODevice by yourself (delete it after finished() signal)

Whats the problem with my code (http post)

i am developing a simple application which uploads image to yfrog.com.(These images will be reflected in twitter account). Here is my code. but it is not working. I am not getting response from server.
QNetworkAccessManager *manager = new QNetworkAccessManager(this);
QNetworkRequest request(QUrl("http://yfrog.com/api/uploadAndPost"));
QByteArray data;
QUrl params,params1;
QFile file("some image path");
QString boundary("-----abcde12345");
QString body = "\r\n--" + boundary + "\r\n";
params.addQueryItem("username",twitterusername);
params.addQueryItem("password",twitterpassword);
params.addQueryItem("message",some message...);
params.addQueryItem("key",mydeveloperkey);
data.append(body);
data.append(params.toString());
QByteArray ba;
ba=file.readAll();
QString body1(ba);
params1.addQueryItem("media",body1);
data.append(params1.toString());
data.append(body);
request.setRawHeader("Content-Type","multipart/form-data; boundary=-----abcde12345");
request.setHeader(QNetworkRequest::ContentLengthHe ader,data.size());
QNetworkReply *reply = manager->post(request,data);
reply->waitForReadyRead(-1);
qDebug() << "replay :"<<reply->readAll();
If i checked the requested TCP packets from wireshark, it is giving a error message like 'malformed packets'.
For reference : http://code.google.com/p/imageshacka...GuploadAndPost
Please any body help regarding this. Where i am doing wrong?
QNetworkReply::waitForReadyRead does not have an implementation so it always refers the base class waitForReadyRead() (in this case QIODevice). In the base class, you will see that waitForReadyRead always returns FALSE.
From the docs, you would have to instead use the readRead() signal in QNetworkReply and read the data when the slot is called.
QNetworkReply *reply = manager->get(request);
connect(reply, SIGNAL(readyRead()), this, SLOT(slotReadyRead()));

downloadProgress not emitted from QNetworkReply

I'm trying to build a module which downloads a binary file in Qt, using QNetworkAccessManager. I use the same approach detailed in the documentation (see below), but while I do get readyRead signals, downloadProgress never arrives.
Everything happens on the same thread (the project is big so I cannot paste it all).
Any ideas?
QNetworkRequest request;
request.setUrl("http://XXX.s3.amazonaws.com/XXX.exe");
request.setRawHeader("User-Agent", "MyOwnBrowser 1.0");
QNetworkAccessManager * m_manager = new QNetworkAccessManager( this );
m_reply = m_manager->get(request);
m_reply->setParent(this);
connect(m_reply, SIGNAL(readyRead()), this, SLOT(slotReadyRead()));
connect(m_reply, SIGNAL(downloadProgress(qint64 bytesReceived, qint64 bytesTotal)),
this, SLOT(replyDownloadProgress(qint64 bytesReceived, qint64 bytesTotal)));
ok found it
wow what a simple mistake.
the answer is syntactic:
connect(m_reply, SIGNAL(downloadProgress(qint64 bytesReceived, qint64 bytesTotal)),
this, SLOT(replyDownloadProgress(qint64 bytesReceived, qint64 bytesTotal)));
is an error
it should be:
connect(m_reply, SIGNAL(downloadProgress(qint64 , qint64 )),
this, SLOT(replyDownloadProgress(qint64 , qint64 ));
once i changed it, i got the signal.
QT DOES NOT CHECK SYNTAX ERRORS IN ITS PREPROCESSOR (note to self)
I've patched my Qt to use a qFatal() instead of qWarning(), so the app asserts instead of printing error messages (that cannot be seen when linking against a release-build Qt). YMMV.

Resources