diff --git a/src/iodaemon/fs.cpp b/src/iodaemon/fs.cpp index 0ba6457..172a33d 100644 --- a/src/iodaemon/fs.cpp +++ b/src/iodaemon/fs.cpp @@ -1,183 +1,183 @@ /* * Copyright 2016 Boudhayan Gupta * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of KDE e.V. (or its successor approved by the * membership of KDE e.V.) nor the names of its contributors may be used * to endorse or promote products derived from this software without * specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #include "fs.h" StashFileSystem::StashFileSystem(QObject *parent) : QObject(parent), root(DirectoryNode) { root.children = new StashNode(); displayRoot(); } StashFileSystem::~StashFileSystem() { deleteChildren(root); } void StashFileSystem::deleteChildren(StashNodeData nodeData) { if (nodeData.children != nullptr) { Q_FOREACH (auto data, nodeData.children->values()) { deleteChildren(data); } delete nodeData.children; nodeData.children = nullptr; } } QStringList StashFileSystem::splitPath(const QString &path) { QString filePath = path; if (filePath.startsWith('/')) { filePath = filePath.right(filePath.size() - 1); } if (filePath.endsWith('/')) { filePath = filePath.left(filePath.size() - 1); } return filePath.split('/'); } bool StashFileSystem::delEntry(const QString &location) { QStringList path = splitPath(location); QString name = path.takeLast(); StashNodeData baseData = findNode(path); if (!(baseData.type == DirectoryNode)) { return false; } if (!(baseData.children->contains(name))) { return false; } deleteChildren(baseData.children->value(name, StashNodeData(InvalidNode))); return (baseData.children->remove(name) > 0); } bool StashFileSystem::addNode(const QString &location, const StashNodeData &data) { QStringList path = splitPath(location); QString name = path.takeLast(); StashNodeData baseData = findNode(path); if (!(baseData.type == DirectoryNode)) { deleteChildren(data); return false; } baseData.children->insert(name, data); return true; } bool StashFileSystem::addFile(const QString &src, const QString &dest) { StashNodeData fileData(FileNode); fileData.source = src; return addNode(dest, fileData); } bool StashFileSystem::addSymlink(const QString &src, const QString &dest) { StashNodeData fileData(SymlinkNode); fileData.source = src; return addNode(dest, fileData); } bool StashFileSystem::addFolder(const QString &dest) { StashNodeData fileData(DirectoryNode); fileData.source = QStringLiteral(""); fileData.children = new StashNode(); return addNode(dest, fileData); } bool StashFileSystem::copyFile(const QString &src, const QString &dest) { StashNodeData fileToCopy = findNode(src); return addNode(dest, fileToCopy); } StashFileSystem::StashNodeData StashFileSystem::findNode(QString path) { return findNode(splitPath(path)); } StashFileSystem::StashNodeData StashFileSystem::findNode(QStringList path) { StashNode *node = root.children; StashNodeData data = StashNodeData(InvalidNode); - if (!path.size() || path.at(0) == "") { + if (!path.size() || path.at(0).isEmpty()) { return root; } else { for (int i = 0; i < path.size(); ++i) { if (node->contains(path[i])) { data = node->value(path[i], StashNodeData(InvalidNode)); if (data.type == DirectoryNode) { node = data.children; } if (i == path.size() - 1) { return data; } } else { return StashNodeData(InvalidNode); } } return StashNodeData(InvalidNode); } } void StashFileSystem::deleteAllItems() { deleteChildren(root); } void StashFileSystem::displayNode(StashNode *node) { - for (auto it = node->begin(); it != node->end(); it++) + for (auto it = node->begin(); it != node->end(); ++it) { qDebug() << "stashpath" << it.key(); qDebug() << "filepath" << it.value().source; qDebug() << "filetype" << it.value().type; if (it.value().type == DirectoryNode) { qDebug() << "parent" << it.key(); displayNode(it.value().children); } } return; } void StashFileSystem::displayRoot() { displayNode(root.children); } diff --git a/src/iodaemon/stashnotifier.cpp b/src/iodaemon/stashnotifier.cpp index 7b4ba19..c42f2bb 100644 --- a/src/iodaemon/stashnotifier.cpp +++ b/src/iodaemon/stashnotifier.cpp @@ -1,221 +1,221 @@ /*************************************************************************** * Copyright (C) 2016 by Arnav Dhamija * * * * This program 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 2 of the License, or * * (at your option) any later version. * * * * This program 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. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * ***************************************************************************/ #include "stashnotifier.h" #include "stash_adaptor.h" #include #include #include #include #include #include #include #include #include K_PLUGIN_FACTORY_WITH_JSON(StashNotifierFactory, "stashnotifier.json", registerPlugin();) StashNotifier::StashNotifier(QObject *parent, const QList &var, const QString daemonService, const QString daemonPath) : KDEDModule(parent), m_daemonService(daemonService), m_daemonPath(daemonPath) { dirWatch = new KDirWatch(this); qDebug() << "Launching stash daemon."; new StashNotifierAdaptor(this); QDBusConnection dbus = QDBusConnection::sessionBus(); dbus.registerObject(m_daemonPath, this); dbus.registerService(m_daemonService); fileSystem = new StashFileSystem(parent); connect(dirWatch, &KDirWatch::dirty, this, &StashNotifier::dirty); connect(dirWatch, &KDirWatch::created, this, &StashNotifier::created); connect(dirWatch, &KDirWatch::deleted, this, &StashNotifier::removePath); connect(this, &StashNotifier::listChanged, this, &StashNotifier::displayRoot); } StashNotifier::~StashNotifier() { } QString StashNotifier::encodeString(StashFileSystem::StashNode::iterator node, const QString &path) //format type::stashpath::source { QString encodedString; switch (node.value().type) { case StashFileSystem::NodeType::DirectoryNode: encodedString = "dir"; break; case StashFileSystem::NodeType::FileNode: encodedString = "file"; break; case StashFileSystem::NodeType::SymlinkNode: encodedString = "symlink"; break; case StashFileSystem::NodeType::InvalidNode: encodedString = "invalid"; break; } if (path == "/") { encodedString += "::" + QStringLiteral("/") + node.key(); } else { encodedString += "::" + path + QStringLiteral("/") + node.key(); } if (node.value().type == StashFileSystem::NodeType::FileNode || node.value().type == StashFileSystem::NodeType::SymlinkNode) { encodedString += "::" + node.value().source; } else { encodedString += "::"; } return encodedString; } QString StashNotifier::encodeString(StashFileSystem::StashNodeData nodeData, const QString &path) { QString encodedString; switch (nodeData.type) { case StashFileSystem::NodeType::DirectoryNode: encodedString = "dir"; break; case StashFileSystem::NodeType::FileNode: encodedString = "file"; break; case StashFileSystem::NodeType::SymlinkNode: encodedString = "symlink"; break; case StashFileSystem::NodeType::InvalidNode: encodedString = "invalid"; break; } encodedString += "::" + path; if (nodeData.type == StashFileSystem::NodeType::FileNode || nodeData.type == StashFileSystem::NodeType::SymlinkNode) { encodedString += "::" + nodeData.source; } else { encodedString += "::"; } return encodedString; } QStringList StashNotifier::fileList(const QString &path) //forwards list over QDBus to the KIO slave { QStringList contents; StashFileSystem::StashNodeData node = fileSystem->findNode(path); if (node.type != StashFileSystem::NodeType::DirectoryNode) { contents.append("error::error::InvalidNode"); } else { - for (auto it = node.children->begin(); it != node.children->end(); it++) { + for (auto it = node.children->begin(); it != node.children->end(); ++it) { contents.append(encodeString(it, path)); } } return contents; } QString StashNotifier::fileInfo(const QString &path) //forwards data of a single file to the KIO slave { QString fileData; StashFileSystem::StashNodeData node = fileSystem->findNode(path); fileData = encodeString(node, path); return fileData; } void StashNotifier::addPath(const QString &source, const QString &stashPath, const int &fileType) { QString processedPath = processString(stashPath); if (fileSystem->findNode(stashPath).type == StashFileSystem::NodeType::InvalidNode) { if (fileType == StashFileSystem::NodeType::DirectoryNode) { dirWatch->addDir(processedPath); fileSystem->addFolder(processedPath); } else if (fileType == StashFileSystem::NodeType::FileNode) { dirWatch->addFile(source); fileSystem->addFile(processString(source), stashPath); } else if (fileType == StashFileSystem::NodeType::SymlinkNode) { dirWatch->addFile(source); fileSystem->addSymlink(processString(source), stashPath); } emit listChanged(); } } QString StashNotifier::processString(const QString &path) { QString processedPath = path.simplified(); if (processedPath.at(processedPath.size() - 1) == '/') { processedPath.chop(1); } return processedPath; } void StashNotifier::removePath(const QString &path) { StashFileSystem::NodeType fileType; QString processedPath = processString(path); if (fileType == StashFileSystem::NodeType::DirectoryNode) { dirWatch->removeDir(processedPath); } else { QString encodedName = fileInfo(path); QString filePath = encodedName.split("::", QString::KeepEmptyParts).at(2); dirWatch->removeFile(filePath); } fileSystem->delEntry(path); emit listChanged(); } void StashNotifier::nukeStash() { qDebug() << "Nuking stash: all files on it will be deleted!"; fileSystem->deleteAllItems(); qDebug() << "Nuked."; } void StashNotifier::pingDaemon() { // just to see if this exists in kded5 or whether we need to create a process for it for the test case } bool StashNotifier::copyWithStash(const QString &src, const QString &dest) { return fileSystem->copyFile(src, dest); } void StashNotifier::dirty(const QString &path) { //nothing to be done here } void StashNotifier::created(const QString &path) { //nothing to be done here } #include "stashnotifier.moc" diff --git a/src/iodaemon/stashnotifier.h b/src/iodaemon/stashnotifier.h index 2d2ed9f..cdcff27 100644 --- a/src/iodaemon/stashnotifier.h +++ b/src/iodaemon/stashnotifier.h @@ -1,73 +1,72 @@ /*************************************************************************** * Copyright (C) 2016 by Arnav Dhamija * * * * This program 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 2 of the License, or * * (at your option) any later version. * * * * This program 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. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * ***************************************************************************/ #ifndef STASHNOTIFIER_H #define STASHNOTIFIER_H #include "fs.h" -#include #include #include class KDirWatch; class StashNotifier : public KDEDModule { Q_OBJECT Q_CLASSINFO("D-Bus Interface", "org.kde.kio.StashNotifier") private: KDirWatch *dirWatch; StashFileSystem *fileSystem; const QString m_daemonService; const QString m_daemonPath; QString processString(const QString &path); QString encodeString(StashFileSystem::StashNode::iterator node, const QString &path); QString encodeString(StashFileSystem::StashNodeData nodeData, const QString &path); public: StashNotifier(QObject* parent, const QList&, const QString daemonService = "org.kde.kio.StashNotifier", const QString daemonPath = "/StashNotifier"); ~StashNotifier(); Q_SIGNALS: Q_SCRIPTABLE void listChanged(); public Q_SLOTS: Q_SCRIPTABLE void addPath(const QString &source, const QString &stashPath, const int &fileType); Q_SCRIPTABLE void removePath(const QString &path); Q_SCRIPTABLE void nukeStash(); Q_SCRIPTABLE void pingDaemon(); Q_SCRIPTABLE bool copyWithStash(const QString &src, const QString &dest); Q_SCRIPTABLE QStringList fileList(const QString &path); Q_SCRIPTABLE QString fileInfo(const QString &path); private Q_SLOTS: void dirty(const QString &path); void created(const QString &path); void displayRoot() //function to the contents of the SFS for testing { //fileSystem->displayRoot(); } }; #endif diff --git a/src/ioslave/ioslave.cpp b/src/ioslave/ioslave.cpp index 3dd88dd..ade5981 100644 --- a/src/ioslave/ioslave.cpp +++ b/src/ioslave/ioslave.cpp @@ -1,431 +1,431 @@ /*************************************************************************** * Copyright (C) 2016 by Arnav Dhamija * * * * This program 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 2 of the License, or * * (at your option) any later version. * * * * This program 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. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * ***************************************************************************/ #include "ioslave.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include class KIOPluginForMetaData : public QObject { Q_OBJECT Q_PLUGIN_METADATA(IID "org.kde.kio.slave.filestash" FILE "ioslave.json") }; extern "C" { int Q_DECL_EXPORT kdemain(int argc, char **argv) { QCoreApplication app(argc, argv); FileStash slave(argv[2], argv[3]); slave.dispatchLoop(); return 0; } } FileStash::FileStash(const QByteArray &pool, const QByteArray &app, const QString daemonService, const QString daemonPath) : KIO::ForwardingSlaveBase("stash", pool, app), m_daemonService(daemonService), m_daemonPath(daemonPath) {} FileStash::~FileStash() {} bool FileStash::rewriteUrl(const QUrl &url, QUrl &newUrl) { if (url.scheme() != "file") { newUrl.setScheme("file"); newUrl.setPath(url.path()); } else { newUrl = url; } return true; } void FileStash::createTopLevelDirEntry(KIO::UDSEntry &entry) { entry.clear(); entry.insert(KIO::UDSEntry::UDS_NAME, QStringLiteral(".")); entry.insert(KIO::UDSEntry::UDS_FILE_TYPE, 0040000); entry.insert(KIO::UDSEntry::UDS_ACCESS, 0700); entry.insert(KIO::UDSEntry::UDS_MIME_TYPE, QStringLiteral("inode/directory")); } QStringList FileStash::setFileList(const QUrl &url) { QDBusMessage msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "fileList"); msg << url.path(); QDBusReply received = QDBusConnection::sessionBus().call(msg); return received.value(); } QString FileStash::setFileInfo(const QUrl &url) { QDBusMessage msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "fileInfo"); msg << url.path(); QDBusReply received = QDBusConnection::sessionBus().call(msg); return received.value(); } void FileStash::stat(const QUrl &url) { KIO::UDSEntry entry; if (isRoot(url.path())) { createTopLevelDirEntry(entry); } else { QString fileInfo = setFileInfo(url); FileStash::dirList item = createDirListItem(fileInfo); if (!createUDSEntry(entry, item)) { error(KIO::ERR_SLAVE_DEFINED, QString("Could not stat.")); return; } } statEntry(entry); finished(); } bool FileStash::statUrl(const QUrl &url, KIO::UDSEntry &entry) { KIO::StatJob *statJob = KIO::stat(url, KIO::HideProgressInfo); bool ok = statJob->exec(); if (ok) { entry = statJob->statResult(); } return ok; } bool FileStash::createUDSEntry(KIO::UDSEntry &entry, const FileStash::dirList &fileItem) { QMimeType fileMimetype; QMimeDatabase mimeDatabase; QString stringFilePath = fileItem.filePath; switch (fileItem.type) { case NodeType::DirectoryNode: entry.insert(KIO::UDSEntry::UDS_FILE_TYPE, 0040000); entry.insert(KIO::UDSEntry::UDS_MIME_TYPE, QString("inode/directory")); entry.insert(KIO::UDSEntry::UDS_NAME, QUrl(stringFilePath).fileName()); entry.insert(KIO::UDSEntry::UDS_DISPLAY_NAME, QUrl(stringFilePath).fileName()); break; case NodeType::InvalidNode: entry.insert(KIO::UDSEntry::UDS_NAME, fileItem.filePath); break; default: QByteArray physicalPath_c = QFile::encodeName(fileItem.source); QT_STATBUF buff; QT_LSTAT(physicalPath_c, &buff); mode_t access = buff.st_mode & 07777; QFileInfo entryInfo; entryInfo = QFileInfo(fileItem.source); fileMimetype = mimeDatabase.mimeTypeForFile(fileItem.source); entry.insert(KIO::UDSEntry::UDS_TARGET_URL, QUrl::fromLocalFile(fileItem.source).toString()); entry.insert(KIO::UDSEntry::UDS_MIME_TYPE, fileMimetype.name()); entry.insert(KIO::UDSEntry::UDS_DISPLAY_NAME, QUrl(stringFilePath).fileName()); entry.insert(KIO::UDSEntry::UDS_NAME, QUrl(stringFilePath).fileName()); entry.insert(KIO::UDSEntry::UDS_ACCESS, access); entry.insert(KIO::UDSEntry::UDS_SIZE, entryInfo.size()); entry.insert(KIO::UDSEntry::UDS_MODIFICATION_TIME, buff.st_mtime); entry.insert(KIO::UDSEntry::UDS_ACCESS_TIME, buff.st_atime); if (fileItem.type == NodeType::FileNode) { entry.insert(KIO::UDSEntry::UDS_FILE_TYPE, 0100000); } else if (fileItem.type == NodeType::SymlinkNode) { entry.insert(KIO::UDSEntry::UDS_FILE_TYPE, 0120000); } else { return false; } } return true; } FileStash::dirList FileStash::createDirListItem(QString fileInfo) { QStringList strings = fileInfo.split("::", QString::KeepEmptyParts); FileStash::dirList item; if (strings.at(0) == "dir") { item.type = FileStash::NodeType::DirectoryNode; } else if (strings.at(0) == "file") { item.type = FileStash::NodeType::FileNode; } else if (strings.at(0) == "symlink") { item.type = FileStash::NodeType::SymlinkNode; } else if (strings.at(0) == "invalid") { item.type = FileStash::NodeType::InvalidNode; } item.filePath = strings.at(1); item.source = strings.at(2); return item; } void FileStash::listDir(const QUrl &url) { QStringList fileList = setFileList(url); if (!fileList.size()) { finished(); return; } FileStash::dirList item; KIO::UDSEntry entry; if (isRoot(url.path())) { createTopLevelDirEntry(entry); listEntry(entry); } if (fileList.at(0) == "error::error::InvalidNode") { error(KIO::ERR_SLAVE_DEFINED, QString("The file either does not exist or has not been stashed yet.")); } else { - for (auto it = fileList.begin(); it != fileList.end(); it++) { + for (auto it = fileList.begin(); it != fileList.end(); ++it) { entry.clear(); item = createDirListItem(*it); if (createUDSEntry(entry, item)) { listEntry(entry); } else { error(KIO::ERR_SLAVE_DEFINED, QString("The UDS Entry could not be created.")); return; } } finished(); } } void FileStash::mkdir(const QUrl &url, int permissions) { Q_UNUSED(permissions) QDBusMessage replyMessage; QDBusMessage msg; msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "addPath"); QString destinationPath = url.path(); msg << "" << destinationPath << NodeType::DirectoryNode; replyMessage = QDBusConnection::sessionBus().call(msg); if (replyMessage.type() != QDBusMessage::ErrorMessage) { finished(); } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not create a directory")); } } bool FileStash::copyFileToStash(const QUrl &src, const QUrl &dest, KIO::JobFlags flags) { Q_UNUSED(flags) NodeType fileType; QFileInfo fileInfo = QFileInfo(src.path()); if (fileInfo.isFile()) { fileType = NodeType::FileNode; } else if (fileInfo.isSymLink()) { fileType = NodeType::SymlinkNode; } else if (fileInfo.isDir()) { // if I'm not wrong, this can never happen, but we should handle it anyway fileType = NodeType::DirectoryNode; qDebug() << "DirectoryNode...created?"; } else { return false; } QDBusMessage replyMessage; QDBusMessage msg; msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "addPath"); QString destinationPath = dest.path(); msg << src.path() << destinationPath << (int) fileType; replyMessage = QDBusConnection::sessionBus().call(msg); if (replyMessage.type() != QDBusMessage::ErrorMessage) { return true; } else { return false; } } bool FileStash::copyStashToFile(const QUrl &src, const QUrl &dest, KIO::JobFlags flags) { const QString destInfo = setFileInfo(src); const FileStash::dirList fileItem = createDirListItem(destInfo); KIO::UDSEntry entry; if (fileItem.type != NodeType::DirectoryNode) { QByteArray physicalPath_c = QFile::encodeName(fileItem.source); QT_STATBUF buff; QT_LSTAT(physicalPath_c, &buff); mode_t access = buff.st_mode & 07777; KIO::ForwardingSlaveBase::copy(QUrl::fromLocalFile(fileItem.source), dest, access, flags); return true; } return false; } bool FileStash::copyStashToStash(const QUrl &src, const QUrl &dest, KIO::JobFlags flags) { Q_UNUSED(flags) KIO::UDSEntry entry; statUrl(src, entry); KFileItem fileItem(entry, src); const dirList item = createDirListItem(setFileInfo(src)); NodeType fileType; if (fileItem.isFile()) { fileType = NodeType::FileNode; } else if (fileItem.isLink()) { fileType = NodeType::SymlinkNode; } else if (fileItem.isDir()) { fileType = NodeType::DirectoryNode; } else { return false; } QDBusMessage replyMessage; QDBusMessage msg; msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "addPath"); msg << item.source << dest.path() << fileType; replyMessage = QDBusConnection::sessionBus().call(msg); if (replyMessage.type() != QDBusMessage::ErrorMessage) { return true; } else { return false; } } void FileStash::copy(const QUrl &src, const QUrl &dest, int permissions, KIO::JobFlags flags) { KIO::UDSEntry entry; statUrl(src, entry); KFileItem item(entry, src); QUrl newDestPath; newDestPath = QUrl(dest.adjusted(QUrl::RemoveFilename).toString() + item.name()); if (src.scheme() != "stash" && dest.scheme() == "stash") { if (copyFileToStash(src, newDestPath, flags)) { finished(); } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not copy.")); } return; } else if (src.scheme() == "stash" && dest.scheme() != "stash") { if (!copyStashToFile(src, newDestPath, flags)) { error(KIO::ERR_SLAVE_DEFINED, QString("Could not copy.")); } return; } else if (src.scheme() == "stash" && dest.scheme() == "stash") { if (copyStashToStash(src, newDestPath, flags)) { finished(); } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not copy.")); } return; } else if (dest.scheme() == "mtp") { error(KIO::ERR_SLAVE_DEFINED, QString("Copying to mtp slaves is still under development!")); } else { KIO::ForwardingSlaveBase::copy(item.targetUrl(), newDestPath, permissions, flags); } } void FileStash::del(const QUrl &url, bool isFile) { Q_UNUSED(isFile) if (deletePath(url)) { finished(); } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not reach the stash daemon")); } } bool FileStash::deletePath(const QUrl &url) { QDBusMessage replyMessage; QDBusMessage msg; msg = QDBusMessage::createMethodCall( m_daemonService, m_daemonPath, "", "removePath"); if (isRoot(url.adjusted(QUrl::RemoveFilename).toString())) { msg << url.fileName(); } else { msg << url.path(); } replyMessage = QDBusConnection::sessionBus().call(msg); if (replyMessage.type() != QDBusMessage::ErrorMessage) { return true; } else { return false; } } void FileStash::rename(const QUrl &src, const QUrl &dest, KIO::JobFlags flags) { KIO::UDSEntry entry; if (src.scheme() == "stash" && dest.scheme() == "stash") { if (copyStashToStash(src, dest, flags)) { if (deletePath(src)) { finished(); } } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not rename.")); } return; } else if (src.scheme() == "file" && dest.scheme() == "stash") { if (copyFileToStash(src, dest, flags)) { finished(); } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not rename.")); } return; } else if (src.scheme() == "stash" && dest.scheme() == "file") { if (copyStashToFile(src, dest, flags)) { if (deletePath(src)) { return; } } else { error(KIO::ERR_SLAVE_DEFINED, QString("Could not rename.")); } } } bool FileStash::isRoot(const QString &string) { if (string.isEmpty() || string == "/") { return true; } return false; } #include "ioslave.moc" diff --git a/src/ioslave/ioslave.h b/src/ioslave/ioslave.h index cfe9512..c4f9ced 100644 --- a/src/ioslave/ioslave.h +++ b/src/ioslave/ioslave.h @@ -1,92 +1,92 @@ /*************************************************************************** * Copyright (C) 2016 by Arnav Dhamija * * * * This program 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 2 of the License, or * * (at your option) any later version. * * * * This program 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. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * ***************************************************************************/ -#ifndef KIO_FILESTASH_H -#define KIO_FILESTASH_H +#ifndef IOSLAVE_H +#define IOSLAVE_H #include #include class FileStash : public KIO::ForwardingSlaveBase { Q_OBJECT public: FileStash(const QByteArray &pool, const QByteArray &app, const QString daemonService = "org.kde.kio.StashNotifier", const QString daemonPath = "/StashNotifier"); ~FileStash(); enum NodeType { DirectoryNode, SymlinkNode, FileNode, InvalidNode }; struct dirList { QString filePath; QString source; FileStash::NodeType type; dirList() {} ~dirList() {} dirList(const dirList &obj) { filePath = obj.filePath; source = obj.source; type = obj.type; } }; private: void createTopLevelDirEntry(KIO::UDSEntry &entry); bool isRoot(const QString &string); bool statUrl(const QUrl &url, KIO::UDSEntry &entry); bool createUDSEntry( KIO::UDSEntry &entry, const FileStash::dirList &fileItem); bool copyFileToStash(const QUrl &src, const QUrl &dest, KIO::JobFlags flags); bool copyStashToFile(const QUrl &src, const QUrl &dest, KIO::JobFlags flags); bool copyStashToStash(const QUrl &src, const QUrl &dest, KIO::JobFlags flags); bool deletePath(const QUrl &src); QStringList setFileList(const QUrl &url); QString setFileInfo(const QUrl &url); FileStash::dirList createDirListItem(QString fileInfo); const QString m_daemonService; const QString m_daemonPath; protected: void listDir(const QUrl &url) Q_DECL_OVERRIDE; void copy(const QUrl &src, const QUrl &dest, int permissions, KIO::JobFlags flags) Q_DECL_OVERRIDE; void mkdir(const QUrl &url, int permissions) Q_DECL_OVERRIDE; bool rewriteUrl(const QUrl &url, QUrl &newUrl) Q_DECL_OVERRIDE; void del(const QUrl &url, bool isFile) Q_DECL_OVERRIDE; void stat(const QUrl &url) Q_DECL_OVERRIDE; void rename(const QUrl &src, const QUrl &dest, KIO::JobFlags flags) Q_DECL_OVERRIDE; }; #endif