From 2fb444df86d56246a8b5cee515eb91490c8dee05 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 15 Sep 2018 11:29:01 +1200 Subject: More work on service implementation --- src/org/traccar/Main.java | 76 ++++++++++++++++++++++--------------- src/org/traccar/ServerManager.java | 2 +- src/org/traccar/WindowsService.java | 33 ++++++++-------- 3 files changed, 61 insertions(+), 50 deletions(-) (limited to 'src/org/traccar') diff --git a/src/org/traccar/Main.java b/src/org/traccar/Main.java index 986731240..992bfd8de 100644 --- a/src/org/traccar/Main.java +++ b/src/org/traccar/Main.java @@ -71,11 +71,16 @@ public final class Main { throw new RuntimeException("Configuration file is not provided"); } - String configFile = args[args.length - 1]; + final String configFile = args[args.length - 1]; - if (args.length > 1) { - WindowsService windowsService = new WindowsService("traccar"); - switch (args[1]) { + if (args[0].startsWith("--")) { + WindowsService windowsService = new WindowsService("traccar") { + @Override + public void run() { + Main.run(configFile); + } + }; + switch (args[0]) { case "--install": windowsService.install("traccar", null, null, null, null, configFile); return; @@ -87,40 +92,49 @@ public final class Main { windowsService.init(); break; } + } else { + run(configFile); } + } - Context.init(configFile); - logSystemInfo(); - LOGGER.info("Version: " + Context.getAppVersion()); - LOGGER.info("Starting server..."); - - Context.getServerManager().start(); - if (Context.getWebServer() != null) { - Context.getWebServer().start(); - } + public static void run(String configFile) { + try { + Context.init(configFile); + logSystemInfo(); + LOGGER.info("Version: " + Context.getAppVersion()); + LOGGER.info("Starting server..."); + + Context.getServerManager().start(); + if (Context.getWebServer() != null) { + Context.getWebServer().start(); + } - new Timer().scheduleAtFixedRate(new TimerTask() { - @Override - public void run() { - try { - Context.getDataManager().clearHistory(); - } catch (SQLException error) { - LOGGER.warn(null, error); + new Timer().scheduleAtFixedRate(new TimerTask() { + @Override + public void run() { + try { + Context.getDataManager().clearHistory(); + } catch (SQLException error) { + LOGGER.warn(null, error); + } } - } - }, 0, CLEAN_PERIOD); + }, 0, CLEAN_PERIOD); - Runtime.getRuntime().addShutdownHook(new Thread() { - @Override - public void run() { - LOGGER.info("Shutting down server..."); + Runtime.getRuntime().addShutdownHook(new Thread() { + @Override + public void run() { + LOGGER.info("Shutting down server..."); - if (Context.getWebServer() != null) { - Context.getWebServer().stop(); + if (Context.getWebServer() != null) { + Context.getWebServer().stop(); + } + Context.getServerManager().stop(); } - Context.getServerManager().stop(); - } - }); + }); + } catch (Exception e) { + LOGGER.error(null, e); + throw new RuntimeException(e); + } } } diff --git a/src/org/traccar/ServerManager.java b/src/org/traccar/ServerManager.java index a67f71be2..17c572ae3 100644 --- a/src/org/traccar/ServerManager.java +++ b/src/org/traccar/ServerManager.java @@ -44,7 +44,7 @@ public class ServerManager { List names = new LinkedList<>(); String packageName = "org.traccar.protocol"; String packagePath = packageName.replace('.', '/'); - URL packageUrl = Thread.currentThread().getContextClassLoader().getResource(packagePath); + URL packageUrl = getClass().getClassLoader().getResource(packagePath); if (packageUrl.getProtocol().equals("jar")) { String jarFileName = URLDecoder.decode(packageUrl.getFile(), StandardCharsets.UTF_8.name()); diff --git a/src/org/traccar/WindowsService.java b/src/org/traccar/WindowsService.java index 398648b7b..dccb01559 100644 --- a/src/org/traccar/WindowsService.java +++ b/src/org/traccar/WindowsService.java @@ -27,17 +27,15 @@ import com.sun.jna.platform.win32.Winsvc.SERVICE_MAIN_FUNCTION; import com.sun.jna.platform.win32.Winsvc.SERVICE_STATUS; import com.sun.jna.platform.win32.Winsvc.SERVICE_STATUS_HANDLE; import com.sun.jna.platform.win32.Winsvc.SERVICE_TABLE_ENTRY; +import jnr.posix.POSIXFactory; + import java.io.File; import java.net.URISyntaxException; -import java.net.URL; -import java.net.URLClassLoader; -public class WindowsService { +public abstract class WindowsService { private static final Advapi32 ADVAPI_32 = Advapi32.INSTANCE; - private final Object waitObject = new Object(); - private String serviceName; private ServiceMain serviceMain; private ServiceControl serviceControl; @@ -53,10 +51,8 @@ public class WindowsService { String javaHome = System.getProperty("java.home"); String javaBinary = javaHome + "\\bin\\java.exe"; - URLClassLoader cl = (URLClassLoader) WindowsService.class.getClassLoader(); - URL jarPath = cl.getURLs()[0]; - File jar = new File(jarPath.toURI()); + File jar = new File(WindowsService.class.getProtectionDomain().getCodeSource().getLocation().toURI()); String command = javaBinary + " -jar \"" + jar.getAbsolutePath() + "\" --service \"" + config + "\""; boolean success = false; @@ -145,7 +141,13 @@ public class WindowsService { return (success); } - public void init() { + public void init() throws URISyntaxException { + String path = new File( + WindowsService.class.getProtectionDomain().getCodeSource().getLocation().toURI()).getParent(); + + POSIXFactory.getPOSIX().chdir(path); + System.setProperty("user.dir", path); + serviceMain = new ServiceMain(); SERVICE_TABLE_ENTRY entry = new SERVICE_TABLE_ENTRY(); entry.lpServiceName = serviceName; @@ -169,6 +171,8 @@ public class WindowsService { ADVAPI_32.SetServiceStatus(serviceStatusHandle, serviceStatus); } + public abstract void run(); + private class ServiceMain implements SERVICE_MAIN_FUNCTION { public void callback(int dwArgc, Pointer lpszArgv) { @@ -178,12 +182,8 @@ public class WindowsService { reportStatus(Winsvc.SERVICE_START_PENDING, WinError.NO_ERROR, 3000); reportStatus(Winsvc.SERVICE_RUNNING, WinError.NO_ERROR, 0); - try { - synchronized (waitObject) { - waitObject.wait(); - } - } catch (InterruptedException ex) { - } + run(); + reportStatus(Winsvc.SERVICE_STOPPED, WinError.NO_ERROR, 0); // Avoid returning from ServiceMain, which will cause a crash @@ -202,9 +202,6 @@ public class WindowsService { case Winsvc.SERVICE_CONTROL_SHUTDOWN: reportStatus(Winsvc.SERVICE_STOP_PENDING, WinError.NO_ERROR, 5000); System.exit(0); - synchronized (waitObject) { - waitObject.notifyAll(); - } default: break; } -- cgit v1.2.3