Skip to content

Commit a2cf966

Browse files
committed
fix: Enhance file monitoring capabilities
- Added functionality to monitor newly created directories and handle pending directories. - Implemented parent directory monitoring for non-existing paths. - Improved logging for directory changes and monitoring status. Log: Enhance file monitoring capabilities Bug: https://pms.uniontech.com/bug-view-327673.html
1 parent dc76f02 commit a2cf966

File tree

3 files changed

+150
-26
lines changed

3 files changed

+150
-26
lines changed

src/src/fileMonitor/fileinotify.cpp

Lines changed: 142 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ FileInotify::FileInotify(QObject *parent)
2626
, m_Supported(LibUnionImage_NameSpace::unionImageSupportFormat() + LibUnionImage_NameSpace::videoFiletypes()) //图片+视频
2727
{
2828
qDebug() << "Initializing FileInotify with supported formats:" << m_Supported;
29-
29+
3030
for (auto &eachData : m_Supported) {
3131
eachData = eachData.toUpper();
3232
}
@@ -35,8 +35,12 @@ FileInotify::FileInotify(QObject *parent)
3535
connect(m_timer, &QTimer::timeout, this, &FileInotify::onNeedSendPictures);
3636

3737
connect(&m_watcher, &QFileSystemWatcher::directoryChanged, this, [this](const QString & path) {
38-
Q_UNUSED(path)
39-
qDebug() << "Directory change detected, starting timer";
38+
qDebug() << "Directory change detected in:" << path;
39+
40+
// 检查是否有待创建的目录已经被创建
41+
checkPendingDirectories(path);
42+
43+
// 启动定时器处理其他变化
4044
m_timer->start(500);
4145
});
4246
}
@@ -50,6 +54,8 @@ FileInotify::~FileInotify()
5054
void FileInotify::checkNewPath()
5155
{
5256
qDebug() << "Checking for new paths in monitored directories";
57+
58+
// 检查现有监控目录的子目录
5359
for (const auto &currentDir : m_currentDirs) {
5460
QDir dir(currentDir);
5561
QFileInfoList list;
@@ -61,19 +67,72 @@ void FileInotify::checkNewPath()
6167
});
6268

6369
if (!dirs.isEmpty()) {
64-
qDebug() << "Adding new directories to watch:" << dirs;
70+
qDebug() << "Adding new subdirectories to watch:" << dirs;
6571
m_watcher.addPaths(dirs);
6672
}
6773
}
74+
75+
// 检查待创建目录是否已经存在
76+
QStringList newlyCreatedDirs;
77+
for (const QString &pendingDir : m_pendingDirs) {
78+
QFileInfo pendingInfo(pendingDir);
79+
if (pendingInfo.exists() && pendingInfo.isDir()) {
80+
newlyCreatedDirs.append(pendingDir);
81+
qInfo() << "Pending directory now exists:" << pendingDir;
82+
}
83+
}
84+
85+
// 为新创建的目录设置直接监听
86+
for (const QString &newDir : newlyCreatedDirs) {
87+
checkPendingDirectories(QFileInfo(newDir).absolutePath());
88+
}
6889
}
6990

