File: File.h

package info (click to toggle)
qtop 2.3.4-4
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 3,976 kB
  • sloc: cpp: 40,477; makefile: 7
file content (331 lines) | stat: -rw-r--r-- 8,197 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
#ifndef File_h
#define File_h

/******************************************************************************
*
* Copyright (C) 2002 Hugo PEREIRA <mailto: hugo.pereira@free.fr>
*
* This 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 software 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, see <http://www.gnu.org/licenses/>.
*
*******************************************************************************/

#include "TimeStamp.h"

#include <QFileInfo>
#include <QList>
#include <QString>
#include <QTextStream>

//* file manipulation utility
class File
{

    public:

    //* shortcut to list of files
    using List=QList<File>;

    //* return list of files in a directory
    enum ListFlag
    {
        None = 0,
        Recursive = 1<<0,
        FollowLinks = 1<<1,
        ShowHiddenFiles = 1<<2
    };

    Q_DECLARE_FLAGS(ListFlags, ListFlag)

    //* universal constructor
    template<typename... Args>
    explicit File(Args&&... args):
        value_( std::forward<Args>(args)... )
    {}

    //* destructor
    virtual ~File() = default;

    //*@name accessors
    //@{

    //* convert to string
    operator const QString& () const { return value_; }

    //* accessor
    const QString& get() const { return value_; }

    template<class T>
        bool startsWith( const T& t ) const
    { return value_.startsWith( t ); }

    template<class T>
        bool endsWith( const T& t ) const
    { return value_.endsWith( t ); }

    template<typename... Args>
        bool contains( Args&&... args ) const
    { return value_.contains( args... ); }

    //* true if empty
    bool isEmpty() const { return value_.isEmpty(); }

    //* returns true if file has absolute pathname
    bool isAbsolute() const
    { return isAbsolute( value_ ); }

    //* time of file creation
    TimeStamp created() const;

    //* time of file last modification
    TimeStamp lastModified() const;

    //* time of file last access
    TimeStamp lastAccessed() const;

    //* user id
    uint userId() const;

    //* group id
    uint groupId() const;

    //* user name
    QString userName() const;

    //* group name
    QString groupName() const;

    //* permissions
    QFile::Permissions permissions() const;

    //* permission string
    QString permissionsString() const
    { return permissionsString( permissions() ); }

    //* permission string
    QString permissionsString( const QFile::Permissions& ) const;

    //* file size
    qint64 fileSize() const;

    //* file size (string version)
    QString sizeString() const
    { return sizeString( fileSize() ); }

    //* file size (string version)
    static QString sizeString( qint64 );

    //* raw file size
    static QString rawSizeString( qint64 );

    //* tells if a file exists
    bool exists() const;

    //* tells if a file exists and can be written into
    bool isWritable() const;

    //* tells if a file exists and can be written into
    bool isReadOnly() const
    { return !isWritable(); }

    //* tells if a file exists and is a directory
    bool isDirectory() const;

    //* tells if a file is hidden
    bool isHidden() const;

    //* tells if a file is a symbolic link
    bool isLink() const;

    //* tells if a file is a broken symbolic link
    bool isBrokenLink() const;

    //* returns true if two file differs
    bool diff( const File& ) const;

    //* returns true if file is the same as argument
    /*
    this is a literal string comparison for files.
    for pathnames, the trailing backslash is ignored
    */
    bool isEqual( const File& ) const;

    //* get path associated to full name
    File path( bool absolute = true ) const;

    //* remove path from full name
    File localName() const;

    //* return canonical name (follow links and remove ".." and ".")
    File canonicalName() const;

    //* get file extension
    File extension() const;

    //* get truncated file (no extension)
    File truncatedName() const;

    //* return first file with matching short name, or empty string if not found
    /** search recursively in this directory and subdirectories */
    File find( const File& file, bool = true ) const;

    //* find file matching this (assuming short name) in list of directries or empty if not found
    File find( const List& ) const;

    //* return list of files in a directory
    List listFiles( ListFlags flags ) const;

    //* expand a file name replacing .. or ~ to full path
    File expanded() const
    { return File(*this).expand(); }

    //@}

    //*@name modifiers
    //@{

    //* accessor
    QString& get() { return value_; }

    //* clear
    void clear() { value_.clear(); }

    //* try create
    bool create() const;

    //* try create directory
    bool createDirectory( const File& = File(".") ) const;

    //* set file as hidden (WIN32 only)
    void setHidden() const;

    //* returns a versioned filename
    /** (add _i at the end with i the first integer for which file is not found) */
    File version() const;

    //* make a backup copy (terminated by ~) of a file, returns backup file
    File backup() const;

    //* return link destination file
    File readLink() const;

    //* removes file from disk
    /**
    returns true if the file does not exists
    or was successfully removed
    */
    bool remove() const;

    //* removes directory from disk, recursively
    bool removeRecursive() const;

    //* rename file
    /** returns true if the file exists and was renamed */
    bool rename( const File& ) const;

    //* copy
    bool copy( const File&, bool = false ) const;

    //* adds path to a file
    /** note: the file is taken raw. No truncation/expension performed.*/
    File& addPath( const File& path, bool absolute = false )
    {
        addPath( value_, path, absolute );
        return *this;
    }

    //* expand a file name replacing .. or ~ to full path
    File& expand()
    {
        expand( value_ );
        return *this;
    }

    //* add trailing slash
    File& addTrailingSlash()
    { addTrailingSlash( value_ ); return *this; }

    //* remove trailing slash
    File& removeTrailingSlash()
    { removeTrailingSlash( value_ ); return *this; }

    //@}

    //*@name utilities
    //@{

    static bool isAbsolute( const QString& );
    static void expand( QString& );
    static void addTrailingSlash( QString& );
    static void removeTrailingSlash( QString& );
    static void addPath( QString& file, const QString& path, bool absolute = false );

    //@}

    //* used to find files pointing to the same link
    class SameLinkFTor
    {

        public:

        //* constructor
        explicit SameLinkFTor( const File& file ):
            file_( file.readLink() )
        {}

        //* predicate
        bool operator() ( const File& file ) const
        { return file.readLink().get() == file_; }

        private:

        //* predicted file
        QString file_;

    };

    //* streamer
    friend QTextStream& operator >> ( QTextStream& in, File& file )
    {
        in >> file.value_;
        return in;
    }

    //* streamer
    friend QTextStream& operator >> ( QTextStream& out, const File& file )
    {
        out << file.value_;
        return out;
    }

    private:

    //* value
    QString value_;

};

//* less than operator
inline bool operator < (const File& first, const File& second)
{ return first.get() < second.get(); }

//* equal to operator
inline bool operator == (const File& first, const File& second)
{ return first.get() == second.get(); }

// specialized copy constructor
template<> File::File<File&>( File& );
template<> File::File<const File&>( const File& );

Q_DECLARE_OPERATORS_FOR_FLAGS( File::ListFlags )
#endif