package org.simantics.fileimport.dropins;\r
\r
-import static java.nio.file.StandardWatchEventKinds.OVERFLOW;\r
import static java.nio.file.StandardWatchEventKinds.ENTRY_CREATE;\r
import static java.nio.file.StandardWatchEventKinds.ENTRY_DELETE;\r
import static java.nio.file.StandardWatchEventKinds.ENTRY_MODIFY;\r
+import static java.nio.file.StandardWatchEventKinds.OVERFLOW;\r
\r
+import java.io.FileNotFoundException;\r
import java.io.IOException;\r
+import java.io.RandomAccessFile;\r
import java.nio.file.FileSystem;\r
+import java.nio.file.FileSystemException;\r
import java.nio.file.FileVisitResult;\r
import java.nio.file.Files;\r
import java.nio.file.Path;\r
import java.nio.file.SimpleFileVisitor;\r
import java.nio.file.WatchEvent;\r
import java.nio.file.WatchEvent.Kind;\r
+import java.nio.file.WatchKey;\r
+import java.nio.file.WatchService;\r
import java.nio.file.attribute.BasicFileAttributes;\r
import java.util.HashMap;\r
import java.util.Map;\r
import java.util.Optional;\r
import java.util.concurrent.atomic.AtomicBoolean;\r
-import java.nio.file.WatchKey;\r
-import java.nio.file.WatchService;\r
\r
import org.simantics.fileimport.Activator;\r
import org.simantics.fileimport.FileImportService;\r
\r
+/**\r
+ * Directory watcher based on {@link java.nio.file.WatchService} which will listen to file changes inside the dropins directory\r
+ * ~/workspace/.metadata/plugins/org.simantics.fileimport/dropins\r
+ * \r
+ * @author Jani Simomaa\r
+ *\r
+ */\r
public class FileImportDropins {\r
\r
private static Thread watcherThread = null;\r
private static DropinsFolderWatcher watcher = null;\r
\r
+ /**\r
+ * Start watching the dropins folder which are located in\r
+ * ~/workspace/.metadata/plugins/org.simantics.fileimport/dropins\r
+ */\r
public static void watchDropinsFolder() {\r
if (watcher == null && watcherThread == null) {\r
try {\r
}\r
}\r
\r
+ /**\r
+ * Stop watching the dropins folder\r
+ */\r
public static void unwatchDropinsFolder() {\r
+ if (watcher == null)\r
+ return;\r
watcher.stop();\r
try {\r
watcherThread.join(500);\r
registerAll(this.dropinsFolder);\r
}\r
\r
+ private static void syncPath(Path f) throws IOException {\r
+ // Does not seem to need 's' according to unit test in Windows\r
+ boolean synced = false;\r
+ int count = 0;\r
+ while (!synced) {\r
+ try (RandomAccessFile raf = new RandomAccessFile(f.toFile(), "rw")) {\r
+ raf.getFD().sync();\r
+ synced = true;\r
+ } catch (IOException e) {\r
+ if (count == 3) {\r
+ throw e;\r
+ } else {\r
+ try {\r
+ Thread.sleep(50);\r
+ } catch (InterruptedException e1) {\r
+ e1.printStackTrace();\r
+ }\r
+ count++;\r
+ }\r
+ }\r
+ }\r
+ }\r
+ \r
@Override\r
public void run() {\r
stopped.set(false);\r
continue;\r
if (ENTRY_CREATE == kind) {\r
System.out.println("New path created: " + newPath);\r
- FileImportService.performFileImport(newPath, Optional.empty());\r
+ int current = 0;\r
+ \r
+ while (!Files.isWritable(newPath) && current <= 10) {\r
+ System.out.println("Sleeping for file import (current=" + current +")");\r
+ Thread.sleep(200);\r
+ current++;\r
+ }\r
+ \r
+ FileImportService.performFileImport(newPath, Optional.of(t -> {\r
+ if ((t instanceof FileSystemException) || (t instanceof FileNotFoundException)) {\r
+ try {\r
+ syncPath(newPath);\r
+ } catch (IOException e) {\r
+ e.printStackTrace();\r
+ }\r
+ FileImportService.performFileImport(newPath, Optional.empty());\r
+ } else {\r
+ t.printStackTrace();\r
+ }\r
+ }));\r
register(newPath);\r
+ \r
} else if (ENTRY_MODIFY == kind) {\r
System.out.println("New path modified: " + newPath);\r
} else if (ENTRY_DELETE == kind) {\r
keys.remove(key);\r
// break; // loop\r
}\r
- } catch (IOException e) {\r
- e.printStackTrace();\r
} catch (InterruptedException e) {\r
if (!stopped.get())\r
e.printStackTrace();\r