File indexing completed on 2024-06-02 05:33:02

0001 /*
0002  * SPDX-FileCopyrightText: 2014 Kevin Ottens <ervin@kde.org>
0003  * SPDX-License-Identifier: GPL-2.0-only OR GPL-3.0-only OR LicenseRef-KDE-Accepted-GPL
0004  */
0005 
0006 
0007 #include "jobhandler.h"
0008 
0009 #include <QHash>
0010 #include <QObject>
0011 
0012 #include <KJob>
0013 
0014 using namespace Utils;
0015 
0016 class JobHandlerInstance : public QObject
0017 {
0018     Q_OBJECT
0019 public:
0020     JobHandlerInstance()
0021         : QObject() {}
0022 
0023 public slots:
0024     void handleJobResult(KJob *job)
0025     {
0026         Q_ASSERT(m_handlers.contains(job) || m_handlersWithJob.contains(job));
0027 
0028         foreach (const auto &handler, m_handlers.take(job)) {
0029             handler();
0030         }
0031 
0032         foreach (const auto &handler, m_handlersWithJob.take(job)) {
0033             handler(job);
0034         }
0035     }
0036 
0037     void onDestroyed(QObject *o)
0038     {
0039         auto job = static_cast<KJob*>(o);
0040         Q_ASSERT(job);
0041         m_handlers.remove(job);
0042         m_handlersWithJob.remove(job);
0043     }
0044 
0045 public:
0046     QHash<KJob *, QList<JobHandler::ResultHandler>> m_handlers;
0047     QHash<KJob *, QList<JobHandler::ResultHandlerWithJob>> m_handlersWithJob;
0048 };
0049 
0050 Q_GLOBAL_STATIC(JobHandlerInstance, jobHandlerInstance)
0051 
0052 void JobHandler::install(KJob *job, const ResultHandler &handler, StartMode startMode)
0053 {
0054     auto self = jobHandlerInstance();
0055     QObject::connect(job, &KJob::result, self, &JobHandlerInstance::handleJobResult, Qt::UniqueConnection);
0056     QObject::connect(job, &KJob::destroyed, self, &JobHandlerInstance::onDestroyed, Qt::UniqueConnection);
0057     self->m_handlers[job] << handler;
0058     if (startMode == AutoStart)
0059         job->start();
0060 }
0061 
0062 void JobHandler::install(KJob *job, const ResultHandlerWithJob &handler, StartMode startMode)
0063 {
0064     auto self = jobHandlerInstance();
0065     QObject::connect(job, &KJob::result, self, &JobHandlerInstance::handleJobResult, Qt::UniqueConnection);
0066     QObject::connect(job, &KJob::destroyed, self, &JobHandlerInstance::onDestroyed, Qt::UniqueConnection);
0067     self->m_handlersWithJob[job] << handler;
0068     if (startMode == AutoStart)
0069         job->start();
0070 }
0071 
0072 template<typename ResultHandler>
0073 void clearJobs(JobHandlerInstance *self, QHash<KJob*, QList<ResultHandler>> &jobs)
0074 {
0075     for (auto it = jobs.cbegin(); it != jobs.cend(); ++it) {
0076         QObject::disconnect(it.key(), 0, self, 0);
0077     }
0078     jobs.clear();
0079 }
0080 
0081 void JobHandler::clear()
0082 {
0083     auto self = jobHandlerInstance();
0084     clearJobs(self, self->m_handlers);
0085     clearJobs(self, self->m_handlersWithJob);
0086 }
0087 
0088 int JobHandler::jobCount()
0089 {
0090     auto self = jobHandlerInstance();
0091     return self->m_handlers.size() + self->m_handlersWithJob.size();
0092 }
0093 
0094 #include "jobhandler.moc"