本文意译自 原文链接,语言上做了精炼和排版的变更,以便更简洁明了。
Delphi 开始支持 Linux 平台为 Delphi 开发人员开辟了创建 Linux 服务器应用程序的可能。但遗憾的是,目前 RAD Studio IDE 并不包括创建 Linux 守护程序()服务)。
【注意】本文假设您已经能够配置好 Linux 编译环境并知道如何在 Linux 命令行启动它。否则请参考:
- http://chapmanworld.com/2017/02/28/embarcadero-delphi-linux-bootcamp/
- http://chapmanworld.com/2016/12/29/configure-delphi-and-redhat-or-ubuntu-for-linux-development/
【守护进程】
在Linux操作系统下,守护进程只是一个没有标准输入和输出流的进程。它在后台运行并不接受键盘输入也不会向屏幕输出(当然可以输出日志)。
【创建服务】
1、创建一个控制台项目,并添加 Linux64 为编译目标。
2、uses 中加入 Posix.Unistd 单元,以便引用其中的 fork 函数创建子进程。
3、在程序的入口地方加入对 fork 的调用,以创建子服务进程。注意 fork 函数的返回子进程的进程 ID,我们有可能需要将它写入到一个配置文件中,以便控制服务的结束(这是后话,原文中没说),下面的示例只是做了一个简单的判断直接退出了。
4、fork 成功后调用 exit 退出当前进程,如果返回值为0,代表自己是子进程。然后执行后面的进程就可以了。
program Project1; {$APPTYPE CONSOLE} {$R *.res} uses System.SysUtils, Posix.Unistd; begin try if fork()<>0 then begin exit; end; ... except on E: Exception do Writeln(E.ClassName, ': ', E.Message); end; end.
5、编译并发布到目标计算机运行进程。
【创建服务】
这一步在不同的平台上不太一样,早期的 Linux 是创建一个脚本,放到 init.d 里,然后一步步注册。新的 centos 是在 /lib/systemd/system 添加 xxx.service 定义。具体就参考相应的文档配置就可以了。
【QDAC 的解决方案】
qconsole_looper 为您提供更简单的解决方案,引用该单元,然后:
TQConsoleLooper.Current.IsDaemon:=True;
TQConsoleLooper.Current.PidFile:=”用来存贮进程PID的文件,如果不需要不用设置”;
TQConsoleLooper.Current.Run;
如果程序要响应特定的信号,则在 HandleSignal 注册,然后响应 OnSignal 事件即可。默认会自动响应 SIGQUIT/SIGABORT,如果用户没有自己响应,在收到这两个信号后会自动退出。