WatchService: use absolute path in processWatchEvent (#4796)
* WatchService: use absolute path in processWatchEvent Signed-off-by: Jimmy Tanagra <jcode@tanagra.id.au> * update interface and use a consistent name `fullPath` Signed-off-by: Jimmy Tanagra <jcode@tanagra.id.au> --------- Signed-off-by: Jimmy Tanagra <jcode@tanagra.id.au>pull/4798/head
parent
8ff69a3f50
commit
c40c258e04
|
@ -78,8 +78,8 @@ public abstract class AbstractScriptDependencyTracker
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
File file = libraryPath.resolve(path).toFile();
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
File file = fullPath.toFile();
|
||||
if (kind == DELETE || (!file.isHidden() && file.canRead() && (kind == CREATE || kind == MODIFY))) {
|
||||
dependencyChanged(file.toString());
|
||||
}
|
||||
|
|
|
@ -218,13 +218,12 @@ public abstract class AbstractScriptFileWatcher implements WatchService.WatchEve
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
if (!initialized.isDone()) {
|
||||
// discard events if the initial import has not finished
|
||||
return;
|
||||
}
|
||||
|
||||
Path fullPath = watchPath.resolve(path);
|
||||
File file = fullPath.toFile();
|
||||
|
||||
// Subdirectory events are filtered out by WatchService, so we only need to deal with files
|
||||
|
|
|
@ -92,7 +92,7 @@ public class AbstractScriptDependencyTrackerTest {
|
|||
scriptDependencyTracker.addChangeTracker(listener2);
|
||||
|
||||
scriptDependencyTracker.startTracking("scriptId", depPath.toString());
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.CREATE, DEPENDENCY);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.CREATE, depPath);
|
||||
|
||||
verify(listener1).onDependencyChange(eq("scriptId"));
|
||||
verify(listener2).onDependencyChange(eq("scriptId"));
|
||||
|
@ -108,7 +108,7 @@ public class AbstractScriptDependencyTrackerTest {
|
|||
|
||||
scriptDependencyTracker.startTracking("scriptId1", depPath.toString());
|
||||
scriptDependencyTracker.startTracking("scriptId2", depPath.toString());
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.MODIFY, DEPENDENCY);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.MODIFY, depPath);
|
||||
|
||||
verify(listener).onDependencyChange(eq("scriptId1"));
|
||||
verify(listener).onDependencyChange(eq("scriptId2"));
|
||||
|
@ -123,8 +123,8 @@ public class AbstractScriptDependencyTrackerTest {
|
|||
|
||||
scriptDependencyTracker.startTracking("scriptId", depPath.toString());
|
||||
scriptDependencyTracker.startTracking("scriptId", depPath2.toString());
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.MODIFY, DEPENDENCY);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.DELETE, DEPENDENCY2);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.MODIFY, depPath);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.DELETE, depPath2);
|
||||
|
||||
verify(listener, times(2)).onDependencyChange(eq("scriptId"));
|
||||
verifyNoMoreInteractions(listener);
|
||||
|
@ -139,7 +139,7 @@ public class AbstractScriptDependencyTrackerTest {
|
|||
scriptDependencyTracker.startTracking("scriptId1", depPath.toString());
|
||||
scriptDependencyTracker.startTracking("scriptId2", depPath2.toString());
|
||||
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.CREATE, DEPENDENCY);
|
||||
scriptDependencyTracker.processWatchEvent(WatchService.Kind.CREATE, depPath);
|
||||
|
||||
verify(listener).onDependencyChange(eq("scriptId1"));
|
||||
verifyNoMoreInteractions(listener);
|
||||
|
|
|
@ -58,8 +58,7 @@ public class AutomationWatchService implements WatchService.WatchEventListener {
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
Path fullPath = watchingDir.resolve(path);
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
try {
|
||||
if (kind == WatchService.Kind.DELETE) {
|
||||
provider.removeResources(fullPath.toFile());
|
||||
|
|
|
@ -63,8 +63,7 @@ public class ConfigDispatcherFileWatcher implements WatchService.WatchEventListe
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
Path fullPath = watchService.getWatchPath().resolve(SERVICES_FOLDER).resolve(path);
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
try {
|
||||
if (kind == WatchService.Kind.CREATE || kind == WatchService.Kind.MODIFY) {
|
||||
if (!Files.isHidden(fullPath) && fullPath.toString().endsWith(".cfg")) {
|
||||
|
@ -79,7 +78,7 @@ public class ConfigDispatcherFileWatcher implements WatchService.WatchEventListe
|
|||
configDispatcher.fileRemoved(fullPath.toString());
|
||||
}
|
||||
} catch (IOException e) {
|
||||
logger.error("Failed to process watch event {} for {}", kind, path, e);
|
||||
logger.error("Failed to process watch event {} for {}", kind, fullPath, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -49,8 +49,6 @@ public class ConfigDispatcherFileWatcherTest {
|
|||
configDispatcherFileWatcher = new ConfigDispatcherFileWatcher(configDispatcherMock, watchService);
|
||||
verify(configDispatcherMock).processConfigFile(any());
|
||||
|
||||
when(watchService.getWatchPath()).thenReturn(tempDir.toAbsolutePath());
|
||||
|
||||
cfgPath = tempDir.resolve("myPath.cfg");
|
||||
nonCfgPath = tempDir.resolve("myPath");
|
||||
|
||||
|
|
|
@ -59,6 +59,7 @@ import org.slf4j.LoggerFactory;
|
|||
@Component(name = "org.openhab.core.folder", immediate = true, configurationPid = "org.openhab.folder", configurationPolicy = ConfigurationPolicy.REQUIRE)
|
||||
public class FolderObserver implements WatchService.WatchEventListener {
|
||||
private final WatchService watchService;
|
||||
private final Path watchPath;
|
||||
private final Logger logger = LoggerFactory.getLogger(FolderObserver.class);
|
||||
|
||||
/* the model repository is provided as a service */
|
||||
|
@ -88,6 +89,7 @@ public class FolderObserver implements WatchService.WatchEventListener {
|
|||
this.modelRepository = modelRepo;
|
||||
this.readyService = readyService;
|
||||
this.watchService = watchService;
|
||||
this.watchPath = watchService.getWatchPath();
|
||||
}
|
||||
|
||||
@Reference(cardinality = ReferenceCardinality.AT_LEAST_ONE, policy = ReferencePolicy.DYNAMIC)
|
||||
|
@ -127,7 +129,7 @@ public class FolderObserver implements WatchService.WatchEventListener {
|
|||
continue;
|
||||
}
|
||||
|
||||
Path folderPath = watchService.getWatchPath().resolve(folderName);
|
||||
Path folderPath = watchPath.resolve(folderName);
|
||||
if (Files.exists(folderPath) && Files.isDirectory(folderPath)) {
|
||||
String[] validExtensions = ((String) config.get(folderName)).split(",");
|
||||
folderFileExtMap.put(folderName, Set.of(validExtensions));
|
||||
|
@ -191,7 +193,7 @@ public class FolderObserver implements WatchService.WatchEventListener {
|
|||
continue;
|
||||
}
|
||||
|
||||
Path folderPath = watchService.getWatchPath().resolve(folderName);
|
||||
Path folderPath = watchPath.resolve(folderName);
|
||||
logger.debug("Adding files in '{}' to the model", folderPath);
|
||||
try (DirectoryStream<Path> stream = Files.newDirectoryStream(folderPath,
|
||||
new FileExtensionsFilter(validExtensions))) {
|
||||
|
@ -287,7 +289,8 @@ public class FolderObserver implements WatchService.WatchEventListener {
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
Path path = watchPath.relativize(fullPath);
|
||||
if (path.getNameCount() != 2) {
|
||||
logger.trace("{} event for {} ignored (only depth 1 allowed)", kind, path);
|
||||
return;
|
||||
|
@ -310,7 +313,6 @@ public class FolderObserver implements WatchService.WatchEventListener {
|
|||
return;
|
||||
}
|
||||
|
||||
Path resolvedPath = watchService.getWatchPath().resolve(path);
|
||||
checkPath(resolvedPath, kind);
|
||||
checkPath(fullPath, kind);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -90,7 +90,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
|
||||
when(modelParserMock.getExtension()).thenReturn("java");
|
||||
when(contextMock.getProperties()).thenReturn(configProps);
|
||||
when(watchServiceMock.getWatchPath()).thenReturn(WATCHED_DIRECTORY.toPath());
|
||||
when(watchServiceMock.getWatchPath()).thenReturn(WATCHED_DIRECTORY.toPath().toAbsolutePath());
|
||||
|
||||
folderObserver = new FolderObserver(modelRepoMock, readyServiceMock, watchServiceMock);
|
||||
folderObserver.addModelParser(modelParserMock);
|
||||
|
@ -129,7 +129,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
Files.writeString(file.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8, StandardOpenOption.CREATE);
|
||||
|
||||
waitForAssert(() -> assertThat(file.exists(), is(true)));
|
||||
folderObserver.processWatchEvent(CREATE, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(CREATE, file.toPath().toAbsolutePath());
|
||||
|
||||
verify(modelRepoMock).addOrRefreshModel(eq(file.getName()), any());
|
||||
verifyNoMoreInteractions(modelRepoMock);
|
||||
|
@ -154,12 +154,12 @@ public class FolderObserverTest extends JavaTest {
|
|||
Files.writeString(file.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8, StandardOpenOption.CREATE);
|
||||
|
||||
waitForAssert(() -> assertThat(file.exists(), is(true)));
|
||||
folderObserver.processWatchEvent(CREATE, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(CREATE, file.toPath().toAbsolutePath());
|
||||
|
||||
String text = "Additional content";
|
||||
Files.writeString(file.toPath(), text, StandardCharsets.UTF_8, StandardOpenOption.APPEND);
|
||||
|
||||
folderObserver.processWatchEvent(MODIFY, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(MODIFY, file.toPath().toAbsolutePath());
|
||||
|
||||
verify(modelRepoMock, times(2)).addOrRefreshModel(eq(file.getName()), any());
|
||||
verifyNoMoreInteractions(modelRepoMock);
|
||||
|
@ -183,7 +183,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
Files.writeString(file.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8, StandardOpenOption.CREATE);
|
||||
waitForAssert(() -> assertThat(file.exists(), is(true)));
|
||||
|
||||
folderObserver.processWatchEvent(CREATE, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(CREATE, file.toPath().toAbsolutePath());
|
||||
|
||||
verifyNoInteractions(modelRepoMock);
|
||||
}
|
||||
|
@ -203,7 +203,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
File file = new File(EXISTING_SUBDIR_PATH, "NewlyCreatedMockFile.java");
|
||||
Files.writeString(file.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8, StandardOpenOption.CREATE);
|
||||
waitForAssert(() -> assertThat(file.exists(), is(true)));
|
||||
folderObserver.processWatchEvent(CREATE, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(CREATE, file.toPath().toAbsolutePath());
|
||||
|
||||
verifyNoInteractions(modelRepoMock);
|
||||
}
|
||||
|
@ -256,7 +256,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
Files.writeString(file.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8, StandardOpenOption.CREATE);
|
||||
waitForAssert(() -> assertThat(file.exists(), is(true)));
|
||||
|
||||
folderObserver.processWatchEvent(CREATE, WATCHED_DIRECTORY.toPath().relativize(file.toPath()));
|
||||
folderObserver.processWatchEvent(CREATE, file.toPath().toAbsolutePath());
|
||||
|
||||
verifyNoInteractions(modelRepoMock);
|
||||
}
|
||||
|
@ -275,13 +275,11 @@ public class FolderObserverTest extends JavaTest {
|
|||
File mockFileWithValidExt = new File(EXISTING_SUBDIR_PATH, "MockFileForModification." + validExtension);
|
||||
Files.writeString(mockFileWithValidExt.toPath(), INITIAL_FILE_CONTENT, StandardCharsets.UTF_8,
|
||||
StandardOpenOption.CREATE);
|
||||
localFolderObserver.processWatchEvent(CREATE,
|
||||
WATCHED_DIRECTORY.toPath().relativize(mockFileWithValidExt.toPath()));
|
||||
localFolderObserver.processWatchEvent(CREATE, mockFileWithValidExt.toPath().toAbsolutePath());
|
||||
|
||||
Files.writeString(mockFileWithValidExt.toPath(), "Additional content", StandardCharsets.UTF_8,
|
||||
StandardOpenOption.APPEND);
|
||||
localFolderObserver.processWatchEvent(MODIFY,
|
||||
WATCHED_DIRECTORY.toPath().relativize(mockFileWithValidExt.toPath()));
|
||||
localFolderObserver.processWatchEvent(MODIFY, mockFileWithValidExt.toPath().toAbsolutePath());
|
||||
|
||||
verify(modelRepoMock, times(2)).addOrRefreshModel(eq(mockFileWithValidExt.getName()), any());
|
||||
}
|
||||
|
@ -325,7 +323,7 @@ public class FolderObserverTest extends JavaTest {
|
|||
walk.sorted(Comparator.reverseOrder()).map(Path::toFile).forEach(File::delete);
|
||||
}
|
||||
}
|
||||
folderObserver.processWatchEvent(CREATE, Path.of(EXISTING_SUBDIR_PATH.getName(), filename));
|
||||
folderObserver.processWatchEvent(CREATE, Path.of(EXISTING_SUBDIR_PATH.getName(), filename).toAbsolutePath());
|
||||
verifyNoInteractions(modelRepoMock);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -130,8 +130,7 @@ public class YamlModelRepositoryImpl implements WatchService.WatchEventListener,
|
|||
public FileVisitResult visitFile(@NonNullByDefault({}) Path file,
|
||||
@NonNullByDefault({}) BasicFileAttributes attrs) throws IOException {
|
||||
if (attrs.isRegularFile()) {
|
||||
Path relativePath = watchPath.relativize(file);
|
||||
processWatchEvent(CREATE, relativePath);
|
||||
processWatchEvent(CREATE, file);
|
||||
}
|
||||
return FileVisitResult.CONTINUE;
|
||||
}
|
||||
|
@ -156,10 +155,10 @@ public class YamlModelRepositoryImpl implements WatchService.WatchEventListener,
|
|||
// The method is "synchronized" to avoid concurrent files processing
|
||||
@Override
|
||||
@SuppressWarnings({ "rawtypes", "unchecked" })
|
||||
public synchronized void processWatchEvent(Kind kind, Path path) {
|
||||
Path fullPath = watchPath.resolve(path);
|
||||
String modelName = path.toString();
|
||||
if (path.startsWith("automation") || !modelName.endsWith(".yaml")) {
|
||||
public synchronized void processWatchEvent(Kind kind, Path fullPath) {
|
||||
Path relativePath = watchPath.relativize(fullPath);
|
||||
String modelName = relativePath.toString();
|
||||
if (relativePath.startsWith("automation") || !modelName.endsWith(".yaml")) {
|
||||
logger.trace("Ignored {}", fullPath);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -103,8 +103,8 @@ public class YamlModelRepositoryImplTest {
|
|||
modelRepository.addYamlModelListener(secondTypeListener1);
|
||||
modelRepository.addYamlModelListener(secondTypeListener2);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
|
@ -158,8 +158,8 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
modelRepository.addYamlModelListener(secondTypeListener1);
|
||||
|
@ -217,23 +217,23 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
// File in v1 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelFileUpdatePost.yaml"), fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), any());
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modelFileUpdatePre.yaml"), fullModelPath, StandardCopyOption.REPLACE_EXISTING);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, fullModelPath);
|
||||
verify(firstTypeListener, times(2)).addedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener).updatedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener).removedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
|
||||
// File in v2 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelV2FileUpdatePost.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), any());
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modelV2FileUpdatePre.yaml"), fullModel2Path,
|
||||
StandardCopyOption.REPLACE_EXISTING);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, fullModel2Path);
|
||||
verify(firstTypeListener, times(2)).addedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener).updatedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener).removedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
|
@ -282,11 +282,11 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
// File in v1 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelFileUpdatePost.yaml"), fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), any());
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve(v1File), fullModelPath, StandardCopyOption.REPLACE_EXISTING);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, fullModelPath);
|
||||
verify(firstTypeListener).removedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
|
||||
Collection<FirstTypeDTO> firstTypeElements = firstTypeCaptor.getAllValues().getFirst();
|
||||
|
@ -298,11 +298,11 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
// File in v2 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelV2FileUpdatePost.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), any());
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve(v2File), fullModel2Path, StandardCopyOption.REPLACE_EXISTING);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.MODIFY, fullModel2Path);
|
||||
verify(firstTypeListener).removedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
|
||||
assertThat(firstTypeCaptor.getAllValues(), hasSize(2));
|
||||
|
@ -322,8 +322,8 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
// File in v1 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelFileUpdatePost.yaml"), fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.DELETE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.DELETE, fullModelPath);
|
||||
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -331,8 +331,8 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
// File in v2 format
|
||||
Files.copy(SOURCE_PATH.resolve("modelV2FileUpdatePost.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.DELETE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.DELETE, fullModel2Path);
|
||||
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -367,7 +367,7 @@ public class YamlModelRepositoryImplTest {
|
|||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
modelRepository.addYamlModelListener(secondTypeListener1);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
FirstTypeDTO added = new FirstTypeDTO("element3", "description3");
|
||||
modelRepository.addElementToModel(MODEL_NAME, added);
|
||||
|
@ -388,7 +388,7 @@ public class YamlModelRepositoryImplTest {
|
|||
assertThat(yaml.load(actualFileContent), equalTo(yaml.load(expectedFileContent)));
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modifyModelV2InitialContent.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
modelRepository.addElementToModel(MODEL2_NAME, added);
|
||||
modelRepository.addElementToModel(MODEL2_NAME, added2);
|
||||
verify(firstTypeListener, times(2)).addedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
|
@ -424,7 +424,7 @@ public class YamlModelRepositoryImplTest {
|
|||
|
||||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
FirstTypeDTO updated = new FirstTypeDTO("element1", "newDescription1");
|
||||
modelRepository.updateElementInModel(MODEL_NAME, updated);
|
||||
|
@ -440,7 +440,7 @@ public class YamlModelRepositoryImplTest {
|
|||
assertThat(yaml.load(actualFileContent), equalTo(yaml.load(expectedFileContent)));
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modifyModelV2InitialContent.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
modelRepository.updateElementInModel(MODEL2_NAME, updated);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), any());
|
||||
verify(firstTypeListener).updatedModel(eq(MODEL2_NAME), firstTypeCaptor.capture());
|
||||
|
@ -464,7 +464,7 @@ public class YamlModelRepositoryImplTest {
|
|||
Files.copy(SOURCE_PATH.resolve("modifyModelInitialContent.yaml"), fullModelPath);
|
||||
|
||||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
FirstTypeDTO removed = new FirstTypeDTO("element1", "description1");
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
|
@ -481,7 +481,7 @@ public class YamlModelRepositoryImplTest {
|
|||
assertThat(yaml.load(actualFileContent), equalTo(yaml.load(expectedFileContent)));
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modifyModelV2InitialContent.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
modelRepository.removeElementFromModel(MODEL2_NAME, removed);
|
||||
verify(firstTypeListener).addedModel(eq(MODEL2_NAME), any());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -505,7 +505,7 @@ public class YamlModelRepositoryImplTest {
|
|||
Files.copy(SOURCE_PATH.resolve("modelFileAddedOrRemoved.yaml"), fullModelPath);
|
||||
|
||||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
FirstTypeDTO added = new FirstTypeDTO("element3", "description3");
|
||||
modelRepository.addElementToModel(MODEL_NAME, added);
|
||||
|
@ -523,7 +523,7 @@ public class YamlModelRepositoryImplTest {
|
|||
assertThat(yaml.load(actualFileContent), equalTo(yaml.load(expectedFileContent)));
|
||||
|
||||
Files.copy(SOURCE_PATH.resolve("modelV2FileAddedOrRemoved.yaml"), fullModel2Path);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
modelRepository.addElementToModel(MODEL2_NAME, added);
|
||||
modelRepository.removeElementFromModel(MODEL2_NAME, removed);
|
||||
modelRepository.updateElementInModel(MODEL2_NAME, updated);
|
||||
|
@ -546,7 +546,7 @@ public class YamlModelRepositoryImplTest {
|
|||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -570,7 +570,7 @@ public class YamlModelRepositoryImplTest {
|
|||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
verify(firstTypeListener).addedModel(eq(MODEL_NAME), firstTypeCaptor.capture());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -594,7 +594,7 @@ public class YamlModelRepositoryImplTest {
|
|||
YamlModelRepositoryImpl modelRepository = new YamlModelRepositoryImpl(watchServiceMock);
|
||||
modelRepository.addYamlModelListener(firstTypeListener);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
|
||||
verify(firstTypeListener, never()).addedModel(any(), any());
|
||||
verify(firstTypeListener, never()).updatedModel(any(), any());
|
||||
|
@ -619,8 +619,8 @@ public class YamlModelRepositoryImplTest {
|
|||
modelRepository.addYamlModelListener(secondTypeListener1);
|
||||
modelRepository.addYamlModelListener(secondTypeListener2);
|
||||
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, MODEL2_PATH);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModelPath);
|
||||
modelRepository.processWatchEvent(WatchService.Kind.CREATE, fullModel2Path);
|
||||
|
||||
verify(secondTypeListener1).addedModel(eq(MODEL_NAME), secondTypeCaptor1.capture());
|
||||
verify(secondTypeListener1, never()).addedModel(eq(MODEL2_NAME), any());
|
||||
|
|
|
@ -67,8 +67,7 @@ public class FileTransformationProvider implements WatchService.WatchEventListen
|
|||
watchService.registerListener(this, transformationPath);
|
||||
// read initial contents
|
||||
try (Stream<Path> files = Files.walk(transformationPath)) {
|
||||
files.filter(Files::isRegularFile).map(transformationPath::relativize)
|
||||
.forEach(f -> processWatchEvent(CREATE, f));
|
||||
files.filter(Files::isRegularFile).forEach(f -> processWatchEvent(CREATE, f));
|
||||
} catch (IOException e) {
|
||||
logger.warn("Could not list files in '{}', transformation configurations might be missing: {}",
|
||||
transformationPath, e.getMessage());
|
||||
|
@ -96,8 +95,8 @@ public class FileTransformationProvider implements WatchService.WatchEventListen
|
|||
}
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(WatchService.Kind kind, Path path) {
|
||||
Path finalPath = transformationPath.resolve(path);
|
||||
public void processWatchEvent(WatchService.Kind kind, Path fullPath) {
|
||||
Path path = transformationPath.relativize(fullPath);
|
||||
try {
|
||||
if (kind == DELETE) {
|
||||
Transformation oldElement = transformationConfigurations.remove(path);
|
||||
|
@ -105,7 +104,7 @@ public class FileTransformationProvider implements WatchService.WatchEventListen
|
|||
logger.trace("Removed configuration from file '{}", path);
|
||||
listeners.forEach(listener -> listener.removed(this, oldElement));
|
||||
}
|
||||
} else if (Files.isRegularFile(finalPath) && !Files.isHidden(finalPath)
|
||||
} else if (Files.isRegularFile(fullPath) && !Files.isHidden(fullPath)
|
||||
&& ((kind == CREATE) || (kind == MODIFY))) {
|
||||
String fileName = path.getFileName().toString();
|
||||
Matcher m = FILENAME_PATTERN.matcher(fileName);
|
||||
|
@ -122,7 +121,7 @@ public class FileTransformationProvider implements WatchService.WatchEventListen
|
|||
return;
|
||||
}
|
||||
|
||||
String content = new String(Files.readAllBytes(finalPath));
|
||||
String content = new String(Files.readAllBytes(fullPath));
|
||||
String uid = path.toString();
|
||||
|
||||
Transformation newElement = new Transformation(uid, uid, fileExtension, Map.of(FUNCTION, content));
|
||||
|
|
|
@ -89,10 +89,11 @@ public class FileTransformationProviderTest {
|
|||
|
||||
@Test
|
||||
public void testAddingConfigurationIsPropagated() throws IOException {
|
||||
Files.writeString(transformationPath.resolve(ADDED_FILENAME), ADDED_CONTENT);
|
||||
Path path = transformationPath.resolve(ADDED_FILENAME);
|
||||
Files.writeString(path, ADDED_CONTENT);
|
||||
Transformation addedConfiguration = new Transformation(ADDED_FILENAME.toString(), ADDED_FILENAME.toString(),
|
||||
FOO_TYPE, Map.of(FUNCTION, ADDED_CONTENT));
|
||||
provider.processWatchEvent(CREATE, ADDED_FILENAME);
|
||||
provider.processWatchEvent(CREATE, path);
|
||||
|
||||
// assert registry is notified and internal cache updated
|
||||
Mockito.verify(listenerMock).added(provider, addedConfiguration);
|
||||
|
@ -101,10 +102,11 @@ public class FileTransformationProviderTest {
|
|||
|
||||
@Test
|
||||
public void testUpdatingConfigurationIsPropagated() throws IOException {
|
||||
Files.writeString(transformationPath.resolve(INITIAL_FILENAME), "updated");
|
||||
Path path = transformationPath.resolve(INITIAL_FILENAME);
|
||||
Files.writeString(path, "updated");
|
||||
Transformation updatedConfiguration = new Transformation(INITIAL_FILENAME.toString(),
|
||||
INITIAL_FILENAME.toString(), FOO_TYPE, Map.of(FUNCTION, "updated"));
|
||||
provider.processWatchEvent(MODIFY, INITIAL_FILENAME);
|
||||
provider.processWatchEvent(MODIFY, path);
|
||||
|
||||
Mockito.verify(listenerMock).updated(provider, INITIAL_CONFIGURATION, updatedConfiguration);
|
||||
assertThat(provider.getAll(), contains(updatedConfiguration));
|
||||
|
@ -113,7 +115,7 @@ public class FileTransformationProviderTest {
|
|||
|
||||
@Test
|
||||
public void testDeletingConfigurationIsPropagated() {
|
||||
provider.processWatchEvent(DELETE, INITIAL_FILENAME);
|
||||
provider.processWatchEvent(DELETE, transformationPath.resolve(INITIAL_FILENAME));
|
||||
|
||||
Mockito.verify(listenerMock).removed(provider, INITIAL_CONFIGURATION);
|
||||
assertThat(provider.getAll(), not(contains(INITIAL_CONFIGURATION)));
|
||||
|
@ -128,15 +130,14 @@ public class FileTransformationProviderTest {
|
|||
|
||||
Transformation expected = new Transformation(fileName, fileName, FOO_TYPE, Map.of(FUNCTION, INITIAL_CONTENT));
|
||||
|
||||
provider.processWatchEvent(CREATE, Path.of(fileName));
|
||||
provider.processWatchEvent(CREATE, path);
|
||||
assertThat(provider.getAll(), hasItem(expected));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMissingExtensionIsIgnored() throws IOException {
|
||||
Path extensionMissing = Path.of("extensionMissing");
|
||||
Path path = transformationPath.resolve(extensionMissing);
|
||||
Files.writeString(path, INITIAL_CONTENT);
|
||||
Path extensionMissing = transformationPath.resolve("extensionMissing");
|
||||
Files.writeString(extensionMissing, INITIAL_CONTENT);
|
||||
provider.processWatchEvent(CREATE, extensionMissing);
|
||||
provider.processWatchEvent(MODIFY, extensionMissing);
|
||||
|
||||
|
@ -146,9 +147,8 @@ public class FileTransformationProviderTest {
|
|||
|
||||
@Test
|
||||
public void testIgnoredExtensionIsIgnored() throws IOException {
|
||||
Path extensionIgnored = Path.of("extensionIgnore.txt");
|
||||
Path path = transformationPath.resolve(extensionIgnored);
|
||||
Files.writeString(path, INITIAL_CONTENT);
|
||||
Path extensionIgnored = transformationPath.resolve("extensionIgnore.txt");
|
||||
Files.writeString(extensionIgnored, INITIAL_CONTENT);
|
||||
provider.processWatchEvent(CREATE, extensionIgnored);
|
||||
provider.processWatchEvent(MODIFY, extensionIgnored);
|
||||
|
||||
|
|
|
@ -289,8 +289,8 @@ public class WatchServiceImpl implements WatchService, DirectoryChangeListener {
|
|||
|
||||
private record Listener(Path rootPath, WatchEventListener watchEventListener) {
|
||||
|
||||
void notify(Path path, Kind kind) {
|
||||
watchEventListener.processWatchEvent(kind, rootPath.relativize(path));
|
||||
void notify(Path fullPath, Kind kind) {
|
||||
watchEventListener.processWatchEvent(kind, fullPath);
|
||||
}
|
||||
|
||||
static Predicate<Listener> isListener(WatchEventListener watchEventListener) {
|
||||
|
|
|
@ -119,9 +119,9 @@ public interface WatchService {
|
|||
* Notify Listener about watch event
|
||||
*
|
||||
* @param kind the {@link Kind} of this event
|
||||
* @param path the relative path of the file associated with this event
|
||||
* @param fullPath the absolute path of the file associated with this event
|
||||
*/
|
||||
void processWatchEvent(Kind kind, Path path);
|
||||
void processWatchEvent(Kind kind, Path fullPath);
|
||||
}
|
||||
|
||||
enum Kind {
|
||||
|
|
|
@ -48,6 +48,7 @@ import org.osgi.framework.BundleContext;
|
|||
@MockitoSettings(strictness = Strictness.LENIENT)
|
||||
public class WatchServiceImplTest extends JavaTest {
|
||||
private static final String SUB_DIR_PATH_NAME = "subDir";
|
||||
private static final String SUB_DIR2_PATH_NAME = "subDir2";
|
||||
private static final String TEST_FILE_NAME = "testFile";
|
||||
|
||||
public @Mock @NonNullByDefault({}) WatchServiceImpl.WatchServiceConfiguration configurationMock;
|
||||
|
@ -78,19 +79,18 @@ public class WatchServiceImplTest extends JavaTest {
|
|||
watchService.registerListener(listener, rootPath, false);
|
||||
|
||||
Path testFile = rootPath.resolve(TEST_FILE_NAME);
|
||||
Path relativeTestFilePath = Path.of(TEST_FILE_NAME);
|
||||
|
||||
Files.writeString(testFile, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.CREATE);
|
||||
assertEvent(testFile, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.MODIFY);
|
||||
assertEvent(testFile, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.delete(testFile);
|
||||
assertEvent(relativeTestFilePath, Kind.DELETE);
|
||||
assertEvent(testFile, Kind.DELETE);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -101,19 +101,18 @@ public class WatchServiceImplTest extends JavaTest {
|
|||
watchService.registerListener(listener, rootPath, true);
|
||||
|
||||
Path testFile = rootPath.resolve(SUB_DIR_PATH_NAME).resolve(TEST_FILE_NAME);
|
||||
Path relativeTestFilePath = Path.of(SUB_DIR_PATH_NAME, TEST_FILE_NAME);
|
||||
|
||||
Files.writeString(testFile, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.CREATE);
|
||||
assertEvent(testFile, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.MODIFY);
|
||||
assertEvent(testFile, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.delete(testFile);
|
||||
assertEvent(relativeTestFilePath, Kind.DELETE);
|
||||
assertEvent(testFile, Kind.DELETE);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -122,21 +121,21 @@ public class WatchServiceImplTest extends JavaTest {
|
|||
|
||||
// listener is only listening to sub-dir of root
|
||||
watchService.registerListener(listener, Path.of(SUB_DIR_PATH_NAME), false);
|
||||
watchService.registerListener(listener, Path.of(SUB_DIR2_PATH_NAME), false);
|
||||
|
||||
Path testFile = rootPath.resolve(SUB_DIR_PATH_NAME).resolve(TEST_FILE_NAME);
|
||||
Path relativeTestFilePath = Path.of(TEST_FILE_NAME);
|
||||
|
||||
Files.writeString(testFile, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.CREATE);
|
||||
assertEvent(testFile, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.MODIFY);
|
||||
assertEvent(testFile, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.delete(testFile);
|
||||
assertEvent(relativeTestFilePath, Kind.DELETE);
|
||||
assertEvent(testFile, Kind.DELETE);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -168,36 +167,70 @@ public class WatchServiceImplTest extends JavaTest {
|
|||
assertNoEvent();
|
||||
|
||||
Path testFile = subDirSubDir.resolve(TEST_FILE_NAME);
|
||||
Path relativeTestFilePath = rootPath.relativize(testFile);
|
||||
|
||||
Files.writeString(testFile, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.CREATE);
|
||||
assertEvent(testFile, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(relativeTestFilePath, Kind.MODIFY);
|
||||
assertEvent(testFile, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.delete(testFile);
|
||||
assertEvent(relativeTestFilePath, Kind.DELETE);
|
||||
assertEvent(testFile, Kind.DELETE);
|
||||
|
||||
Files.delete(subDirSubDir);
|
||||
assertNoEvent();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWatchMultiplePaths() throws IOException, InterruptedException {
|
||||
Files.createDirectories(rootPath.resolve(SUB_DIR_PATH_NAME));
|
||||
Files.createDirectories(rootPath.resolve(SUB_DIR2_PATH_NAME));
|
||||
|
||||
watchService.registerListener(listener, List.of(Path.of(SUB_DIR_PATH_NAME), Path.of(SUB_DIR2_PATH_NAME)), true);
|
||||
|
||||
Path testFile = rootPath.resolve(SUB_DIR_PATH_NAME).resolve(TEST_FILE_NAME);
|
||||
Path testFile2 = rootPath.resolve(SUB_DIR2_PATH_NAME).resolve(TEST_FILE_NAME);
|
||||
|
||||
Files.writeString(testFile, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(testFile, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(testFile, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.writeString(testFile2, "initial content", StandardCharsets.UTF_8);
|
||||
assertEvent(testFile2, Kind.CREATE);
|
||||
|
||||
Files.writeString(testFile2, "modified content", StandardCharsets.UTF_8);
|
||||
assertEvent(testFile2, Kind.MODIFY);
|
||||
|
||||
Files.writeString(testFile2, "modified content", StandardCharsets.UTF_8);
|
||||
assertNoEvent();
|
||||
|
||||
Files.delete(testFile);
|
||||
assertEvent(testFile, Kind.DELETE);
|
||||
|
||||
Files.delete(testFile2);
|
||||
assertEvent(testFile2, Kind.DELETE);
|
||||
}
|
||||
|
||||
private void assertNoEvent() throws InterruptedException {
|
||||
Thread.sleep(5000);
|
||||
|
||||
assertThat(listener.events, empty());
|
||||
}
|
||||
|
||||
private void assertEvent(Path path, Kind kind) throws InterruptedException {
|
||||
private void assertEvent(Path fullPath, Kind kind) throws InterruptedException {
|
||||
waitForAssert(() -> assertThat(listener.events, not(empty())));
|
||||
Thread.sleep(500);
|
||||
|
||||
assertThat(listener.events, hasSize(1));
|
||||
assertThat(listener.events, hasItem(new Event(path, kind)));
|
||||
assertThat(listener.events, hasItem(new Event(fullPath, kind)));
|
||||
listener.events.clear();
|
||||
}
|
||||
|
||||
|
@ -205,11 +238,11 @@ public class WatchServiceImplTest extends JavaTest {
|
|||
List<Event> events = new CopyOnWriteArrayList<>();
|
||||
|
||||
@Override
|
||||
public void processWatchEvent(Kind kind, Path path) {
|
||||
events.add(new Event(path, kind));
|
||||
public void processWatchEvent(Kind kind, Path fullPath) {
|
||||
events.add(new Event(fullPath, kind));
|
||||
}
|
||||
}
|
||||
|
||||
record Event(Path path, Kind kind) {
|
||||
record Event(Path fullPath, Kind kind) {
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue