Questions on the get() method of the Future returned by calling HystrixCommand..queue()

489 views
Skip to first unread message

hao chen

unread,
Sep 6, 2015, 12:44:28 PM9/6/15
to HystrixOSS
I will implement the fire and forget pattern by extending HystrixCommand and am planning to just call HystrixCommand..queue() without calling the get() method of the returned Future. I have the following questions:
1. is " extending HystrixCommand and just calling HystrixCommand..queue() without calling the get() method of the returned Future" a proper way to utilize Hystrix to implement fire and forget pattern. If this is not a proper approach, what is the proper way to use Hystrix to implement the fire and forget pattern?
2. Is it possible to make HystrixCommand's run() method not return any thing such as void? or returns null without causing exception or Hystrix thinking something wrong.  If it is not possible, then I would like to know how Hystrix releases the returned object, such as under what condition or via some timeout setting to de-reference the object such that the object can be garbage collected by JVM. The reason I ask the question is that the get() method of the returned Future is never called. Then I guess the Hystrix does not know if and how long it needs to held the object returned by run() method and I am afraid of the object will be piled up similar to memory leak.
3. doing " extending HystrixCommand and just calling HystrixCommand..queue() without calling the get() method of the returned Future", will we still be able to take advantage of Hystrix, thread pool management, thread or execution timeout feature, circuit breaker, automatically recovering?

Matt Jacobs

unread,
Sep 9, 2015, 9:18:29 AM9/9/15
to HystrixOSS
Hao -

For a fire-and-forget command, if you never block on the result via Future.get(), then you don't know if the command succeeds/fails.  This is possible, but has a few implications.  It really only makes sense for this command to return Void, as you're relying on a side-effect, not the returned value.  

All limitations imposed by Hystrix still apply (timeout + threadpool bounds + circuit health).  So if you fire a large number of commands that consume a Hystrix thread, but your Tomcat thread walks away, then the Hystrix threads are still active even after the request is over.  But as they are on a Hystrix thread, this is a shared resource, and properly prevents too many commands from being placed into this threadpool.  The command instance lifetime is from the moment is gets constructed to the time it experiences a terminal event and cleans itself up.  That may occur due to success/timeout/failure/rejection.  So the object lifetimes are bounded but they may, in your case, exceed a request boundary.

Another implication is that since you're not waiting for any feedback from your command execution, you don't know in your application whether or not the command succeeded.  Circuits will still open/close, and timeouts will still occur, but they will only be visible as side-effects in your metrics/dashboards, and by whatever effects your commands had on downstream systems.

Hope that helps,
Matt

hao chen

unread,
Sep 9, 2015, 11:36:36 AM9/9/15
to HystrixOSS
Hi Matt,

Thanks a lot for your response. Based on your response, I have the following concerns:
1. I can't define HystrixCommand<void> but I can do HystrixCommand<String> and run() method returns null. Will this cause the thread fail or as normal response?
2. Because I do not call the Future.get() method, I want to confirm if there's a way to make Hystrix thread pool or thread management know the run() method success or failure. I think if the run() method does not throw any exception, then the invocation successes; otherwise, fails. I wish only run() throws exception, thread times out, or thread pool or queue is full will trigger the circuit health mechanism. I do not want the successful case (run() does not throw exception) to be treated by Hystrix as failure case because the get() is not called. Is there any way to achieve this by using Hystrix API?
3. I also do not want the thread is not released to the thread pool just because the get() method is not called. I also do not want the thread is terminated only because thread timeout or runtime error. Should a way we can signal normal run condition such that the thread is back to the thread pool in success case even without call get() method?

Highly appreciated to clarify the above concerns.

Matt Jacobs

unread,
Sep 9, 2015, 12:32:48 PM9/9/15
to HystrixOSS
1) You are free to define HystrixCommand<Void> and return null
2) Yes, all Hystrix internals keep track of the work being done on a Hystrix thread, regardless of whether your application waits for the response or not.  Success/Failures are tracked as always.  No difference from the case where .get() is called
3) As in 2), you should be fine.

hao chen

unread,
Sep 9, 2015, 1:29:53 PM9/9/15
to HystrixOSS
Hi Matt,

Your response makes me comfortable to implement this by using Hystrix. Thanks a lot.
Reply all
Reply to author
Forward
0 new messages