zachallaun/mneme

Use string multiline when newline available in string

Closed this issue · 2 comments

Hi,

Just try your library and it's awesome! Thanks for creating it.

I try this library with https://github.com/dagger/dagger/tree/main/sdk/elixir/dagger_codegen, it's a tool to generate code from GraphQL schema into Elixir. I use this library to make sure the codegen generated correctly. The minor issue is auto_assert just use string single after agree the changes, it cause a little bit hard to read (but better than write it by hand, for sure).

Here is the example.

defmodule Dagger.Codegen.ElixirGenerator.ObjectRendererTest do
  use ExUnit.Case, async: true
  use Mneme

  alias Dagger.Codegen.ElixirGenerator.ObjectRenderer

  test "generate a module" do
    auto_assert(
      "# This file generated by `dagger_codegen`. Please DO NOT EDIT.\ndefmodule Dagger.Client do\n  @moduledoc \"The root of the DAG.\"\n\n  use Dagger.Core.QueryBuilder\n\n  defstruct [:selection, :client]\n\n  @type t() :: %__MODULE__{}\n\n  @doc \"Create a new TypeDef.\"\n  @spec type_def(t()) :: Dagger.TypeDef.t()\n  def type_def(%__MODULE__{} = client) do\n    selection =\n      client.selection |> select(\"typeDef\")\n\n    %Dagger.TypeDef{\n      selection: selection,\n      client: client.client\n    }\n  end\nend" <-
        render_type(ObjectRenderer, "test/fixtures/objects/chain-selection.json")
    )
  end

  defp decode_type_from_file(path) do
    path
    |> File.read!()
    |> Jason.decode!()
    |> Nestru.decode_from_map!(Dagger.Codegen.Introspection.Types.Type)
  end

  defp render(type, renderer) do
    renderer.render(type)
    |> IO.iodata_to_binary()
    |> Code.format_string!()
    |> IO.iodata_to_binary()
  end

  defp render_type(renderer, path) do
    path
    |> decode_type_from_file()
    |> render(renderer)
  end
end

So my proposal is detecting newline in result and converting it to multiline string. I didn't find the solution yet but I'll find the time if you think it looks impossible.

Hi @wingyplus! Mneme should be offering two options in this case, one using a multiline string and one using a single line string. You can usually "scroll" through the options with j and k. Can you please confirm that this isn't available? If it's not suggesting the multiline variant, that's a bug!

Hi @wingyplus! Mneme should be offering two options in this case, one using a multiline string and one using a single line string. You can usually "scroll" through the options with j and k. Can you please confirm that this isn't available? If it's not suggesting the multiline variant, that's a bug!

Oh, I didn't recognize that keys. So I try j or k it show multiline version like this.

[1] New · test return object node (Dagger.Codegen.ElixirGenerator.ObjectRendererTest)
test/dagger/codegen/elixir_generator/object_renderer_test.exs:8

─old────────────────────────────────────────────────────────────────────────────────────────────────────┬─new────────────────────────────────────────────────────────────────────────────────────────────────────
  -  auto_assert(render_type(ObjectRenderer, "test/fixtures/objects/chain-selection.json"))             │  +  auto_assert(
  ·                                                                                                     │  +    """
  ·                                                                                                     │  +    # This file generated by `dagger_codegen`. Please DO NOT EDIT.
  ·                                                                                                     │  +    defmodule Dagger.Client do
  ·                                                                                                     │  +      @moduledoc "The root of the DAG."
  ·                                                                                                     │  +
  ·                                                                                                     │  +      use Dagger.Core.QueryBuilder
  ·                                                                                                     │  +
  ·                                                                                                     │  +      defstruct [:selection, :client]
  ·                                                                                                     │  +
  ·                                                                                                     │  +      @type t() :: %__MODULE__{}
  ·                                                                                                     │  +
  ·                                                                                                     │  +      @doc "Create a new TypeDef."
  ·                                                                                                     │  +      @spec type_def(t()) :: Dagger.TypeDef.t()
  ·                                                                                                     │  +      def type_def(%__MODULE__{} = client) do
  ·                                                                                                     │  +        selection =
  ·                                                                                                     │  +          client.selection |> select("typeDef")
  ·                                                                                                     │  +
  ·                                                                                                     │  +        %Dagger.TypeDef{
  ·                                                                                                     │  +          selection: selection,
  ·                                                                                                     │  +          client: client.client
  ·                                                                                                     │  +        }
  ·                                                                                                     │  +      end
  ·                                                                                                     │  +    end\
  ·                                                                                                     │  +    """ <- render_type(ObjectRenderer, "test/fixtures/objects/chain-selection.json")
  ·                                                                                                     │  +  )
─old────────────────────────────────────────────────────────────────────────────────────────────────────┴─new────────────────────────────────────────────────────────────────────────────────────────────────────

Accept new assertion?
> j
y yes  n no  s skip  ❮ j ○● k ❯

Looks nice! I think we can close the issue now. Thank you for your help.