@@ -317,17 +317,25 @@ defmodule Module.Types.Expr do
317317 |> dynamic_unless_static ( stack )
318318 end
319319
320- def of_expr ( { :case , meta , [ _case_expr , [ { :do , _clauses } ] ] } , _expected , _expr , stack , context )
320+ def of_expr ( { :case , meta , [ case_expr , [ { :do , _clauses } ] ] } , expected , _expr , stack , context )
321321 when stack . reverse_arrow == :use do
322322 version = Keyword . fetch! ( meta , :version )
323323 clauses = Map . fetch! ( context . reverse_arrows , version )
324- result = Enum . reduce ( clauses , none ( ) , & union ( elem ( & 1 , 1 ) , & 2 ) )
325- dynamic_unless_static ( { result , context } , stack )
324+
325+ case_expected =
326+ Enum . reduce ( clauses , none ( ) , fn { arg_type , body_type } , acc ->
327+ if disjoint? ( body_type , expected ) do
328+ acc
329+ else
330+ union ( arg_type , acc )
331+ end
332+ end )
333+
334+ { _ , context } = of_expr ( case_expr , case_expected , case_expr , stack , context )
335+ { expected , context }
326336 end
327337
328338 def of_expr ( { :case , meta , [ case_expr , [ { :do , clauses } ] ] } , expected , _expr , stack , base_context ) do
329- version = Keyword . fetch! ( meta , :version )
330-
331339 { case_type , context } =
332340 of_expr ( case_expr , term ( ) , case_expr , % { stack | reverse_arrow: :cache } , base_context )
333341
@@ -360,7 +368,7 @@ defmodule Module.Types.Expr do
360368 end
361369
362370 result_context =
363- cache_arrows ( version , stack , fn ->
371+ cache_arrows ( meta , stack , fn ->
364372 of_clauses_fun ( clauses , [ case_type ] , info , stack , context , of_body , [ ] , fn
365373 trees , body_type , context , acc ->
366374 [ arg_type ] = Pattern . of_domain ( trees , stack , context )
@@ -767,10 +775,11 @@ defmodule Module.Types.Expr do
767775 defp dynamic_unless_static ( { _ , _ } = output , % { mode: :static } ) , do: output
768776 defp dynamic_unless_static ( { type , context } , % { mode: _ } ) , do: { dynamic ( type ) , context }
769777
770- defp cache_arrows ( _version , % { reverse_arrow: nil } , _fun ) , do: nil
778+ defp cache_arrows ( _meta , % { reverse_arrow: nil } , _fun ) , do: nil
771779
772- defp cache_arrows ( version , % { reverse_arrow: :cache } , fun ) do
780+ defp cache_arrows ( meta , % { reverse_arrow: :cache } , fun ) do
773781 { clauses , context } = fun . ( )
782+ version = Keyword . fetch! ( meta , :version )
774783 context = put_in ( context . reverse_arrows [ version ] , clauses )
775784 result = Enum . reduce ( clauses , none ( ) , & union ( elem ( & 1 , 1 ) , & 2 ) )
776785 { result , context }
0 commit comments