From 2b45b88335a102e6a9c98b8fbbf61a9ec71dbf3d Mon Sep 17 00:00:00 2001 From: Fons van der Plas Date: Mon, 23 Mar 2020 16:50:46 +0100 Subject: [PATCH] =?UTF-8?q?=F0=9F=8E=83=20Fix=20#32?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Project.toml | 2 +- src/react/ExploreExpression.jl | 13 +++++++++---- src/webserver/NotebookServer.jl | 28 ++++++++++++++++------------ test/ExploreExpression.jl | 2 ++ test/React.jl | 13 +++++++++++++ 5 files changed, 41 insertions(+), 17 deletions(-) diff --git a/Project.toml b/Project.toml index 1bba52f460..7c2858944a 100644 --- a/Project.toml +++ b/Project.toml @@ -2,7 +2,7 @@ name = "Pluto" uuid = "c3e4b0f8-55cb-11ea-2926-15256bba5781" license = "MIT" authors = ["Fons van der Plas ", "MikoĊ‚aj Bochenski "] -version = "0.3.5" +version = "0.3.6" [deps] HTTP = "cd3eb016-35fb-5094-929b-558a96fad6f3" diff --git a/src/react/ExploreExpression.jl b/src/react/ExploreExpression.jl index d73e88357f..393ee003a0 100644 --- a/src/react/ExploreExpression.jl +++ b/src/react/ExploreExpression.jl @@ -45,7 +45,7 @@ function get_global_assignees(assignee_exprs, scopestate::ScopeState) if ae.head == :(::) will_assign_global(ae.args[1], scopestate) && push!(global_assignees, ae.args[1]) else - @warn "Unknown assignee expression" + @warn "Unknown assignee expression" ae end end end @@ -117,7 +117,7 @@ function explore!(ex::Expr, scopestate::ScopeState)::SymbolsState elseif isa(ex.args[1], Expr) if ex.args[1].head == :tuple # (x, y) = (1, 23) - ex.args[1].args + filter(s -> s isa Symbol, ex.args[1].args) elseif ex.args[1].head == :(::) # TODO: type is referenced [ex.args[1].args[1]] @@ -134,9 +134,14 @@ function explore!(ex::Expr, scopestate::ScopeState)::SymbolsState # function f(x, y) x + y end return explore!(Expr(:function, ex.args...), scopestate) else - @warn "unknow use of =. Assignee is unrecognised." + @warn "unknow use of =. Assignee is unrecognised." ex.args[1] [] end + else + # When you assign to a datatype like Int, String, or anything bad like that + # e.g. 1 = 2 + # This is parsable code, so we have to treat it + [] end val = ex.args[2] @@ -363,7 +368,7 @@ function explore!(ex::Expr, scopestate::ScopeState)::SymbolsState end - function compute_symbolreferences(ex) +function compute_symbolreferences(ex) explore!(ex, ScopeState(true, Set{Symbol}(), Set{Symbol}())) end diff --git a/src/webserver/NotebookServer.jl b/src/webserver/NotebookServer.jl index 67ae3f1239..a060653afe 100644 --- a/src/webserver/NotebookServer.jl +++ b/src/webserver/NotebookServer.jl @@ -66,8 +66,9 @@ function flushclient(client) return false end end - catch e - @warn "Failed to write to WebSocket of $(client.id) " e + catch ex + bt = stacktrace(catch_backtrace()) + @warn "Failed to write to WebSocket of $(client.id) " exception=(ex,bt) return false end end @@ -171,26 +172,29 @@ function run(port = 1234, launchbrowser = false) @warn "Message of type $(messagetype) not recognised" end end - catch e - if e isa InterruptException - rethrow(e) - elseif e isa HTTP.WebSockets.WebSocketError + catch ex + if ex isa InterruptException + rethrow(ex) + elseif ex isa HTTP.WebSockets.WebSocketError # that's fine! - elseif e isa InexactError + elseif ex isa InexactError # that's fine! this is a (fixed) HTTP.jl bug: https://github.com/JuliaWeb/HTTP.jl/issues/471 # TODO: remove this switch else bt = stacktrace(catch_backtrace()) - @warn "Reading WebSocket client stream failed for unknown reason:" e bt + @warn "Reading WebSocket client stream failed for unknown reason:" exception=(ex,bt) end end end end - catch e - if e isa InterruptException - rethrow(e) + catch ex + if ex isa InterruptException + rethrow(ex) + elseif ex isa ArgumentError && occursin("stream is closed", ex.msg) + # that's fine! else - @info "HTTP upgrade failed, should be fine" e + bt = stacktrace(catch_backtrace()) + @warn "HTTP upgrade failed for unknown reason" exception=(ex,bt) end end else diff --git a/test/ExploreExpression.jl b/test/ExploreExpression.jl index aa2612cb3e..c563a62f92 100644 --- a/test/ExploreExpression.jl +++ b/test/ExploreExpression.jl @@ -66,6 +66,8 @@ end @test testee(:(x = let r = 1; r + r end), [:+], [:x]) @test testee(:(begin let r = 1; r + r end; r = 2 end), [:+], [:r]) @test testee(:(a, b = 1, 2), [], [:a, :b]) + @test testee(:((a, b) = 1, 2), [], [:a, :b]) + @test testee(:((a[1], b.r) = (1, 2)), [], []) @test testee(:((k = 2; 123)), [], [:k]) @test testee(:((a = 1; b = a + 1)), [:+], [:a, :b]) @test testee(:(let k = 2; 123 end), [], []) diff --git a/test/React.jl b/test/React.jl index 00c38783e2..565de6a770 100644 --- a/test/React.jl +++ b/test/React.jl @@ -21,6 +21,19 @@ import Pluto: Notebook, Client, run_reactive!,fakeclient, createcell_fromcode, @test notebook.cells[1].output == notebook.cells[2].output end + @testset "Bad code" begin + notebook = Notebook(joinpath(tempdir(), "test.jl"), [ + createcell_fromcode("a"), + createcell_fromcode("1 = 2") + ]) + fakeclient.connected_notebook = notebook + + @test_nowarn run_reactive!(fakeclient, notebook, notebook.cells[1]) + @test_nowarn run_reactive!(fakeclient, notebook, notebook.cells[2]) + @test notebook.cells[1].errormessage !== nothing + @test notebook.cells[2].errormessage !== nothing + end + @testset "Cyclic" begin notebook = Notebook(joinpath(tempdir(), "test.jl"), [ createcell_fromcode("x = y"),