mirror of
https://github.com/livebook-dev/livebook.git
synced 2024-12-27 09:53:08 +08:00
Make failed evaluations preserve evaluation context (#145)
This commit is contained in:
parent
051156588d
commit
b3661ed2f0
2 changed files with 38 additions and 11 deletions
|
@ -121,19 +121,22 @@ defmodule Livebook.Evaluator do
|
|||
file = Keyword.get(opts, :file, "nofile")
|
||||
context = put_in(context.env.file, file)
|
||||
|
||||
case eval(code, context.binding, context.env) do
|
||||
{:ok, result, binding, env} ->
|
||||
result_context = %{binding: binding, env: env}
|
||||
new_contexts = Map.put(state.contexts, ref, result_context)
|
||||
new_state = %{state | contexts: new_contexts}
|
||||
{result_context, response} =
|
||||
case eval(code, context.binding, context.env) do
|
||||
{:ok, result, binding, env} ->
|
||||
result_context = %{binding: binding, env: env}
|
||||
response = {:ok, result}
|
||||
{result_context, response}
|
||||
|
||||
send_evaluation_response(send_to, ref, {:ok, result}, state.formatter)
|
||||
{:noreply, new_state}
|
||||
{:error, kind, error, stacktrace} ->
|
||||
response = {:error, kind, error, stacktrace}
|
||||
{context, response}
|
||||
end
|
||||
|
||||
{:error, kind, error, stacktrace} ->
|
||||
send_evaluation_response(send_to, ref, {:error, kind, error, stacktrace}, state.formatter)
|
||||
{:noreply, state}
|
||||
end
|
||||
send_evaluation_response(send_to, ref, response, state.formatter)
|
||||
|
||||
new_state = put_in(state.contexts[ref], result_context)
|
||||
{:noreply, new_state}
|
||||
end
|
||||
|
||||
def handle_cast({:forget_evaluation, ref}, state) do
|
||||
|
|
|
@ -109,6 +109,30 @@ defmodule Livebook.EvaluatorTest do
|
|||
end)
|
||||
end
|
||||
|
||||
test "in case of an error uses own evaluation context as the resulting context",
|
||||
%{evaluator: evaluator} do
|
||||
code1 = """
|
||||
x = 2
|
||||
"""
|
||||
|
||||
code2 = """
|
||||
raise ":<"
|
||||
"""
|
||||
|
||||
code3 = """
|
||||
x * x
|
||||
"""
|
||||
|
||||
Evaluator.evaluate_code(evaluator, self(), code1, :code_1)
|
||||
assert_receive {:evaluation_response, :code_1, {:ok, _}}
|
||||
|
||||
Evaluator.evaluate_code(evaluator, self(), code2, :code_2, :code_1)
|
||||
assert_receive {:evaluation_response, :code_2, {:error, _, _, _}}
|
||||
|
||||
Evaluator.evaluate_code(evaluator, self(), code3, :code_3, :code_2)
|
||||
assert_receive {:evaluation_response, :code_3, {:ok, 4}}
|
||||
end
|
||||
|
||||
test "given file option sets it in evaluation environment", %{evaluator: evaluator} do
|
||||
code = """
|
||||
__DIR__
|
||||
|
|
Loading…
Reference in a new issue