db/update/InotifyUpdate: obey .mpdignore files

Closes https://github.com/MusicPlayerDaemon/MPD/issues/846
This commit is contained in:
Max Kellermann 2020-09-16 20:47:47 +02:00
parent e8213220e2
commit e113ce9621
2 changed files with 31 additions and 2 deletions

2
NEWS
View File

@ -1,4 +1,6 @@
ver 0.21.26 (not yet released) ver 0.21.26 (not yet released)
* database
- inotify: obey ".mpdignore" files
* output * output
- osx: fix crash bug - osx: fix crash bug
- sles: support floating point samples - sles: support floating point samples

View File

@ -21,11 +21,15 @@
#include "InotifySource.hxx" #include "InotifySource.hxx"
#include "InotifyQueue.hxx" #include "InotifyQueue.hxx"
#include "InotifyDomain.hxx" #include "InotifyDomain.hxx"
#include "ExcludeList.hxx"
#include "storage/StorageInterface.hxx" #include "storage/StorageInterface.hxx"
#include "input/InputStream.hxx"
#include "input/Error.hxx"
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/DirectoryReader.hxx" #include "fs/DirectoryReader.hxx"
#include "fs/FileInfo.hxx" #include "fs/FileInfo.hxx"
#include "fs/Traits.hxx" #include "fs/Traits.hxx"
#include "thread/Mutex.hxx"
#include "util/Compiler.h" #include "util/Compiler.h"
#include "Log.hxx" #include "Log.hxx"
@ -52,6 +56,8 @@ struct WatchDirectory {
int descriptor; int descriptor;
ExcludeList exclude_list;
std::forward_list<WatchDirectory> children; std::forward_list<WatchDirectory> children;
template<typename N> template<typename N>
@ -64,11 +70,14 @@ struct WatchDirectory {
WatchDirectory(WatchDirectory &_parent, N &&_name, WatchDirectory(WatchDirectory &_parent, N &&_name,
int _descriptor) int _descriptor)
:parent(&_parent), name(std::forward<N>(_name)), :parent(&_parent), name(std::forward<N>(_name)),
descriptor(_descriptor) {} descriptor(_descriptor),
exclude_list(_parent.exclude_list) {}
WatchDirectory(const WatchDirectory &) = delete; WatchDirectory(const WatchDirectory &) = delete;
WatchDirectory &operator=(const WatchDirectory &) = delete; WatchDirectory &operator=(const WatchDirectory &) = delete;
void LoadExcludeList(Path directory_path) noexcept;
gcc_pure gcc_pure
unsigned GetDepth() const noexcept; unsigned GetDepth() const noexcept;
@ -76,6 +85,18 @@ struct WatchDirectory {
AllocatedPath GetUriFS() const noexcept; AllocatedPath GetUriFS() const noexcept;
}; };
void
WatchDirectory::LoadExcludeList(Path directory_path) noexcept
try {
Mutex mutex;
auto is = InputStream::OpenReady((directory_path / Path::FromFS(".mpdignore")).c_str(),
mutex);
exclude_list.Load(std::move(is));
} catch (...) {
if (!IsFileNotFound(std::current_exception()))
LogError(std::current_exception());
}
static InotifySource *inotify_source; static InotifySource *inotify_source;
static InotifyQueue *inotify_queue; static InotifyQueue *inotify_queue;
@ -163,7 +184,8 @@ SkipFilename(Path name) noexcept
static void static void
recursive_watch_subdirectories(WatchDirectory &parent, recursive_watch_subdirectories(WatchDirectory &parent,
const AllocatedPath &path_fs, unsigned depth) const AllocatedPath &path_fs,
unsigned depth)
try { try {
assert(depth <= inotify_max_depth); assert(depth <= inotify_max_depth);
assert(!path_fs.IsNull()); assert(!path_fs.IsNull());
@ -181,6 +203,9 @@ try {
if (SkipFilename(name_fs)) if (SkipFilename(name_fs))
continue; continue;
if (parent.exclude_list.Check(name_fs))
continue;
const auto child_path_fs = path_fs / name_fs; const auto child_path_fs = path_fs / name_fs;
FileInfo fi; FileInfo fi;
@ -213,6 +238,7 @@ try {
name_fs, name_fs,
ret); ret);
child = &parent.children.front(); child = &parent.children.front();
child->LoadExcludeList(child_path_fs);
tree_add_watch_directory(child); tree_add_watch_directory(child);
@ -317,6 +343,7 @@ mpd_inotify_init(EventLoop &loop, Storage &storage, UpdateService &update,
} }
inotify_root = new WatchDirectory(path, descriptor); inotify_root = new WatchDirectory(path, descriptor);
inotify_root->LoadExcludeList(path);
tree_add_watch_directory(inotify_root); tree_add_watch_directory(inotify_root);