Qt封装网络类发起多次GET/POST请求无响应问题求助
问题原因
- 重复使用同一个
QFile对象未重置读取位置:第一次调用searchCSV时文件内容被完全读取,文件指针指向EOF,第二次调用时POST请求体为空,请求不合法无法触发后续响应流程。 - 错误设置外部
QFile的父对象:代码中将外部传入的file的父对象设为当前请求的QHttpMultiPart,当第一次请求结束后QHttpMultiPart被自动回收,会连带销毁外部file对象,第二次调用时操作的是已销毁的野指针,直接导致请求异常。
解决方案
仅需要修改searchCSV方法即可,不需要改动类的其他结构,修改后支持单个实例任意次数调用任意方法:
- 每次读取文件前先重置文件指针到开头
- 删除给外部
file设置父对象的逻辑,由调用方自行管理外部文件生命周期 - 给
QHttpMultiPart绑定父对象到请求返回的QNetworkReply,自动管理动态分配的内存避免泄漏
修改后的核心代码
void searchCSV(QFile& file, QFile& outfile){ // 重置文件读取指针到开头,保证每次都能读取完整内容 if(!file.seek(0)){ qDebug() << "文件指针重置失败:" << file.errorString(); return; } QNetworkRequest request(QUrl("https://api-adresse.data.gouv.fr/search/csv/")); request.setAttribute(QNetworkRequest::User, outfile.fileName()); QHttpMultiPart *multipart = new QHttpMultiPart(QHttpMultiPart::FormDataType); QHttpPart postpart; postpart.setHeader(QNetworkRequest::ContentDispositionHeader, QString("form-data; name=%1; filename=%2") .arg("data", file.fileName())); postpart.setBodyDevice(&file); multipart->append(postpart); // 移除给外部file设置父对象的逻辑,避免外部文件被意外回收 // file.setParent(multipart); // 绑定multipart的生命周期到reply,请求结束后自动回收 QNetworkReply *reply = manager.post(request, multipart); multipart->setParent(reply); }
可选优化:如果需要每次写入输出文件时覆盖旧内容,可修改handle_finished中的文件打开参数:
if(out.open(QIODevice::WriteOnly | QIODevice::Truncate)){
内容的提问来源于stack exchange,提问作者Angela Riley
相关产品推荐
相关产品推荐

