Fsharp: [Tooling] "Find usages" command does not work for public generic function with constraint by interface

Created on 3 Aug 2020  路  3Comments  路  Source: dotnet/fsharp

In Visual studio "Find usages" command does not find usages of public generic function, when one of its generic arguments is constrained by interface.

Steps to reproduce:

  1. Open Visual Studio 2019
  2. Use menu New -> Project -> Class Library (.NET Core, F#)
  3. Replace content of generated file Library.fs with following code:
module Module

[<Interface>] 
type IValueProvider = 
    abstract Value: int

let getValue (valueProvider: #IValueProvider) = 
    valueProvider.Value

let run () = 
    let valueProvider = { 
        new IValueProvider with
            member _.Value = 0 }
    getValue valueProvider
  1. Invoke command "Find usages" from context menu for function getValue.

Expected behavior

One usage from function run should be found

Actual behavior

No references found to getValue

Known workarounds

  1. Find usages manually, which is extremely inconvenient.
  2. Make target function private. Requires merging multiple modules in one, which is not acceptable in my case.

Related information

I was trying to solve problem of managing dependencies in functional way using approach described in article Dealing with complex dependency injection in F#. It works great for me, except for described issue, which significantly complicated navigation across code-base.

Used versions:

  • Windows 10.0.17763 Build 17763
  • .NET Core 3.1.6
  • Visual Studio 16.6.4
Area-IDE Language Service bug regression

All 3 comments

This is seems to be related to a similar problem I experienced with VS 16.7 for several functions in our codebase.

Here is a minimal repro: Paste the following contents into a new .NET Core F# class library's Library.fs:

module Mod

let gen (_: 'a) = ()
gen true

"Find all references" on the generic function gen does not show the usage in the line below, making gen private works.

Ugh, definitely an annoying bug here. Note that in an F# script file, both repros succeed and show the reference.

Was this page helpful?
0 / 5 - 0 ratings