我刚刚继承了一个java应用程序,需要在XP和vista上作为服务安装。我已经8年没有使用任何形式的windows了,我从来没有创建过服务,更不用说从java应用程序(我已经为应用程序准备了一个jar和一个依赖jar - log4j)。使其作为服务运行所必需的魔力是什么?我已经得到了源代码,所以代码修改(尽管最好避免)是可能的。
当前回答
我在Java服务包装器方面有一些运气
其他回答
JavaService是LGPL。这是非常容易和稳定的。强烈推荐。
Apache Commons Daemon是一个很好的替代方案。它为windows服务提供Procrun,为unix守护进程提供Jsvc。它使用限制较少的Apache许可证,Apache Tomcat将其作为自身的一部分运行在Windows和Linux上!要让它工作起来有点棘手,但是有一篇详细的文章提供了工作示例。
除此之外,您可以查看Apache Tomcat中的bin\service.bat以了解如何设置服务。在Tomcat中,他们重命名Procrun二进制文件(prunsrv.exe -> tomcat6.exe, prunmgr.exe -> tomcat6w.exe)。
我在使用Procrun时遇到了一些困难,您的启动和停止方法必须接受参数(String[] argv)。例如"start(String[] argv)"和"stop(String[] argv)"可以工作,但"start()"和"stop()"会导致错误。如果您不能修改这些调用,请考虑创建一个bootstrapper类,它可以根据您的需要修改这些调用。
另一种选择是WinRun4J。这是一个可配置的java启动器,可作为windows服务主机(32位和64位版本)。它是开源的,使用上没有限制。
(完全披露:我参与了这个项目)。
我目前需要运行一个基于eclipse的应用程序,但我需要先设置一些应用程序本地的变量。sc.exe只允许可执行文件,不允许脚本,所以我转向了Windows 2003资源包中的autoexnt.exe。它将服务限制为单个批处理文件,但我只需要将一个批处理脚本转换为服务。
嗨!
通过结合使用外部内存和连接器API(从JDK16开始预览)与OpenJDK jextract项目来处理Windows服务的回调,然后使用jpackage来生成一个Windows EXE,然后可以注册为Windows服务,这是可能在100% Java代码中实现Windows服务。
请看这个例子,它概述了实现Windows服务所需的工作。所有Windows服务EXE必须为主入口点ServiceMain和服务控制处理程序提供回调,并在Advapi.DLL中使用API调用StartServiceCtrlDispatcherW, RegisterServiceCtrlHandlerExW和SetServiceStatus。
在具有外部内存结构的Java中,上述回调的流程是:
main()
Must register ServiceMain using StartServiceCtrlDispatcherW
Above call blocks until ServiceMain exits
void ServiceMain(int dwNumServicesArgs, MemoryAddress lpServiceArgVectors)
Must register SvcCtrlHandler using RegisterServiceCtrlHandlerExW
Use SetServiceStatus(SERVICE_START_PENDING)
Initialise app
Use SetServiceStatus(SERVICE_RUNNING)
wait for app shutdown notification
Use SetServiceStatus(SERVICE_STOPPED)
int SvcCtrlHandler(int dwControl, int dwEventType, MemoryAddress lpEventData, MemoryAddress lpContext)
Must respond to service control events and report back using SetServiceStatus
On receiving SERVICE_CONTROL_STOP reports SetServiceStatus(SERVICE_STOP_PENDING)
then set app shutdown notification
一旦完成Java应用程序,jpackage可以创建运行时+EXE,然后可以安装和注册为Windows服务。以管理员身份运行(=后面的空格很重要):
sc create YourJavaServiceName type= own binpath= "c:\Program Files\Your Release Dir\yourjavaservice.exe"
推荐文章
- Mockito中检测到未完成的存根
- 我应该如何复制字符串在Java?
- “while(true)”循环有那么糟糕吗?
- 这个方法签名中的省略号(…)是干什么用的?
- .msi和setup.exe文件之间的具体区别是什么?
- Java:如何测试调用System.exit()的方法?
- 带有返回类型的Java方法在没有返回语句的情况下编译
- Java“此语言级别不支持lambda表达式”
- “Java”不能被识别为内部或外部命令
- JPA:如何将本机查询结果集转换为POJO类集合
- 日历日期为yyyy-MM-dd格式的java
- 在IntelliJ IDEA中导入Maven依赖项
- 在Java中转换float为String和String为float
- 将double类型转换为字符串
- Java关联数组