forked from oliyh/superlifter
-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
비동기 pooled executor로 변경 #11
Closed
Closed
Changes from all commits
Commits
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,74 @@ | ||
(ns superlifter.future | ||
(:import | ||
java.util.concurrent.Callable)) | ||
|
||
(def default-executor | ||
clojure.lang.Agent/pooledExecutor) | ||
|
||
(defn binding-conveyor-fn | ||
{:private true | ||
:added "1.3"} | ||
[f] | ||
(let [frame (clojure.lang.Var/cloneThreadBindingFrame)] | ||
(fn | ||
([] | ||
(clojure.lang.Var/resetThreadBindingFrame frame) | ||
(f)) | ||
([x] | ||
(clojure.lang.Var/resetThreadBindingFrame frame) | ||
(f x)) | ||
([x y] | ||
(clojure.lang.Var/resetThreadBindingFrame frame) | ||
(f x y)) | ||
([x y z] | ||
(clojure.lang.Var/resetThreadBindingFrame frame) | ||
(f x y z)) | ||
([x y z & args] | ||
(clojure.lang.Var/resetThreadBindingFrame frame) | ||
(apply f x y z args))))) | ||
|
||
(defn ^:private deref-future | ||
([^java.util.concurrent.Future fut] | ||
(.get fut)) | ||
([^java.util.concurrent.Future fut timeout-ms timeout-val] | ||
(try (.get fut timeout-ms java.util.concurrent.TimeUnit/MILLISECONDS) | ||
(catch java.util.concurrent.TimeoutException e | ||
timeout-val)))) | ||
|
||
(defn future-call-with-executor | ||
"Takes a function of no args (and optionally an ExecutorService | ||
instance that will run the task, by default it uses pooledExecutor) | ||
and yields a future object that will invoke the function in another thread, and will | ||
cache the result and return it on all subsequent calls to | ||
deref/@. If the computation has not yet finished, calls to deref/@ | ||
will block, unless the variant of deref with timeout is used. See | ||
also - realized?." | ||
([f executor] | ||
(let [f (binding-conveyor-fn f) | ||
fut (.submit ^java.util.concurrent.ExecutorService executor | ||
^Callable f)] | ||
(reify | ||
clojure.lang.IDeref | ||
(deref [_] (deref-future fut)) | ||
clojure.lang.IBlockingDeref | ||
(deref | ||
[_ timeout-ms timeout-val] | ||
(deref-future fut timeout-ms timeout-val)) | ||
clojure.lang.IPending | ||
(isRealized [_] (.isDone fut)) | ||
java.util.concurrent.Future | ||
(get [_] (.get fut)) | ||
(get [_ timeout unit] (.get fut timeout unit)) | ||
(isCancelled [_] (.isCancelled fut)) | ||
(isDone [_] (.isDone fut)) | ||
(cancel [_ interrupt?] (.cancel fut interrupt?))))) | ||
([f] | ||
(future-call-with-executor f clojure.lang.Agent/pooledExecutor))) | ||
|
||
(defmacro future-with-pooled-executor | ||
"Takes a executor and body of expressions and yields a future object that will | ||
invoke the body in another thread, and will cache the result and | ||
return it on all subsequent calls to deref/@. If the computation has | ||
not yet finished, calls to deref/@ will block, unless the variant of | ||
deref with timeout is used. See also - realized?." | ||
([& body] `(future-call-with-executor (^{:once true} fn* [] ~@body) default-executor))) |
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
core에 같이 넣기는 애매한것같아서 future라는 ns를 만들고 core 함수를 가져와서 executor를 주입할 수 있도록 일부 수정했습니다.
private으로 설정된 녀석들도 있어서 불가피하게 같이 가져왔어요.