应用程序在Clozure中交付长时间运行的应用程序CL
问题描述:
应用程序交付的所有基本示例都显示了如何用自己的代替顶层函数。一旦该功能完成,应用程序退出。我想知道为长期运行的应用程序创建顶层函数的最佳方法是什么。我的代码是应用程序在Clozure中交付长时间运行的应用程序CL
(ql:quickload :my-app)
(defun main()
(swank:create-server :dont-close t)
(my-app:start-server) ; Essentially creates a hunchentoot handler and returns
(loop for x = (read-line)
when (string= x "q") do (quit)
do (format t "Type q to quit~%" x)))
(save-application "my-app" :toplevel-function #'main :prepend-kernel t)
有没有更好的方法?我不喜欢循环,但是释放终端的东西也可以。
答
正如你所说,一旦主要功能完成,应用程序就会退出。 Ergo,你需要保持该功能运行,直到你想退出应用程序。
最简单的解决方法就是离开主回路中的sleep
一个无限循环:
(defun main()
(swank:create-server :dont-close t)
(my-app:start-server)
(loop (sleep 60)))
当你开始一个斯旺克服务器,你可能要包括的功能,通过一个泥干净地退出应用程序连接。你可以,例如,喜欢写东西下面,使用bt-semaphore
包:
(defvar *quit-my-app* (bt-semaphore:make-semamphore))
(defun main()
(swank:create-server :dont-close t)
(my-app:start-server)
(bt-semaphore:wait-on-semaphore *quit-my-app*)
(my-app:clean-up)) ; or whatever you need to do for cleaning up
(defun quit-my-app()
(bt-semaphore:signal-semaphore *quit-my-app*))
现在你可以粘液连接上简单地评价(quit-my-app)
关闭应用程序。
您也可以使用主线程进行维护工作。在我的服务器上,我执行简单的日志循环:
(defun seconds-until-tomorrow()
(multiple-value-bind (second minute hour day month year daylight-p zone)
(decode-universal-time (+ (get-universal-time) (* 60 60 26))) ; safely tomorrow
(declare (ignore second minute hour daylight-p))
(- (encode-universal-time 0 0 0 day month year zone)
(get-universal-time))))
(defun main()
(swank:create-server :dont-close t)
(let (cur-logfile
cur-logfile-name
;; assuming that start-server returns the Hunchentoot acceptor
(acpt (my-app:start-server)))
(loop
(let* ((lf-stem (log-file-name))
(logfile-name (merge-pathnames lf-stem *temp-path*))
(new-logfile (open logfile-name :direction :output
:if-exists :append
:if-does-not-exist :create)))
(setf (hunchentoot:acceptor-message-log-destination acpt) new-logfile
(hunchentoot:acceptor-access-log-destination acpt) new-logfile)
(when cur-logfile
(close cur-logfile)
(run-program "/usr/bin/xz" (list (princ-to-string cur-logfile-name))))
(setf cur-logfile new-logfile
cur-logfile-name logfile-name)
(when (bt-semaphore:wait-on-semaphore *quit-my-app* (seconds-until-tomorrow))
(return)))))
释放终端必然是平台(OS)特定的。你在哪个平台上运行你的应用程序?另外,请澄清你的“更好的方式”的定义。您认为最佳的主要功能是什么? – jlahd 2014-10-31 07:38:03
“更好的方式”是主观的我猜。我真正的意思是惯用/最佳实践,甚至是改进代码的建议。是否有必要有一个循环做一个阻塞的读线或有其他方式不能退出?我正在OSX上开发,不确定终端是否可用。 – 2014-10-31 16:51:56