jfmengels / review-unused / NoUnused.CustomTypeConstructors

Forbid having unused custom type constructors inside the project.

Rule

rule : List { moduleName : String, typeName : String, index : Basics.Int } -> Review.Rule.Rule

Forbid having unused custom type constructors.

config =
    [ NoUnused.CustomTypeConstructors.rule []
    ]

Note that this rule reports any custom type constructor that isn't used anywhere in the project.

If the project is a package and the module that declared the type is exposed and the type's constructors are exposed, then the constructors will not be reported.

This does not prevent you from using phantom types: A constructor won't be reported if

Note: At the time of writing, there may be cases where phantom types are not well detected. When an opaque type is defined in a dependency, we don't know whether a type variable should be considered as a phantom type.

Therefore, sometimes this rule will need some help, by having you tell it what type variables of which type is a phantom type variable. That's what the argument to the rule is for.

To explain that the a in type Id a = Id String from the IdModule module corresponds to a phantom type variable, you would configure the rule like this:

config =
    [ NoUnused.CustomTypeConstructors.rule
        [ { moduleName = "IdModule"
          , typeName = "Id"
          , index = 0 -- Position of the phantom variable in the type's arguments
          }
        ]
    ]

This rule could do a much better job than it currently does at figuring this out, by following the definitions of custom types and type aliases, until it finds out that the type variable is not used, or that it hits the limit related to dependencies described above. In the meantime, you can configure the rule with all the phantom type exceptions.

I would love help with improving this :)

Fail

module A exposing (a)

type MyType
    = UsedType
    | UnusedType -- Will get reported

a =
    UsedType

Success

module A exposing (ExposedType(..))

type MyType
    = UsedType

a =
    UsedType

type ExposedType
    = A
    | B
    | C

-----------------------
module A exposing (..)

type ExposedType
    = A
    | B
    | C