Set a Timeout on a Block of Code

Posted 04/09/2018 5:51 PM by Corey Klass

Sometimes you have a segment of code that you want to kill if it runs any longer than a specified time period, for example a database query, external API call, or other type of long-running request.

To do this, you want to wrap the block of code to time out in a Callable, and use the ExecutorService to execute the code with a time limit. It will return an array of Future objects, which you can then reference with the .get() method to retrieve the Callable return value.

In your build.gradle file, you will need to include the Grails Executor plug-in if you want to have any GORM/Hibernate functionality in your Callable statement.

    compile "org.grails.plugins:grails-executor:0.4"

You can then use the following code to put a timeout on your executing code. When the timeout is reached, the thread that was spawned is terminated.

    class CallableTestService {

        ExecutorService executorService

        Object performAction() {
            def callable = ({
                // do some logic here
                def resultValue = true

                // return the value
                return resultValue
            } as Callable<Object>)

            def callables = [callable]
            def result = null

            try {
                def timeLimitMS = 1000

                def futures = this.executorService.invokeAll(callables, timeLimitMS, TimeUnit.MILLISECONDS)
                def future = futures?.first()

                result = future.get()

            } catch (error) {
              // error handling goes here
            }


            // do something with the result
            return result
        }
    }