Skip to content

Commit 0873535

Browse files
quexplmhanberg
andauthored
feat(dev_server): error page for compile and build errors (#120)
Co-authored-by: Mitchell Hanberg <[email protected]>
1 parent 15c7e58 commit 0873535

File tree

5 files changed

+63
-12
lines changed

5 files changed

+63
-12
lines changed

lib/mix/tasks/tableau.build.ex

+13-5
Original file line numberDiff line numberDiff line change
@@ -44,12 +44,20 @@ defmodule Mix.Tasks.Tableau.Build do
4444
pages =
4545
pages
4646
|> Task.async_stream(fn {mod, page} ->
47-
content = Tableau.Document.render(graph, mod, token, page)
48-
permalink = Nodable.permalink(mod)
49-
50-
Map.merge(page, %{body: content, permalink: permalink})
47+
try do
48+
content = Tableau.Document.render(graph, mod, token, page)
49+
permalink = Nodable.permalink(mod)
50+
51+
Map.merge(page, %{body: content, permalink: permalink})
52+
rescue
53+
exception ->
54+
reraise TableauDevServer.BuildException, [page: page, exception: exception], __STACKTRACE__
55+
end
56+
end)
57+
|> Stream.map(fn
58+
{:ok, result} -> result
59+
{:exit, {exception, stacktrace}} -> reraise exception, stacktrace
5160
end)
52-
|> Stream.map(fn {:ok, result} -> result end)
5361
|> Enum.to_list()
5462

5563
token = put_in(token.site[:pages], pages)
+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
defmodule TableauDevServer.BuildException do
2+
@moduledoc false
3+
@type t :: %__MODULE__{
4+
page: map(),
5+
exception: any()
6+
}
7+
8+
defexception [:page, :exception]
9+
10+
@impl true
11+
def exception(page: page, exception: exception) do
12+
%__MODULE__{page: page, exception: exception}
13+
end
14+
15+
@impl true
16+
def message(%__MODULE__{page: page, exception: exception}) do
17+
exception = String.replace(exception, ~r/\x1B\[[0-9;]*m/, "")
18+
19+
"""
20+
An exception was raised:
21+
#{Exception.format_banner(:error, exception)}
22+
23+
occurred during the build process on the page:
24+
#{inspect(page, pretty: true)}
25+
"""
26+
end
27+
end

lib/tableau_dev_server/router.ex

+20-4
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
defmodule TableauDevServer.Router do
22
@moduledoc false
33
use Plug.Router, init_mode: :runtime
4+
use Plug.Debugger
45

56
require Logger
67

@@ -32,11 +33,26 @@ defmodule TableauDevServer.Router do
3233
end
3334

3435
defp recompile(conn, _) do
35-
if conn.request_path != "/ws" do
36-
WebDevUtils.CodeReloader.reload()
37-
end
36+
if conn.request_path == "/ws" do
37+
conn
38+
else
39+
case WebDevUtils.CodeReloader.reload() do
40+
{:error, errors} ->
41+
errors = Enum.filter(errors, &(&1.severity == :error))
3842

39-
conn
43+
message =
44+
errors
45+
|> Enum.map_join("\n", & &1.message)
46+
|> String.replace(~r/\x1B\[[0-9;]*m/, "")
47+
48+
stacktrace = List.first(errors).stacktrace
49+
50+
reraise CompileError, [description: message], stacktrace
51+
52+
_ ->
53+
conn
54+
end
55+
end
4056
end
4157

4258
defp rerender(conn, _) do

mix.exs

+1-1
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@ defmodule Tableau.MixProject do
4242
{:plug_static_index_html, "~> 1.0"},
4343
{:schematic, "~> 0.4"},
4444
{:tz, "~> 0.28.1"},
45-
{:web_dev_utils, "~> 0.2"},
45+
{:web_dev_utils, "~> 0.3"},
4646
{:websock_adapter, "~> 0.5"},
4747
{:xml_builder, "~> 2.1"},
4848
{:yaml_elixir, "~> 2.9"},

mix.lock

+2-2
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
"date_time_parser": {:hex, :date_time_parser, "1.2.0", "3d5a816b91967f51e0f94dcb16a34b2cb780f22cd48931779e81d72f7d3eadb1", [:mix], [{:kday, "~> 1.0", [hex: :kday, repo: "hexpm", optional: false]}], "hexpm", "0cf09ada9f42c0b3bfba02dc0ea2e4b4d2f543d9d2bf99b831a29e6b4a4160e5"},
55
"earmark_parser": {:hex, :earmark_parser, "1.4.41", "ab34711c9dc6212dda44fcd20ecb87ac3f3fce6f0ca2f28d4a00e4154f8cd599", [:mix], [], "hexpm", "a81a04c7e34b6617c2792e291b5a2e57ab316365c2644ddc553bb9ed863ebefa"},
66
"ex_doc": {:hex, :ex_doc, "0.34.2", "13eedf3844ccdce25cfd837b99bea9ad92c4e511233199440488d217c92571e8", [:mix], [{:earmark_parser, "~> 1.4.39", [hex: :earmark_parser, repo: "hexpm", optional: false]}, {:makeup_c, ">= 0.1.0", [hex: :makeup_c, repo: "hexpm", optional: true]}, {:makeup_elixir, "~> 0.14 or ~> 1.0", [hex: :makeup_elixir, repo: "hexpm", optional: false]}, {:makeup_erlang, "~> 0.1 or ~> 1.0", [hex: :makeup_erlang, repo: "hexpm", optional: false]}, {:makeup_html, ">= 0.1.0", [hex: :makeup_html, repo: "hexpm", optional: true]}], "hexpm", "5ce5f16b41208a50106afed3de6a2ed34f4acfd65715b82a0b84b49d995f95c1"},
7-
"file_system": {:hex, :file_system, "1.0.1", "79e8ceaddb0416f8b8cd02a0127bdbababe7bf4a23d2a395b983c1f8b3f73edd", [:mix], [], "hexpm", "4414d1f38863ddf9120720cd976fce5bdde8e91d8283353f0e31850fa89feb9e"},
7+
"file_system": {:hex, :file_system, "1.1.0", "08d232062284546c6c34426997dd7ef6ec9f8bbd090eb91780283c9016840e8f", [:mix], [], "hexpm", "bfcf81244f416871f2a2e15c1b515287faa5db9c6bcf290222206d120b3d43f6"},
88
"floki": {:hex, :floki, "0.36.2", "a7da0193538c93f937714a6704369711998a51a6164a222d710ebd54020aa7a3", [:mix], [], "hexpm", "a8766c0bc92f074e5cb36c4f9961982eda84c5d2b8e979ca67f5c268ec8ed580"},
99
"hpax": {:hex, :hpax, "1.0.0", "28dcf54509fe2152a3d040e4e3df5b265dcb6cb532029ecbacf4ce52caea3fd2", [:mix], [], "hexpm", "7f1314731d711e2ca5fdc7fd361296593fc2542570b3105595bb0bc6d0fad601"},
1010
"html_entities": {:hex, :html_entities, "0.5.2", "9e47e70598da7de2a9ff6af8758399251db6dbb7eebe2b013f2bbd2515895c3c", [:mix], [], "hexpm", "c53ba390403485615623b9531e97696f076ed415e8d8058b1dbaa28181f4fdcc"},
@@ -25,7 +25,7 @@
2525
"telemetry": {:hex, :telemetry, "1.3.0", "fedebbae410d715cf8e7062c96a1ef32ec22e764197f70cda73d82778d61e7a2", [:rebar3], [], "hexpm", "7015fc8919dbe63764f4b4b87a95b7c0996bd539e0d499be6ec9d7f3875b79e6"},
2626
"thousand_island": {:hex, :thousand_island, "1.3.5", "6022b6338f1635b3d32406ff98d68b843ba73b3aa95cfc27154223244f3a6ca5", [:mix], [{:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "2be6954916fdfe4756af3239fb6b6d75d0b8063b5df03ba76fd8a4c87849e180"},
2727
"tz": {:hex, :tz, "0.28.1", "717f5ffddfd1e475e2a233e221dc0b4b76c35c4b3650b060c8e3ba29dd6632e9", [:mix], [{:castore, "~> 0.1 or ~> 1.0", [hex: :castore, repo: "hexpm", optional: true]}, {:mint, "~> 1.6", [hex: :mint, repo: "hexpm", optional: true]}], "hexpm", "bfdca1aa1902643c6c43b77c1fb0cb3d744fd2f09a8a98405468afdee0848c8a"},
28-
"web_dev_utils": {:hex, :web_dev_utils, "0.2.0", "3bcd109d1ac18445d06db095d5cfdca5de7586022641c0b09b0702788b8e4ea8", [:mix], [{:file_system, "~> 1.0", [hex: :file_system, repo: "hexpm", optional: false]}], "hexpm", "595e9bd35440ea2add0156ae9e68e578d986805d801dacf22b13067ca48980ed"},
28+
"web_dev_utils": {:hex, :web_dev_utils, "0.3.0", "463f3695dcdee9a6f18dbc783ee76f0ecdd1c9a489a6482aadcf166b3e5fee12", [:mix], [{:file_system, "~> 1.0", [hex: :file_system, repo: "hexpm", optional: false]}], "hexpm", "c239d4d24bfc61110a98b7d75bb7bbbb1752a5d8fcb5a2d369c5d4f64d1d7aec"},
2929
"websock": {:hex, :websock, "0.5.3", "2f69a6ebe810328555b6fe5c831a851f485e303a7c8ce6c5f675abeb20ebdadc", [:mix], [], "hexpm", "6105453d7fac22c712ad66fab1d45abdf049868f253cf719b625151460b8b453"},
3030
"websock_adapter": {:hex, :websock_adapter, "0.5.7", "65fa74042530064ef0570b75b43f5c49bb8b235d6515671b3d250022cb8a1f9e", [:mix], [{:bandit, ">= 0.6.0", [hex: :bandit, repo: "hexpm", optional: true]}, {:plug, "~> 1.14", [hex: :plug, repo: "hexpm", optional: false]}, {:plug_cowboy, "~> 2.6", [hex: :plug_cowboy, repo: "hexpm", optional: true]}, {:websock, "~> 0.5", [hex: :websock, repo: "hexpm", optional: false]}], "hexpm", "d0f478ee64deddfec64b800673fd6e0c8888b079d9f3444dd96d2a98383bdbd1"},
3131
"xml_builder": {:hex, :xml_builder, "2.3.0", "69d214c6ad41ae1300b36acff4367551cdfd9dc1b860affc16e103c6b1589053", [:mix], [], "hexpm", "972ec33346a225cd5acd14ab23d4e79042bd37cb904e07e24cd06992dde1a0ed"},

0 commit comments

Comments
 (0)