@@ -468,49 +468,37 @@ to catch and handle."
468
468
(defonce ^:private ^ExecutorService io-thread-exec
469
469
(Executors/newCachedThreadPool (conc/counted-thread-factory " io-thread-macro-%d" true )))
470
470
471
- (defmacro io-thread
472
- " Asynchronously executes the body in a thread compatible with I/O workload,
473
- returning immediately to the calling thread. Only blocking operations should
474
- be used in io-thread bodies.
471
+ (defn thread-call
472
+ " Executes f in another thread, returning immediately to the calling
473
+ thread. Returns a channel which will receive the result of calling
474
+ f when completed, then close."
475
+ ([f] (thread-call f thread-macro-executor))
476
+ ([f ^ExecutorService exec]
477
+ (let [c (chan 1 )]
478
+ (let [binds (Var/getThreadBindingFrame )]
479
+ (.execute exec
480
+ (fn []
481
+ (Var/resetThreadBindingFrame binds)
482
+ (try
483
+ (let [ret (f )]
484
+ (when-not (nil? ret)
485
+ (>!! c ret)))
486
+ (finally
487
+ (close! c))))))
488
+ c)))
475
489
476
- io-thread bodies should not (either directly or indirectly) perform operations
477
- that never block nor run pure compute operations. Parking ops
478
- (i.e. <!, >! and alt!/alts!) used in io-thread bodies will throw at
490
+ (defmacro io-thread
491
+ " Asynchronously executes the body in a thread intended for I/O
492
+ workloads, returning immediately to the calling thread.
493
+ io-thread bodies may (either directly or indirectly) perform
494
+ operations that may block indefinitely. Parking ops (i.e. <!,
495
+ >! and alt!/alts!) used in io-thread bodies will throw at
479
496
runtime.
480
497
481
498
Returns a channel which will receive the result of the body when
482
499
completed"
483
500
[& body]
484
- `(let [c# (chan 1 )
485
- captured-bindings# (Var/getThreadBindingFrame )]
486
- (.execute ^ExecutorService @#'io-thread-exec
487
- (^:once fn* []
488
- (Var/resetThreadBindingFrame captured-bindings#)
489
- (try
490
- (let [result# (do ~@body)]
491
- (when-not (nil? result#)
492
- (>!! c# result#)))
493
- (finally
494
- (close! c#)))))
495
- c#))
496
-
497
- (defn thread-call
498
- " Executes f in another thread, returning immediately to the calling
499
- thread. Returns a channel which will receive the result of calling
500
- f when completed, then close."
501
- [f]
502
- (let [c (chan 1 )]
503
- (let [binds (Var/getThreadBindingFrame )]
504
- (.execute thread-macro-executor
505
- (fn []
506
- (Var/resetThreadBindingFrame binds)
507
- (try
508
- (let [ret (f )]
509
- (when-not (nil? ret)
510
- (>!! c ret)))
511
- (finally
512
- (close! c))))))
513
- c))
501
+ `(thread-call (^:once fn* [] ~@body) @#'io-thread-exec))
514
502
515
503
(defmacro thread
516
504
" Executes the body in another thread, returning immediately to the
0 commit comments