7091
void FileInotify::addWather(const QStringList &paths, const QString &album, int UID)
7192
{
7293
qDebug() << "Adding watch for paths:" << paths << "Album:" << album << "UID:" << UID;
73-
m_currentDirs = paths;
94+
7495
m_currentAlbum = album;
7596
m_currentUID = UID;
76-
m_watcher.addPaths(paths);
97+
98+
// 分类路径:存在的和不存在的
99+
QStringList existingPaths;
100+
QStringList nonExistingPaths;
101+
102+
for (const QString &path : paths) {
103+
QFileInfo info(path);
104+
if (info.exists() && info.isDir()) {
105+
existingPaths.append(path);
106+
} else {
107+
nonExistingPaths.append(path);
108+
qDebug() << "Path does not exist, will try parent monitoring:" << path;
109+
}
110+
}
111+
112+
// 设置当前监控的直接路径
113+
m_currentDirs = existingPaths;
114+
115+
// 为存在的路径添加直接监听
116+
if (!existingPaths.isEmpty()) {
117+
m_watcher.addPaths(existingPaths);
118+
qDebug() << "Added direct monitoring for existing paths:" << existingPaths;
119+
}
120+
121+
// 为不存在的路径设置父级监听
122+
for (const QString &path : nonExistingPaths) {
123+
QFileInfo pathInfo(path);
124+
QString parentPath = pathInfo.absolutePath();
125+
QFileInfo parentInfo(parentPath);
126+
127+
if (parentInfo.exists() && parentInfo.isDir()) {
128+
addParentWatcher(parentPath, path);
129+
m_pendingDirs.append(path);
130+
qDebug() << "Added parent monitoring for non-existing path:" << path << "parent:" << parentPath;
131+
} else {
132+
qWarning() << "Cannot monitor path, parent directory does not exist:" << path << "parent:" << parentPath;
133+
}
134+
}
135+
77136
m_timer->start(1500);
78137
}
79138

