1 /* 2 SPDX-FileCopyrightText: 2007 Henrique Pinto <henrique.pinto@kdemail.net> 3 SPDX-FileCopyrightText: 2008-2009 Harald Hvaal <haraldhv@stud.ntnu.no> 4 SPDX-FileCopyrightText: 2009-2012 Raphael Kubo da Costa <rakuco@FreeBSD.org> 5 SPDX-FileCopyrightText: 2016 Vladyslav Batyrenko <mvlabat@gmail.com> 6 7 SPDX-License-Identifier: BSD-2-Clause 8 */ 9 10 #ifndef ARCHIVEINTERFACE_H 11 #define ARCHIVEINTERFACE_H 12 13 #include "archive_kerfuffle.h" 14 #include "kerfuffle_export.h" 15 #include "archiveentry.h" 16 17 #include <KPluginMetaData> 18 19 #include <QObject> 20 #include <QStringList> 21 #include <QString> 22 #include <QVariantList> 23 24 namespace Kerfuffle 25 { 26 class Query; 27 28 enum { 29 PossiblyMaliciousArchiveError = KJob::UserDefinedError + 1, 30 DestinationNotWritableError 31 }; 32 33 34 class KERFUFFLE_EXPORT ReadOnlyArchiveInterface: public QObject 35 { 36 Q_OBJECT 37 public: 38 explicit ReadOnlyArchiveInterface(QObject *parent, const QVariantList &args); 39 ~ReadOnlyArchiveInterface() override; 40 41 /** 42 * Returns the filename of the archive currently being handled. 43 */ 44 QString filename() const; 45 46 /** 47 * Returns the comment of the archive. 48 */ 49 QString comment() const; 50 51 /** 52 * @return The password of the archive, if any. 53 */ 54 QString password() const; 55 56 bool isMultiVolume() const; 57 int numberOfVolumes() const; 58 59 /** 60 * Returns whether the file can only be read. 61 * 62 * @return @c true The file cannot be written. 63 * @return @c false The file can be read and written. 64 */ 65 virtual bool isReadOnly() const; 66 67 virtual bool open(); 68 69 /** 70 * List archive contents. 71 * This runs the process of reading archive contents. 72 * When subclassing, you can block as long as you need (unless you called setWaitForFinishedSignal(true)). 73 * @returns whether the listing succeeded. 74 * @note If returning false, make sure to emit the error() signal beforewards to notify 75 * the user of the error condition. 76 */ 77 virtual bool list() = 0; 78 virtual bool testArchive() = 0; 79 void setPassword(const QString &password); 80 void setHeaderEncryptionEnabled(bool enabled); 81 82 /** 83 * Extracts the given @p files to the given @p destinationDirectory. 84 * If @p files is empty, the whole archive will be extracted. 85 * When subclassing, you can block as long as you need (unless you called setWaitForFinishedSignal(true)). 86 * @returns whether the extraction succeeded. 87 * @note If returning false, make sure to emit the error() signal beforewards to notify 88 * the user of the error condition. 89 */ 90 virtual bool extractFiles(const QVector<Archive::Entry*> &files, const QString &destinationDirectory, const ExtractionOptions &options) = 0; 91 92 /** 93 * @return Whether the plugins do NOT run the functions in their own thread. 94 * @see setWaitForFinishedSignal() 95 */ 96 bool waitForFinishedSignal(); 97 98 /** 99 * Returns count of required finish signals for a job to be finished. 100 * 101 * These two methods are used by move and copy jobs, which in some plugins implementations have to call 102 * several processes sequentially. For instance, moving entries in zip archive is only possible if 103 * extracting the entries, deleting them, recreating destination folder structure and adding them back again. 104 */ 105 virtual int moveRequiredSignals() const; 106 virtual int copyRequiredSignals() const; 107 108 /** 109 * Returns the list of filenames retrieved from the list of entries. 110 */ 111 static QStringList entryFullPaths(const QVector<Archive::Entry*> &entries, PathFormat format = WithTrailingSlash); 112 113 /** 114 * Returns the list of the entries, excluding their children. 115 * 116 * This method relies on entries paths so doesn't require parents to be set. 117 */ 118 static QVector<Archive::Entry*> entriesWithoutChildren(const QVector<Archive::Entry*> &entries); 119 120 /** 121 * Returns the string list of entry paths, which will be a result of adding/moving/copying entries. 122 * 123 * @param entries The entries which will be added/moved/copied. 124 * @param destination Destination path within the archive to which entries have to be added. For renaming an entry 125 * the path has to contain a new filename too. 126 * @param entriesWithoutChildren Entries count, excluding their children. For AddJob or CopyJob 0 MUST be passed. 127 * 128 * @return For entries 129 * some/dir/ 130 * some/dir/entry 131 * some/dir/some/entry 132 * some/another/entry 133 * and destination 134 * some/destination 135 * will return 136 * some/destination/dir/ 137 * some/destination/dir/entry 138 * some/destination/dir/some/enty 139 * some/destination/entry 140 */ 141 static QStringList entryPathsFromDestination(QStringList entries, const Archive::Entry *destination, int entriesWithoutChildren); 142 143 /** 144 * @return true if the interface has killed the job. 145 * Otherwise returns false if the interface is not able to instantly kill the operation. 146 */ 147 virtual bool doKill(); 148 149 bool isHeaderEncryptionEnabled() const; 150 virtual QString multiVolumeName() const; 151 void setMultiVolume(bool value); 152 uint numberOfEntries() const; 153 QMimeType mimetype() const; 154 155 /** 156 * @return Whether the interface supports progress reporting for BatchExtractJobs. 157 */ 158 virtual bool hasBatchExtractionProgress() const; 159 160 /** 161 * @return Whether the archive is locked (RAR feature). 162 */ 163 virtual bool isLocked() const; 164 165 Q_SIGNALS: 166 167 /** 168 * Emitted when the user cancels the operation. Examples: 169 * - the user cancels the password dialog 170 * - the user cancels the overwrite dialog 171 */ 172 void cancelled(); 173 void error(const QString &message, const QString &details = QString(), int errorCode = KJob::UserDefinedError); 174 void entry(Archive::Entry *archiveEntry); 175 void progress(double progress); 176 void info(const QString &info); 177 void finished(bool result); 178 void testSuccess(); 179 void compressionMethodFound(const QString &method); 180 void encryptionMethodFound(const QString &method); 181 182 /** 183 * Emitted when @p query needs to be executed on the GUI thread. 184 */ 185 void userQuery(Kerfuffle::Query *query); 186 187 protected: 188 189 /** 190 * Setting this option to true will NOT run the functions in their own thread. 191 * Instead it will be necessary to call finished(bool) when the operation is actually finished. 192 */ 193 void setWaitForFinishedSignal(bool value); 194 195 void setCorrupt(bool isCorrupt); 196 bool isCorrupt() const; 197 QString m_comment; 198 int m_numberOfVolumes; 199 uint m_numberOfEntries; 200 KPluginMetaData m_metaData; 201 202 private: 203 QString m_filename; 204 QMimeType m_mimetype; 205 QString m_password; 206 bool m_waitForFinishedSignal; 207 bool m_isHeaderEncryptionEnabled; 208 bool m_isCorrupt; 209 bool m_isMultiVolume; 210 211 private Q_SLOTS: 212 void onEntry(Archive::Entry *archiveEntry); 213 }; 214 215 class KERFUFFLE_EXPORT ReadWriteArchiveInterface: public ReadOnlyArchiveInterface 216 { 217 Q_OBJECT 218 public: 219 enum OperationMode { 220 NoOperation, 221 List, 222 Extract, 223 Add, 224 Move, 225 Copy, 226 Delete, 227 Comment, 228 Test 229 }; 230 231 explicit ReadWriteArchiveInterface(QObject *parent, const QVariantList &args); 232 ~ReadWriteArchiveInterface() override; 233 234 bool isReadOnly() const override; 235 236 /** 237 * Adds the given @p files under the given @p destination. 238 * If @p destination is null, the files will be added under the root of the archive. 239 * @param options The compression options that must be respected. 240 * @param numberOfEntriesToAdd The total number of entries the will be added. 241 * @return Whether the operation succeeded. 242 * @note If returning false, make sure to emit the error() signal beforewards to notify 243 * the user of the error condition. 244 */ 245 virtual bool addFiles(const QVector<Archive::Entry*> &files, const Archive::Entry *destination, const CompressionOptions& options, uint numberOfEntriesToAdd = 0) = 0; 246 virtual bool moveFiles(const QVector<Archive::Entry*> &files, Archive::Entry *destination, const CompressionOptions& options) = 0; 247 virtual bool copyFiles(const QVector<Archive::Entry*> &files, Archive::Entry *destination, const CompressionOptions& options) = 0; 248 virtual bool deleteFiles(const QVector<Archive::Entry*> &files) = 0; 249 virtual bool addComment(const QString &comment) = 0; 250 251 Q_SIGNALS: 252 void entryRemoved(const QString &path); 253 254 protected: 255 OperationMode m_operationMode = NoOperation; 256 257 private Q_SLOTS: 258 void onEntryRemoved(const QString &path); 259 }; 260 261 } // namespace Kerfuffle 262 263 #endif // ARCHIVEINTERFACE_H 264