Skip to content
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

Macro to timeout operations that take too long #282

Open
pw0908 opened this issue May 24, 2024 · 4 comments
Open

Macro to timeout operations that take too long #282

pw0908 opened this issue May 24, 2024 · 4 comments

Comments

@pw0908
Copy link

pw0908 commented May 24, 2024

Hi!

On my Genie app, there are some cases where, if the user inputs unphysical conditions, the solvers will get stuck / take a long time to output an unreasonable result. As such, it would be great to have some sort of macro that will only allow a task to only run for a certain amount of time. There was an example here: https://discourse.julialang.org/t/simple-timeout-of-function/99578/3

The macro they propose looks like this:

macro timeout(seconds, expr_to_run, expr_when_fails="Timed out")
    quote
        tsk = @task $(esc(expr_to_run))
        schedule(tsk)
        Timer($(esc(seconds))) do timer
            istaskdone(tsk) || Base.throwto(tsk, InterruptException())
        end
        try
            fetch(tsk)
        catch _
            $(esc(expr_when_fails))
        end
    end
end

However, I've found that this macro doesn't work for my cases. Here is an MWE (you'll need to install Clapeyron):

using Clapeyron

model = PCSAFT(["water", "carbon dioxide"])

@time bubble_pressure(model,298.15,[0.9,0.1])
# After first compilation, this should take about 0.8s

@timeout 0.01 bubble_pressure(model,298.15,[0.9,0.1])
# Doesn't timeout
@hhaensel
Copy link
Member

hhaensel commented Jun 3, 2024

Not sure what you are doing in Clapeyron. (Typically for an MWE (MINIMAL workable example) you don't need to install a foreign dependency.)
But the following MWE does work as expected:

@app MyApp begin
    @in a = 12
end

function f(model)
    println("before $(model.a[])")
    sleep(1)
    println("after $(model.a[])")
end

then

julia> model = @init MyApp;
julia> @timeout 2 f(model)
before 12
after 12

julia> @timeout  0.2 f(model)
before 12
"Timed out"

@pw0908
Copy link
Author

pw0908 commented Jun 3, 2024

My apologies for not being clearer. I can get it to work for simple examples like the one you've shown. However, once calls to module functions are used, like bubble_pressure, I noticed that @timeout wouldn't actually timeout. In my case, I used Clapeyron since that's the package I'm trying to timeout in Genie. However, I've found this isn't unique to Clapeyron as even 'simple' packages like Roots.jl also don't timeout when they should. For example:

f(x) = exp(-x^2)-sin(x)

@time fzeros(f,-10000,10000);
#  0.074126 seconds (1.39 M allocations: 38.786 MiB, 3.51% gc time)

@timeout 1e-4 fzeros(f,-10000,10000) # Doesn't timeout

Any idea why that would be?

@hhaensel
Copy link
Member

hhaensel commented Jun 3, 2024

I could reproduce that and still don't know why. Interestingly, it works if you keep the wrapping @time macro

julia> @timeout 0.02 @time(fzeros(f,-10000,10000))
  0.074842 seconds (1.38 M allocations: 38.043 MiB, 5.59% gc time)
"Timed out"

@pw0908
Copy link
Author

pw0908 commented Jun 3, 2024

Really weird... Although in the above, it still computed the function and then timed-out. So it didn't do its job...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants