с сервера посредством связывания через
connect(reply, &QNetworkReply::finished, this, &UpdateChecker::updatingFiles);
(в `updatingFiles()`ответ обновляется через sender())
QNetworkReply * reply = dynamic_cast<QNetworkReply*>(sender());
Это решение работало, до недавного времени, когда сервер перестал справляться с многопоточной нагрузкой.
Собственно вопрос: как реализовать последовательную загрузку файлов?
Пробовал использовать QRunnable и QThreadPool. Пока не получается.
Вот ссылка на эту попытку:
https://ru.stackoverflow.com/questions/1338319/%d0%9a%d0%b0%d0%ba-%d0%bf%d0%be%d1%81%d0%bb%d0%b5%d0%b4%d0%be%d0%b2%d0%b0%d1%82%d0%b5%d0%bb%d1%8c%d0%bd%d0%be-%d0%b7%d0%b0%d0%b3%d1%80%d1%83%d0%b7%d0%b8%d1%82%d1%8c-%d1%84%d0%b0%d0%b9%d0%bb%d1%8b-%d1%81-%d0%bf%d0%be%d0%bc%d0%be%d1%89%d1%8c%d1%8e-qthreadpool-qrunnable-%d0%b8-qnetworkr
а точно сервер не блокирует по числу запросов? достаточно не отправлять новый запрос пока прошлый файл не докачается
Так использую же finished в качестве сигнала. Должен уже скачаться
QThreadPool для запуска задач в потоках. для скачивания файлов один за другим последовательно это не подходит. должно хватить одного main потока.
Хорошо, но как тогда загружать файлы в одном потоке?
QNAM и так будет делать параллельно несколько задач.. количество "параллельных" скачек у них хардкодно зашито в коде и не меняется
если правильно понял твои требования, то сначала сохранять файл, а после этого отправлять следующий запрос через qnam
вроде было 5 одновременных запросов на один хост:порт
я честно не помню, ну что то типа у них это объясняется там какой то политикой корректности.. ну можно обойти сделав пул из QNAM если очень надо
можно, но это совсем другая задача
блин логично. Сильно затупил. Попробую. Огромное спасибо!
ну если больше 5 одновременно надо
я не спорю, если такие требования то да
4-е. Но Nam - асинхронно работает, потому для нас кажется что параллельных задач много больше
вовсе нет необходимости их строго последовательно выполнять-сохранять. А вообще конечно правильно бы сделать - организовать очередь.. можно и без нее, если есть список файлов для скачки. Он и будет выступать "очередью". Ограничить (это как душе угодно из каких угодно соображений) кол-во одновременных запросов (строго параллельно один NaM может выполнить 4-е запроса), но никто не мешает нам сделать столько NaM, сколько мы хотим в разумных пределах. Создать Любой контейнер для хранения NaM'ов. Я часто использую даже QMap<Nam,reply> хотя это избыточно, но мне порой удобнее. обрабатывать лучше не nam->finished, а reply->finished, а заодно и reply>downloadProgress писать в контейнер NAM при старте запроса, выкидывать при окончании, и не делать новых запросов, пока размер контейнера больше заданного лимита. P.S. перекиньте автору :) я заблудился в мессагах по теме
почему нет необходимости последовательно их выполнять? этого и хотел добиться спрашивающий
ну возможно я не так понял, и невнимательно ну с последовательной загрузкой вообще откуда проблемы то.. странно
или ты про то что можно сразу очередь организовать?
да нет, наверное я не так поянл. вон выше а вообще сделав контейнер для хранения Nam'ов которые в работе, можно огграничить их кол-во Одним и будет последовательно строго :)
А как ограничить NAM? Я использую примерно такую конструкцию: While(item != item.end()) { QNetworkReplay *replay = m_manager.get(Qrequest(QUrl(str))); connection (replay, signal(finished), this, slot(download)); ++item; }
Ну просто же очень всё 1. создавай Nam динамически при запросе 2. создай контейнер-член класса и складывай туда Nam, например член класса QList <QNam> m_namList; в твоем методе while (m_namList.size() > ...) qApp->processEvents(); Nam *nam=new QNam(...) reply=nam->get(...) connection() m_namList<<nam; в reply::onFinished do_something nam->deleteLater(); m_namList.removeOne(nam);
ну не знаю.. создавать Nam просто ради того чтобы на finished взять из очереди следующий url и его обработать.. еще и while () processEvents()
это сугубо ваше право :) если же надо сугубо последовательно сделать в твоем случае ну подними флаг работы после get и сбрось его в finished()
Огромное спасибо!
Обсуждают сегодня