2012-03-09 16:25:49 +01:00
|
|
|
/* This file is part of Clementine.
|
|
|
|
Copyright 2012, David Sansome <me@davidsansome.com>
|
2014-11-01 19:38:39 +01:00
|
|
|
Copyright 2014, John Maguire <john.maguire@gmail.com>
|
2014-11-02 19:50:39 +01:00
|
|
|
Copyright 2014, Krzysztof Sobiecki <sobkas@gmail.com>
|
2014-02-07 16:34:20 +01:00
|
|
|
|
2012-03-09 16:25:49 +01:00
|
|
|
Clementine is free software: you can redistribute it and/or modify
|
|
|
|
it under the terms of the GNU General Public License as published by
|
|
|
|
the Free Software Foundation, either version 3 of the License, or
|
|
|
|
(at your option) any later version.
|
2014-02-07 16:34:20 +01:00
|
|
|
|
2012-03-09 16:25:49 +01:00
|
|
|
Clementine is distributed in the hope that it will be useful,
|
|
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
GNU General Public License for more details.
|
2014-02-07 16:34:20 +01:00
|
|
|
|
2012-03-09 16:25:49 +01:00
|
|
|
You should have received a copy of the GNU General Public License
|
|
|
|
along with Clementine. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include "gpoddersync.h"
|
2014-12-13 02:24:20 +01:00
|
|
|
|
|
|
|
#include <QCoreApplication>
|
|
|
|
#include <QHostInfo>
|
|
|
|
#include <QNetworkAccessManager>
|
|
|
|
#include <QSettings>
|
|
|
|
#include <QTimer>
|
|
|
|
|
2012-03-09 17:47:56 +01:00
|
|
|
#include "podcastbackend.h"
|
|
|
|
#include "podcasturlloader.h"
|
2012-03-09 16:25:49 +01:00
|
|
|
#include "core/application.h"
|
|
|
|
#include "core/closure.h"
|
2012-03-09 17:47:56 +01:00
|
|
|
#include "core/logging.h"
|
2012-03-09 16:25:49 +01:00
|
|
|
#include "core/network.h"
|
2012-03-09 17:47:56 +01:00
|
|
|
#include "core/timeconstants.h"
|
2012-03-09 16:25:49 +01:00
|
|
|
#include "core/utilities.h"
|
|
|
|
|
|
|
|
const char* GPodderSync::kSettingsGroup = "Podcasts";
|
2014-02-07 16:34:20 +01:00
|
|
|
const int GPodderSync::kFlushUpdateQueueDelay = 30 * kMsecPerSec; // 30 seconds
|
|
|
|
const int GPodderSync::kGetUpdatesInterval =
|
|
|
|
30 * 60 * kMsecPerSec; // 30 minutes
|
2012-03-09 16:25:49 +01:00
|
|
|
|
|
|
|
GPodderSync::GPodderSync(Application* app, QObject* parent)
|
2014-02-07 16:34:20 +01:00
|
|
|
: QObject(parent),
|
|
|
|
app_(app),
|
|
|
|
network_(new NetworkAccessManager(this)),
|
|
|
|
backend_(app_->podcast_backend()),
|
|
|
|
loader_(new PodcastUrlLoader(this)),
|
|
|
|
get_updates_timer_(new QTimer(this)),
|
|
|
|
flush_queue_timer_(new QTimer(this)),
|
|
|
|
flushing_queue_(false) {
|
2012-03-09 16:25:49 +01:00
|
|
|
ReloadSettings();
|
2012-03-09 17:47:56 +01:00
|
|
|
LoadQueue();
|
|
|
|
|
2012-03-09 16:25:49 +01:00
|
|
|
connect(app_, SIGNAL(SettingsChanged()), SLOT(ReloadSettings()));
|
2014-02-07 16:34:20 +01:00
|
|
|
connect(backend_, SIGNAL(SubscriptionAdded(Podcast)),
|
|
|
|
SLOT(SubscriptionAdded(Podcast)));
|
|
|
|
connect(backend_, SIGNAL(SubscriptionRemoved(Podcast)),
|
|
|
|
SLOT(SubscriptionRemoved(Podcast)));
|
2012-03-09 17:47:56 +01:00
|
|
|
|
2012-03-10 13:25:58 +01:00
|
|
|
get_updates_timer_->setInterval(kGetUpdatesInterval);
|
|
|
|
connect(get_updates_timer_, SIGNAL(timeout()), SLOT(GetUpdatesNow()));
|
|
|
|
|
2012-03-09 17:47:56 +01:00
|
|
|
flush_queue_timer_->setInterval(kFlushUpdateQueueDelay);
|
|
|
|
flush_queue_timer_->setSingleShot(true);
|
|
|
|
connect(flush_queue_timer_, SIGNAL(timeout()), SLOT(FlushUpdateQueue()));
|
|
|
|
|
|
|
|
if (is_logged_in()) {
|
|
|
|
GetUpdatesNow();
|
|
|
|
flush_queue_timer_->start();
|
2012-03-10 13:25:58 +01:00
|
|
|
get_updates_timer_->start();
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
2012-03-09 16:25:49 +01:00
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
GPodderSync::~GPodderSync() {}
|
2012-03-09 16:25:49 +01:00
|
|
|
|
|
|
|
QString GPodderSync::DeviceId() {
|
2014-02-07 16:34:20 +01:00
|
|
|
return QString("%1-%2")
|
|
|
|
.arg(qApp->applicationName(), QHostInfo::localHostName())
|
|
|
|
.toLower();
|
2012-03-09 16:25:49 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
QString GPodderSync::DefaultDeviceName() {
|
2014-02-07 16:34:20 +01:00
|
|
|
return tr("%1 on %2")
|
|
|
|
.arg(qApp->applicationName(), QHostInfo::localHostName());
|
2012-03-09 16:25:49 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
bool GPodderSync::is_logged_in() const {
|
|
|
|
return !username_.isEmpty() && !password_.isEmpty() && api_;
|
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::ReloadSettings() {
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
|
|
|
|
username_ = s.value("gpodder_username").toString();
|
|
|
|
password_ = s.value("gpodder_password").toString();
|
2012-03-09 17:47:56 +01:00
|
|
|
last_successful_get_ = s.value("gpodder_last_get").toDateTime();
|
2012-03-09 16:25:49 +01:00
|
|
|
|
|
|
|
if (!username_.isEmpty() && !password_.isEmpty()) {
|
|
|
|
api_.reset(new mygpo::ApiRequest(username_, password_, network_));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
QNetworkReply* GPodderSync::Login(const QString& username,
|
|
|
|
const QString& password,
|
2012-03-09 16:25:49 +01:00
|
|
|
const QString& device_name) {
|
|
|
|
api_.reset(new mygpo::ApiRequest(username, password, network_));
|
|
|
|
|
|
|
|
QNetworkReply* reply = api_->renameDevice(
|
2014-02-07 16:34:20 +01:00
|
|
|
username, DeviceId(), device_name,
|
|
|
|
Utilities::IsLaptop() ? mygpo::Device::LAPTOP : mygpo::Device::DESKTOP);
|
|
|
|
NewClosure(reply, SIGNAL(finished()), this,
|
|
|
|
SLOT(LoginFinished(QNetworkReply*, QString, QString)), reply,
|
|
|
|
username, password);
|
2012-03-09 16:25:49 +01:00
|
|
|
return reply;
|
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
void GPodderSync::LoginFinished(QNetworkReply* reply, const QString& username,
|
|
|
|
const QString& password) {
|
2012-03-09 16:25:49 +01:00
|
|
|
reply->deleteLater();
|
|
|
|
|
|
|
|
if (reply->error() == QNetworkReply::NoError) {
|
|
|
|
username_ = username;
|
|
|
|
password_ = password;
|
|
|
|
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
s.setValue("gpodder_username", username);
|
|
|
|
s.setValue("gpodder_password", password);
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
DoInitialSync();
|
2012-03-09 16:25:49 +01:00
|
|
|
} else {
|
|
|
|
api_.reset();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::Logout() {
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
s.remove("gpodder_username");
|
|
|
|
s.remove("gpodder_password");
|
2012-03-09 17:47:56 +01:00
|
|
|
s.remove("gpodder_last_get");
|
2012-03-09 16:25:49 +01:00
|
|
|
|
|
|
|
api_.reset();
|
|
|
|
}
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
void GPodderSync::GetUpdatesNow() {
|
2014-02-07 16:34:20 +01:00
|
|
|
if (!is_logged_in()) return;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
qlonglong timestamp = 0;
|
|
|
|
if (last_successful_get_.isValid()) {
|
2012-03-10 13:25:58 +01:00
|
|
|
timestamp = last_successful_get_.toTime_t();
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
mygpo::DeviceUpdatesPtr reply(
|
|
|
|
api_->deviceUpdates(username_, DeviceId(), timestamp));
|
|
|
|
NewClosure(reply, SIGNAL(finished()), this,
|
|
|
|
SLOT(DeviceUpdatesFinished(mygpo::DeviceUpdatesPtr)), reply);
|
|
|
|
NewClosure(reply, SIGNAL(parseError()), this,
|
|
|
|
SLOT(DeviceUpdatesFailed(mygpo::DeviceUpdatesPtr)), reply);
|
|
|
|
NewClosure(reply, SIGNAL(requestError(QNetworkReply::NetworkError)), this,
|
|
|
|
SLOT(DeviceUpdatesFailed(mygpo::DeviceUpdatesPtr)), reply);
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
|
2012-03-19 22:16:37 +01:00
|
|
|
void GPodderSync::DeviceUpdatesFailed(mygpo::DeviceUpdatesPtr reply) {
|
2012-03-09 17:47:56 +01:00
|
|
|
qLog(Warning) << "Failed to get gpodder.net device updates";
|
|
|
|
}
|
|
|
|
|
2012-03-19 22:16:37 +01:00
|
|
|
void GPodderSync::DeviceUpdatesFinished(mygpo::DeviceUpdatesPtr reply) {
|
2012-03-09 17:47:56 +01:00
|
|
|
// Remember episode actions for each podcast, so when we add a new podcast
|
|
|
|
// we can apply the actions immediately.
|
2014-12-16 14:59:17 +01:00
|
|
|
QMap<QUrl, QList<mygpo::EpisodePtr>> episodes_by_podcast;
|
2014-02-09 17:53:20 +01:00
|
|
|
for (mygpo::EpisodePtr episode : reply->updateList()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
episodes_by_podcast[episode->podcastUrl()].append(episode);
|
|
|
|
}
|
|
|
|
|
2014-02-09 17:53:20 +01:00
|
|
|
for (mygpo::PodcastPtr podcast : reply->addList()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
const QUrl url(podcast->url());
|
|
|
|
|
|
|
|
// Are we subscribed to this podcast already?
|
|
|
|
Podcast existing_podcast = backend_->GetSubscriptionByUrl(url);
|
|
|
|
if (existing_podcast.is_valid()) {
|
|
|
|
// Just apply actions to this existing podcast
|
2014-02-07 16:34:20 +01:00
|
|
|
ApplyActions(episodes_by_podcast[url],
|
|
|
|
existing_podcast.mutable_episodes());
|
2012-03-09 17:47:56 +01:00
|
|
|
backend_->UpdateEpisodes(existing_podcast.episodes());
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Start loading the podcast. Remember actions and apply them after we
|
|
|
|
// have a list of the episodes.
|
|
|
|
PodcastUrlLoaderReply* loader_reply = loader_->Load(url);
|
2014-02-07 16:34:20 +01:00
|
|
|
NewClosure(loader_reply, SIGNAL(Finished(bool)), this,
|
|
|
|
SLOT(NewPodcastLoaded(PodcastUrlLoaderReply*, QUrl,
|
|
|
|
QList<mygpo::EpisodePtr>)),
|
2012-03-09 17:47:56 +01:00
|
|
|
loader_reply, url, episodes_by_podcast[url]);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Unsubscribe from podcasts that were removed.
|
2014-02-09 17:07:35 +01:00
|
|
|
for (const QUrl& url : reply->removeList()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
backend_->Unsubscribe(backend_->GetSubscriptionByUrl(url));
|
|
|
|
}
|
|
|
|
|
|
|
|
last_successful_get_ = QDateTime::currentDateTime();
|
|
|
|
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
s.setValue("gpodder_last_get", last_successful_get_);
|
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
void GPodderSync::NewPodcastLoaded(PodcastUrlLoaderReply* reply,
|
|
|
|
const QUrl& url,
|
2012-03-09 17:47:56 +01:00
|
|
|
const QList<mygpo::EpisodePtr>& actions) {
|
|
|
|
reply->deleteLater();
|
|
|
|
|
|
|
|
if (!reply->is_success()) {
|
|
|
|
qLog(Warning) << "Error fetching podcast at" << url << ":"
|
|
|
|
<< reply->error_text();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (reply->result_type() != PodcastUrlLoaderReply::Type_Podcast) {
|
|
|
|
qLog(Warning) << "The URL" << url << "no longer contains a podcast";
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Apply the actions to the episodes in the podcast.
|
2014-02-07 20:34:34 +01:00
|
|
|
for (Podcast podcast : reply->podcast_results()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
ApplyActions(actions, podcast.mutable_episodes());
|
|
|
|
|
|
|
|
// Add the subscription
|
|
|
|
backend_->Subscribe(&podcast);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
void GPodderSync::ApplyActions(
|
2014-12-16 14:59:17 +01:00
|
|
|
const QList<QSharedPointer<mygpo::Episode>>& actions,
|
2014-02-07 16:34:20 +01:00
|
|
|
PodcastEpisodeList* episodes) {
|
|
|
|
for (PodcastEpisodeList::iterator it = episodes->begin();
|
|
|
|
it != episodes->end(); ++it) {
|
2012-03-09 17:47:56 +01:00
|
|
|
// Find an action for this episode
|
2014-02-09 17:53:20 +01:00
|
|
|
for (mygpo::EpisodePtr action : actions) {
|
2014-02-07 16:34:20 +01:00
|
|
|
if (action->url() != it->url()) continue;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
switch (action->status()) {
|
2014-02-07 16:34:20 +01:00
|
|
|
case mygpo::Episode::PLAY:
|
|
|
|
case mygpo::Episode::DOWNLOAD:
|
|
|
|
it->set_listened(true);
|
|
|
|
break;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
default:
|
|
|
|
break;
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::SubscriptionAdded(const Podcast& podcast) {
|
2014-02-07 16:34:20 +01:00
|
|
|
if (!is_logged_in()) return;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
const QUrl& url = podcast.url();
|
|
|
|
|
|
|
|
queued_remove_subscriptions_.remove(url);
|
|
|
|
queued_add_subscriptions_.insert(url);
|
|
|
|
|
|
|
|
SaveQueue();
|
|
|
|
flush_queue_timer_->start();
|
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::SubscriptionRemoved(const Podcast& podcast) {
|
2014-02-07 16:34:20 +01:00
|
|
|
if (!is_logged_in()) return;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
const QUrl& url = podcast.url();
|
|
|
|
|
|
|
|
queued_remove_subscriptions_.insert(url);
|
|
|
|
queued_add_subscriptions_.remove(url);
|
|
|
|
|
|
|
|
SaveQueue();
|
|
|
|
flush_queue_timer_->start();
|
|
|
|
}
|
|
|
|
|
|
|
|
namespace {
|
2014-02-07 16:34:20 +01:00
|
|
|
template <typename T>
|
|
|
|
void WriteContainer(const T& container, QSettings* s, const char* array_name,
|
|
|
|
const char* item_name) {
|
|
|
|
s->beginWriteArray(array_name, container.count());
|
|
|
|
int index = 0;
|
2014-02-09 17:07:35 +01:00
|
|
|
for (const auto& item : container) {
|
2014-02-07 16:34:20 +01:00
|
|
|
s->setArrayIndex(index++);
|
|
|
|
s->setValue(item_name, item);
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
2014-02-07 16:34:20 +01:00
|
|
|
s->endArray();
|
|
|
|
}
|
2012-03-09 17:47:56 +01:00
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
template <typename T>
|
|
|
|
void ReadContainer(T* container, QSettings* s, const char* array_name,
|
|
|
|
const char* item_name) {
|
|
|
|
container->clear();
|
|
|
|
const int count = s->beginReadArray(array_name);
|
|
|
|
for (int i = 0; i < count; ++i) {
|
|
|
|
s->setArrayIndex(i);
|
|
|
|
*container << s->value(item_name).value<typename T::value_type>();
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
2014-02-07 16:34:20 +01:00
|
|
|
s->endArray();
|
|
|
|
}
|
2014-02-07 20:34:34 +01:00
|
|
|
} // namespace
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
void GPodderSync::SaveQueue() {
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
WriteContainer(queued_add_subscriptions_, &s,
|
|
|
|
"gpodder_queued_add_subscriptions", "url");
|
|
|
|
WriteContainer(queued_remove_subscriptions_, &s,
|
|
|
|
"gpodder_queued_remove_subscriptions", "url");
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::LoadQueue() {
|
|
|
|
QSettings s;
|
|
|
|
s.beginGroup(kSettingsGroup);
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
ReadContainer(&queued_add_subscriptions_, &s,
|
|
|
|
"gpodder_queued_add_subscriptions", "url");
|
|
|
|
ReadContainer(&queued_remove_subscriptions_, &s,
|
|
|
|
"gpodder_queued_remove_subscriptions", "url");
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::FlushUpdateQueue() {
|
2014-02-07 16:34:20 +01:00
|
|
|
if (!is_logged_in() || flushing_queue_) return;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
QSet<QUrl> all_urls =
|
|
|
|
queued_add_subscriptions_ + queued_remove_subscriptions_;
|
|
|
|
if (all_urls.isEmpty()) return;
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
flushing_queue_ = true;
|
2014-02-09 17:53:20 +01:00
|
|
|
mygpo::AddRemoveResultPtr reply(api_->addRemoveSubscriptions(
|
2014-02-07 16:34:20 +01:00
|
|
|
username_, DeviceId(), queued_add_subscriptions_.toList(),
|
|
|
|
queued_remove_subscriptions_.toList()));
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
qLog(Info) << "Sending" << all_urls.count() << "changes to gpodder.net";
|
|
|
|
|
2014-02-07 16:34:20 +01:00
|
|
|
NewClosure(reply, SIGNAL(finished()), this,
|
|
|
|
SLOT(AddRemoveFinished(mygpo::AddRemoveResultPtr, QList<QUrl>)),
|
2012-03-19 22:16:37 +01:00
|
|
|
reply, all_urls.toList());
|
2014-02-07 16:34:20 +01:00
|
|
|
NewClosure(reply, SIGNAL(parseError()), this,
|
|
|
|
SLOT(AddRemoveFailed(mygpo::AddRemoveResultPtr)), reply);
|
|
|
|
NewClosure(reply, SIGNAL(requestError(QNetworkReply::NetworkError)), this,
|
|
|
|
SLOT(AddRemoveFailed(mygpo::AddRemoveResultPtr)), reply);
|
2012-03-09 17:47:56 +01:00
|
|
|
}
|
|
|
|
|
2012-03-19 22:16:37 +01:00
|
|
|
void GPodderSync::AddRemoveFailed(mygpo::AddRemoveResultPtr reply) {
|
2012-03-09 17:47:56 +01:00
|
|
|
flushing_queue_ = false;
|
|
|
|
qLog(Warning) << "Failed to update gpodder.net subscriptions";
|
|
|
|
}
|
|
|
|
|
2012-03-19 22:16:37 +01:00
|
|
|
void GPodderSync::AddRemoveFinished(mygpo::AddRemoveResultPtr reply,
|
2012-03-09 17:47:56 +01:00
|
|
|
const QList<QUrl>& affected_urls) {
|
|
|
|
flushing_queue_ = false;
|
|
|
|
|
|
|
|
// Remove the URLs from the queue.
|
2014-02-09 17:07:35 +01:00
|
|
|
for (const QUrl& url : affected_urls) {
|
2012-03-09 17:47:56 +01:00
|
|
|
queued_add_subscriptions_.remove(url);
|
|
|
|
queued_remove_subscriptions_.remove(url);
|
|
|
|
}
|
|
|
|
|
|
|
|
SaveQueue();
|
|
|
|
|
|
|
|
// Did more change in the mean time?
|
2014-02-07 16:34:20 +01:00
|
|
|
if (!queued_add_subscriptions_.isEmpty() ||
|
|
|
|
!queued_remove_subscriptions_.isEmpty()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
flush_queue_timer_->start();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void GPodderSync::DoInitialSync() {
|
|
|
|
// Get updates from the server
|
|
|
|
GetUpdatesNow();
|
2012-03-10 13:25:58 +01:00
|
|
|
get_updates_timer_->start();
|
2012-03-09 17:47:56 +01:00
|
|
|
|
|
|
|
// Send our complete list of subscriptions
|
|
|
|
queued_remove_subscriptions_.clear();
|
|
|
|
queued_add_subscriptions_.clear();
|
2014-02-07 20:40:23 +01:00
|
|
|
for (const Podcast& podcast : backend_->GetAllSubscriptions()) {
|
2012-03-09 17:47:56 +01:00
|
|
|
queued_add_subscriptions_.insert(podcast.url());
|
|
|
|
}
|
|
|
|
|
|
|
|
SaveQueue();
|
|
|
|
FlushUpdateQueue();
|
|
|
|
}
|