defmodule CPSolver.Examples.Utils do
require Logger
def notify_client_handler() do
client = self()
fn solution -> send(client, {:solution, solution}) end
end
def wait_for_solution(timeout, solution_checker_fun) do
receive do
{:solution, solution} ->
solution
|> Enum.map(fn {_ref, s} -> s end)
|> then(fn sol -> solution_checker_fun.(sol) |> tap(fn res -> handle_checked(res) end) end)
after
timeout ->
handle_timeout()
end
|> tap(fn _ -> flush_solutions() end)
end
def wait_for_solutions(expected, timeout, solution_checker_fun) do
wait_for_solutions(expected, timeout, solution_checker_fun, 0)
end
def wait_for_solutions(0, _timeout, _solution_checker_fun, successes) do
successes
end
def wait_for_solutions(num, timeout, solution_checker_fun, successes) do
case wait_for_solution(timeout, solution_checker_fun) do
{:error, :timeout} ->
{:error, :timeout}
true ->
wait_for_solutions(num - 1, timeout, solution_checker_fun, successes + 1)
end
end
defp handle_timeout() do
Logger.error("Timed out :-(")
{:error, :timeout}
end
defp handle_checked(solution_checked?) do
(solution_checked? && Logger.notice("Solution checked!")) || Logger.error("Wrong solution!")
end
def flush_solutions() do
receive do
{:solution, _} -> flush_solutions()
after
0 -> :ok
end
end
end