Skip to content

Commit 1878e30

Browse files
committed
Improve docs and support column in IO.warn, closes #13179
1 parent 88bbffd commit 1878e30

File tree

2 files changed

+47
-13
lines changed

2 files changed

+47
-13
lines changed

lib/elixir/lib/io.ex

Lines changed: 22 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -308,17 +308,20 @@ defmodule IO do
308308
entry from the compilation environment will be used
309309
310310
* a keyword list with at least the `:file` option representing
311-
a single stacktrace entry (since v1.14.0). The `:line`, `:module`,
312-
`:function` options are also supported
311+
a single stacktrace entry (since v1.14.0). The `:line`, `:column`,
312+
`:module`, and `:function` options are also supported
313313
314-
This function also notifies the compiler a warning was printed
315-
(in case --warnings-as-errors was enabled). It returns `:ok`
316-
if it succeeds.
314+
This function notifies the compiler a warning was printed
315+
and emits a compiler diagnostic (`t:Code.diagnostic/1`).
316+
The diagnostic will include precise file and location information
317+
if a `Macro.Env` is given or those values have been passed as
318+
keyword list, but not for stacktraces, as they are often imprecise.
319+
320+
It returns `:ok` if it succeeds.
317321
318322
## Examples
319323
320-
stacktrace = [{MyApp, :main, 1, [file: 'my_app.ex', line: 4]}]
321-
IO.warn("variable bar is unused", stacktrace)
324+
IO.warn("variable bar is unused", module: MyApp, function: {:main, 1}, line: 4, file: "my_app.ex")
322325
#=> warning: variable bar is unused
323326
#=> my_app.ex:4: MyApp.main/1
324327
@@ -337,15 +340,22 @@ defmodule IO do
337340

338341
def warn(message, [{_, _} | _] = keyword) do
339342
if file = keyword[:file] do
340-
warn(
341-
message,
342-
%{
343+
line = keyword[:line]
344+
column = keyword[:column]
345+
position = if line && column, do: {line, column}, else: line
346+
message = to_chardata(message)
347+
348+
stacktrace =
349+
Macro.Env.stacktrace(%{
343350
__ENV__
344351
| module: keyword[:module],
345352
function: keyword[:function],
346-
line: keyword[:line],
353+
line: line,
347354
file: file
348-
}
355+
})
356+
357+
:elixir_errors.emit_diagnostic(:warning, position, file, message, stacktrace,
358+
read_snippet: true
349359
)
350360
else
351361
warn(message, [])

lib/elixir/test/elixir/kernel/diagnostics_test.exs

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -769,6 +769,30 @@ defmodule Kernel.DiagnosticsTest do
769769
purge(Sample)
770770
end
771771

772+
@tag :tmp_dir
773+
test "IO.warn file+line", %{tmp_dir: tmp_dir} do
774+
path = make_relative_tmp(tmp_dir, "io-warn-file-line.ex")
775+
776+
source = """
777+
IO.warn("oops\\nmulti\\nline", file: __ENV__.file, line: __ENV__.line)
778+
"""
779+
780+
File.write!(path, source)
781+
782+
expected = """
783+
warning: oops
784+
multi
785+
line
786+
787+
1 │ IO.warn("oops\\nmulti\\nline", file: __ENV__.file, line: __ENV__.line)
788+
│ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
789+
790+
└─ tmp\
791+
"""
792+
793+
assert capture_io(:stderr, fn -> Code.eval_file(path) end) =~ expected
794+
end
795+
772796
@tag :tmp_dir
773797
test "IO.warn file+line+column", %{tmp_dir: tmp_dir} do
774798
path = make_relative_tmp(tmp_dir, "io-warn-file-line-column.ex")
@@ -785,7 +809,7 @@ defmodule Kernel.DiagnosticsTest do
785809
line
786810
787811
1 │ IO.warn("oops\\nmulti\\nline", file: __ENV__.file, line: __ENV__.line, column: 4)
788-
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
812+
~
789813
790814
└─ tmp\
791815
"""

0 commit comments

Comments
 (0)