| 258 | } |
| 259 | |
| 260 | bool SystemRemoteDataPathsSource::nextFile() |
| 261 | { |
| 262 | while (true) |
| 263 | { |
| 264 | while (!paths_stack.empty()) |
| 265 | { |
| 266 | auto & current = paths_stack.back(); |
| 267 | ++current.position; |
| 268 | /// Move to the next child in the current directory |
| 269 | if (current.position < static_cast<ssize_t>(current.names.size())) |
| 270 | break; |
| 271 | /// Move up to the parent directory if this was the last child |
| 272 | paths_stack.pop_back(); |
| 273 | } |
| 274 | |
| 275 | /// Done with the current disk? |
| 276 | if (paths_stack.empty()) |
| 277 | return false; |
| 278 | |
| 279 | const auto current_path = getCurrentPath(); |
| 280 | |
| 281 | try |
| 282 | { |
| 283 | const auto & disk = disks[current_disk].second; |
| 284 | |
| 285 | /// Stop if current path is a file |
| 286 | if (disk->existsFile(current_path)) |
| 287 | return true; |
| 288 | |
| 289 | /// Files or directories can disappear due to concurrent operations |
| 290 | if (!disk->existsFileOrDirectory(current_path)) |
| 291 | continue; |
| 292 | |
| 293 | /// If current path is a directory list its contents and step into it |
| 294 | std::vector<std::string> children; |
| 295 | disk->listFiles(current_path, children); |
| 296 | |
| 297 | /// Use current predicate for all children |
| 298 | const auto & skip_predicate = getCurrentSkipPredicate(); |
| 299 | DirListingAndPosition dir; |
| 300 | for (const auto & child : children) |
| 301 | dir.names.push_back({child, skip_predicate}); |
| 302 | dir.position = -1; |
| 303 | |
| 304 | paths_stack.emplace_back(std::move(dir)); |
| 305 | } |
| 306 | catch (const Exception & e) |
| 307 | { |
| 308 | /// Files or directories can disappear due to concurrent operations |
| 309 | if (e.code() == ErrorCodes::FILE_DOESNT_EXIST || |
| 310 | e.code() == ErrorCodes::DIRECTORY_DOESNT_EXIST) |
| 311 | continue; |
| 312 | |
| 313 | throw; |
| 314 | } |
| 315 | catch (const fs::filesystem_error & e) |
| 316 | { |
| 317 | /// Files or directories can disappear due to concurrent operations |
no test coverage detected