diff --git a/lib/elixir/lib/code/formatter.ex b/lib/elixir/lib/code/formatter.ex index c76f2be8704..366a8d8b275 100644 --- a/lib/elixir/lib/code/formatter.ex +++ b/lib/elixir/lib/code/formatter.ex @@ -506,6 +506,22 @@ defmodule Code.Formatter do quoted_to_algebra({:if, meta, [negate_condition(condition), block]}, context, state) end + # a |> b() |> unless(...) => a |> b() |> Kernel.!() |> unless(...) + defp quoted_to_algebra( + {:|>, meta1, [{:|>, _, _} = condition, {:unless, meta2, [block]}]}, + context, + %{migrate_unless: true} = state + ) do + negated_condition = {:|>, [], [condition, {{:., [], [Kernel, :!]}, [closing: []], []}]} + + quoted_to_algebra( + {:|>, meta1, [negated_condition, {:if, meta2, [block]}]}, + context, + state + ) + end + + # condition |> unless(...) => negated(condition) |> unless(...) defp quoted_to_algebra( {:|>, meta1, [condition, {:unless, meta2, [block]}]}, context, @@ -2516,7 +2532,6 @@ defmodule Code.Formatter do defp negate_condition(condition) do case condition do {neg, _, [condition]} when neg in [:!, :not] -> condition - {:|>, _, _} -> {:|>, [], [condition, {{:., [], [Kernel, :!]}, [closing: []], []}]} {op, _, [_, _]} when op in @bool_operators -> {:not, [], [condition]} {guard, _, [_ | _]} when guard in @guards -> {:not, [], [condition]} {:==, meta, [left, right]} -> {:!=, meta, [left, right]} diff --git a/lib/elixir/test/elixir/code_formatter/migration_test.exs b/lib/elixir/test/elixir/code_formatter/migration_test.exs index 42d0174220f..1f3978c45d5 100644 --- a/lib/elixir/test/elixir/code_formatter/migration_test.exs +++ b/lib/elixir/test/elixir/code_formatter/migration_test.exs @@ -242,6 +242,11 @@ defmodule Code.Formatter.MigrationTest do good = "x |> foo() |> Kernel.!() |> if(do: y)" assert_format bad, good, @opts + + bad = "unless x |> foo(), do: y" + good = "if !(x |> foo()), do: y" + + assert_format bad, good, @opts end test "rewrites in as not in" do