@@ -94,8 +153,13 @@ void FileInotify::clear()
94153
qDebug() << "Clearing FileInotify state";
95154
m_Supported.clear();
96155
m_newFile.clear();
97-
m_Supported.clear();
98-
if (m_timer->isActive()) {
156+
m_deleteFile.clear();
157+
m_currentDirs.clear();
158+
m_pendingDirs.clear();
159+
m_parentDirs.clear();
160+
m_parentToChildren.clear();
161+
162+
if (m_timer && m_timer->isActive()) {
99163
m_timer->stop();
100164
delete m_timer;
101165
m_timer = nullptr;
@@ -195,7 +259,7 @@ void FileInotify::onNeedSendPictures()
195259

196260
//发送导入
197261
if (!m_newFile.isEmpty() || !m_deleteFile.isEmpty()) {
198-
qInfo() << "Emitting monitor changed signal - New files:" << m_newFile.size()
262+
qInfo() << "Emitting monitor changed signal - New files:" << m_newFile.size()
199263
<< "Deleted files:" << m_deleteFile.size();
200264
emit sigMonitorChanged(m_newFile, m_deleteFile, m_currentAlbum, m_currentUID);
201265

@@ -216,3 +280,72 @@ void FileInotify::onNeedSendPictures()
216280

217281
m_timer->stop();
218282
}
283+
284+
void FileInotify::addParentWatcher(const QString &parentPath, const QString &targetChild)
285+
{
286+
qDebug() << "Adding parent watcher for:" << parentPath << "target child:" << targetChild;
287+
288+
// 检查是否已经监听了这个父级目录
289+
if (!m_parentDirs.contains(parentPath)) {
290+
m_parentDirs.append(parentPath);
291+
m_watcher.addPath(parentPath);
292+
qDebug() << "Started monitoring parent directory:" << parentPath;
293+
}
294+
295+
// 建立父级目录到子目录的映射
296+
if (!m_parentToChildren.contains(parentPath)) {
297+
m_parentToChildren[parentPath] = QStringList();
298+
}
299+
300+
if (!m_parentToChildren[parentPath].contains(targetChild)) {
301+
m_parentToChildren[parentPath].append(targetChild);
302+
qDebug() << "Added target child mapping:" << parentPath << "->" << targetChild;
303+
}
304+
}
305+
306+
void FileInotify::checkPendingDirectories(const QString &changedPath)
307+
{
308+
qDebug() << "Checking pending directories for changed path:" << changedPath;
309+
310+
// 检查是否有待创建的目录位于变化的路径下
311+
QStringList foundDirs;
312+
for (const QString &pendingDir : m_pendingDirs) {
313+
QFileInfo pendingInfo(pendingDir);
314+
315+
// 如果待创建目录的父级路径就是变化的路径,并且现在已经存在
316+
if (pendingInfo.absolutePath() == changedPath && pendingInfo.exists() && pendingInfo.isDir()) {
317+
foundDirs.append(pendingDir);
318+
qInfo() << "Found newly created target directory:" << pendingDir;
319+
}
320+
}
321+
322+
// 为新创建的目录添加直接监听
323+
for (const QString &foundDir : foundDirs) {
324+
// 从待创建列表中移除
325+
m_pendingDirs.removeAll(foundDir);
326+
327+
// 添加到当前监控目录列表
328+
m_currentDirs.append(foundDir);
329+
330+
// 添加直接监听
331+
m_watcher.addPath(foundDir);
332+
qInfo() << "Added direct monitoring for newly created directory:" << foundDir;
333+
334+
// 检查是否可以移除父级监听
335+
QString parentPath = QFileInfo(foundDir).absolutePath();
336+
if (m_parentToChildren.contains(parentPath)) {
337+
m_parentToChildren[parentPath].removeAll(foundDir);
338+
339+
// 如果这个父级目录不再需要监听其他子目录,移除父级监听
340+
if (m_parentToChildren[parentPath].isEmpty()) {
341+
m_parentToChildren.remove(parentPath);
342+
m_parentDirs.removeAll(parentPath);
343+
m_watcher.removePath(parentPath);
344+
qDebug() << "Removed parent monitoring for:" << parentPath;
345+
}
346+
}
347+
348+
// 触发新路径检查以监听该目录下的子目录
349+
m_timer->start(500);
350+
}
351+
}

src/src/fileMonitor/fileinotify.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,11 +41,18 @@ public slots:
4141
private:
4242
//检查是否新建了子文件夹
4343
void checkNewPath();
44+
//检查待创建的目录是否已经创建
45+
void checkPendingDirectories(const QString &changedPath);
46+
//添加父级目录监听
47+
void addParentWatcher(const QString &parentPath, const QString &targetChild);
4448

4549
bool m_running = false;
4650
QStringList m_newFile; //当前新添加的
4751
QStringList m_deleteFile; //当前删除的
4852
QStringList m_currentDirs; //给定的当前监控路径
53+
QStringList m_pendingDirs; //等待创建的目标目录
54+
QStringList m_parentDirs; //当前监听的父级目录
55+
QMap<QString, QStringList> m_parentToChildren; //父级目录到子目录的映射
4956
QString m_currentAlbum; //给定当前的相册
5057
int m_currentUID; //给定当前的相册的UID
5158
QStringList m_Supported; //支持的格式

src/src/fileMonitor/fileinotifygroup.cpp

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -18,25 +18,9 @@ FileInotifyGroup::FileInotifyGroup(QObject *parent) : QObject(parent)
1818
void FileInotifyGroup::startWatch(const QStringList &paths, const QString &album, int UID)
1919
{
2020
qDebug() << "Starting watch for album:" << album << "UID:" << UID << "with paths:" << paths;
21-
22-
//去除不存在的路径
23-
QStringList watchPaths;
24-
for (const auto &path : paths) {
25-
QFileInfo info(path);
26-
if (info.exists() && info.isDir()) {
27-
watchPaths.push_back(path);
28-
} else {
29-
qWarning() << "Path does not exist or is not a directory, skipping:" << path;
30-
}
31-
}
32-
if (watchPaths.isEmpty()) {
33-
qWarning() << "No valid paths to watch for album:" << album << "UID:" << UID;
34-
return;
35-
}
36-
3721
//启动监控
3822
auto watcher = new FileInotify;
39-
watcher->addWather(watchPaths, album, UID);
23+
watcher->addWather(paths, album, UID);
4024

4125
//原cpp为signal发送的全局信号,现在改为传递的方法,发送回albumControl
4226
connect(watcher, &FileInotify::sigMonitorChanged, this, &FileInotifyGroup::sigMonitorChanged);

0 commit comments

Comments
 (0)