@@ -483,14 +483,14 @@ defmodule ElixirSense.Providers.Definition.Locator do
483483 defp search_in_using_macro ( module , fun ) do
484484 case Location . find_mod_fun_source ( module , :__using__ , :any ) do
485485 % Location { file: file , line: using_line , column: using_col } when not is_nil ( file ) ->
486- search_function_in_using_macro ( file , using_line , using_col , fun )
486+ find_function_def_in_using_macro_source ( file , using_line , using_col , fun )
487487
488488 _ ->
489489 nil
490490 end
491491 end
492492
493- defp search_function_in_using_macro ( file , using_line , using_col , fun ) do
493+ defp find_function_def_in_using_macro_source ( file , using_line , using_col , fun ) do
494494 content = File . read! ( file )
495495 { _ , suffix } = Source . split_at ( content , using_line , using_col )
496496 regex = ~r/ def\s +(#{ Regex . escape ( Atom . to_string ( fun ) ) } \b )/
@@ -522,6 +522,17 @@ defmodule ElixirSense.Providers.Definition.Locator do
522522 |> then ( fn lines -> { length ( lines ) - 1 , String . length ( List . last ( lines ) || "" ) } end )
523523 end
524524
525+ defp fallback_location ( line , column , end_line , end_column , info ) do
526+ % Location {
527+ file: nil ,
528+ type: if ( info , do: ModFunInfo . get_category ( info ) , else: :function ) ,
529+ line: line ,
530+ column: column ,
531+ end_line: end_line ,
532+ end_column: end_column
533+ }
534+ end
535+
525536 defp find_function_in_using_macro ( metadata , env , line , column , end_line , end_column , fun , info ) do
526537 # This might be a function defined via `use`
527538 # We need to find the `use` statement and the module being used
@@ -536,67 +547,14 @@ defmodule ElixirSense.Providers.Definition.Locator do
536547 nil
537548 end
538549
539- case used_module do
540- nil ->
541- % Location {
542- file: nil ,
543- type: if ( info , do: ModFunInfo . get_category ( info ) , else: :function ) ,
544- line: line ,
545- column: column ,
546- end_line: end_line ,
547- end_column: end_column
548- }
550+ case used_module && Location . find_mod_fun_source ( used_module , :__using__ , :any ) do
551+ % Location { file: file , line: using_line , column: using_col } = using_location
552+ when not is_nil ( file ) ->
553+ find_function_def_in_using_macro_source ( file , using_line , using_col , fun ) ||
554+ using_location
549555
550- used_module ->
551- # Find __using__ macro in the used module
552- case Location . find_mod_fun_source ( used_module , :__using__ , :any ) do
553- % Location { file: file , line: using_line , column: using_col } = using_location
554- when not is_nil ( file ) ->
555- # Function is defined inside quote block, not as actual module function.
556- # Use regex to find def within __using__ source text.
557- content = File . read! ( file )
558- { _ , suffix } = Source . split_at ( content , using_line , using_col )
559-
560- regex = ~r/ def\s +(#{ Regex . escape ( Atom . to_string ( fun ) ) } \b )/
561-
562- case Regex . run ( regex , suffix , return: :index ) do
563- [ _entire_match , { fun_offset , _fun_len } ] ->
564- { line_offset , col_offset } =
565- suffix
566- |> String . slice ( 0 , fun_offset )
567- |> Source . split_lines ( )
568- |> then ( fn lines ->
569- { length ( lines ) - 1 , String . length ( List . last ( lines ) || "" ) }
570- end )
571-
572- target_line = using_line + line_offset
573-
574- target_column =
575- if line_offset == 0 , do: using_col + col_offset , else: 1 + col_offset
576-
577- % Location {
578- file: file ,
579- type: :function ,
580- line: target_line ,
581- column: target_column ,
582- end_line: target_line ,
583- end_column: target_column
584- }
585-
586- nil ->
587- using_location
588- end
589-
590- _ ->
591- % Location {
592- file: nil ,
593- type: if ( info , do: ModFunInfo . get_category ( info ) , else: :function ) ,
594- line: line ,
595- column: column ,
596- end_line: end_line ,
597- end_column: end_column
598- }
599- end
556+ _ ->
557+ fallback_location ( line , column , end_line , end_column , info )
600558 end
601559 end
602560end
0 commit comments