Clojure代理程序能否自动重启?

Clojure代理程序能否自动重启?

问题描述:

我想了解失败的代理是否可以自动重新启动。它不会出现在我的代码示例中:Clojure代理程序能否自动重启?

(def a (agent 0)) 

(defn h [a e] 
    (restart-agent a 0)) 

(set-error-handler! a h) 

(send a inc) 
;; 1 

(send a #(/ % 0)) 
;; error handler h will be triggered 

(send a inc) 
;; ArithmeticException Divide by zero (agent didn't restart) 

我错过了什么吗?

的事情是,在点在那里你请致电restart-agent不需要重新启动。您可以通过将您的处理程序更改为:

(defn h [a e] 
    (try (restart-agent a 0) 
    (catch Exception e (println e)))) 

引发异常,说'代理程序不需要重新启动'。只有在处理程序运行后才能执行:fail(或:continue)。

不知道你在后,或许引进起搏器?

(def a (agent 0)) 
(def a-pacemaker (agent nil)) 

(defn h [a e] 
    (send a-pacemaker (fn [_] (restart-agent a 0)))) 

(set-error-handler! a h) 
+0

我标志着这是正确的答案,因为它帮助我了解问题的真正原因,这意味着由此我明白了为什么@ AlanThompson的答案(即使用未来的)工作。 – Integralist

这似乎是一个未公开的要求,即restart-agent在不同的线程比错误处理程序被调用:

(dotest 
    (future (println "running in a thread...")) 
    (let [agt (agent 0) 

     ; This doesn't work 
     h01 (fn [a e] 
       (println :10 "agent error found:") 
       (println :11 "restarting agent...") 
       (restart-agent a 100) 
       (Thread/sleep 100) 
       (println :12 "agent restarted, state=" @a)) 

     ; This works. Need to call restart-agent in a separate thread 
     h02 (fn [a e] 
       (println :20 "agent error found:") 
       (future 
       (println :21 "restarting agent...") 
       (restart-agent a 200) 
       (println :22 "agent restarted, state=" @a))) ;=> 200 
    ] 
    (set-error-handler! agt h02) 
    (send agt inc) 
    (Thread/sleep 100) (spy :01 @agt) ;=> 1 
    (Thread/sleep 100) (send agt #(/ % 0)) 
    (Thread/sleep 100) (spy :02 @agt) ;=> 200 
    (Thread/sleep 100) (send agt inc) 
    (Thread/sleep 100) (spy :03 @agt) ;=> 201 
)) 

有了结果:

running in a thread... 
:01 => 1 
:20 agent error found: 
:21 restarting agent... 
:22 agent restarted, state= 200 
:02 => 200 
:03 => 201