Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mimic.allow raises if no expectations #83

Open
michaelst opened this issue Oct 2, 2024 · 0 comments
Open

Mimic.allow raises if no expectations #83

michaelst opened this issue Oct 2, 2024 · 0 comments

Comments

@michaelst
Copy link
Contributor

michaelst commented Oct 2, 2024

Here is the error

     20:57:32.287 [error] GenServer Mimic.Server terminating
     ** (CaseClauseError) no case clause matching: []
         (mimic 1.10.1) lib/mimic/server.ex:402: Mimic.Server.handle_call/3
         (stdlib 5.2.3) gen_server.erl:1131: :gen_server.try_handle_call/4
         (stdlib 5.2.3) gen_server.erl:1160: :gen_server.handle_msg/6
         (stdlib 5.2.3) proc_lib.erl:241: :proc_lib.init_p_do_apply/3
     Last message (from #PID<0.619.0>): {:allow, Auth.ApiKeys, #PID<0.604.0>, #PID<0.619.0>}
     20:57:32.294 [error] ** (exit) exited in: GenServer.call(Mimic.Server, {:allow, Auth.ApiKeys, #PID<0.604.0>, #PID<0.619.0>}, 5000)
         ** (EXIT) an exception was raised:
             ** (CaseClauseError) no case clause matching: []
                 (mimic 1.10.1) lib/mimic/server.ex:402: Mimic.Server.handle_call/3
                 (stdlib 5.2.3) gen_server.erl:1131: :gen_server.try_handle_call/4
                 (stdlib 5.2.3) gen_server.erl:1160: :gen_server.handle_msg/6
                 (stdlib 5.2.3) proc_lib.erl:241: :proc_lib.init_p_do_apply/3
         (elixir 1.16.2) lib/gen_server.ex:1114: GenServer.call/3
         (mimic 1.10.1) lib/mimic.ex:342: Mimic.allow/3
         (auth 0.1.0) test/support/grpc_test_allowance.ex:23: AuthGRPC.Interceptors.TestAllowance.call/4
         (grpc 0.9.0) lib/grpc/telemetry.ex:96: anonymous fn/2 in GRPC.Telemetry.server_span/5
         (telemetry 1.2.1) /Users/michael/code/auth/deps/telemetry/src/telemetry.erl:321: :telemetry.span/3
         (grpc 0.9.0) lib/grpc/telemetry.ex:95: GRPC.Telemetry.server_span/5
         (grpc 0.9.0) lib/grpc/server/adapters/cowboy/handler.ex:532: GRPC.Server.Adapters.Cowboy.Handler.do_call_rpc/3
         (grpc 0.9.0) lib/grpc/server/adapters/cowboy/handler.ex:505: GRPC.Server.Adapters.Cowboy.Handler.call_rpc/3
         (stdlib 5.2.3) proc_lib.erl:241: :proc_lib.init_p_do_apply/3

Reproduce steps:
We have an interceptor that reads the test pid from headers so we can call allow on multiple modules. However, not every module is used in every test case.

defmodule AuthGRPC.Interceptors.TestAllowance do
  @behaviour GRPC.Server.Interceptor

  def init(opts) do
    opts
  end

  def call(req, stream, next, _opts) do
    %{"test_pid" => string_pid} = GRPC.Stream.get_headers(stream)

    test_pid =
      string_pid
      |> String.to_charlist()
      |> :erlang.list_to_pid()

    Mimic.allow(Auth.ApiKeys, test_pid, self())
    Mimic.allow(Auth.OneTimeAccess, test_pid, self())
    Mimic.allow(Auth.Signing, test_pid, self())
    Mimic.allow(Auth.User, test_pid, self())

    next.(req, stream)
  end
end

We have this in our GRPC test case setup block

{:ok, channel} =
  GRPC.Stub.connect("localhost:50052",
    headers: [{"authorization", "Bearer m2m-jwt"}, {"test_pid", :erlang.pid_to_list(self())}]
  )

Then if you write a test that doesn't call Mimic.expect for all 4 it will raise, for example the below test will raise on Mimic.allow(Auth.OneTimeAccess, test_pid, self()).

defmodule AuthGRPC.ApiKeys.ApiKeyServiceTest do
  use AuthGRPC.GRPCCase, async: true

  alias AuthGRPC.ApiKeys.Utils
  alias Protos.Grpc.Auth.ApiKeys.V1, as: Messages
  alias Protos.Grpc.Auth.ApiKeys.V1.ApiKeysService.Stub

  test "get_api_keys/2", %{channel: channel} do
    %{id: account_id} = account = build(:account)
    api_key = build(:api_key, account: account)
    request = %Messages.GetApiKeysRequest{account_id: account_id}

    Auth.Signing
    |> expect(:verify_m2m_token, fn "m2m-jwt" ->
      {:ok, %{"aud" => "auth", "kind" => "m2m"}}
    end)

    Auth.User
    |> expect(:get_or_create_account, fn ^ account_id ->
      {:ok, account}
    end)

    Auth.ApiKeys
    |> expect(:list, fn ^account_id ->
      [api_key]
    end)

    formatted_api_key = Utils.format_api_key(api_key)

    {:ok, %Messages.GetApiKeysResponse{api_keys: [^formatted_api_key]}} = Stub.get_api_keys(channel, request)
  end

Fix in: #82

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant