Compiler errors when instance and class symbols collide

I ran into something super confusing in my Swift Vapor app today. Fluent uses FieldKey to make column naming type-safe. It also conforms to CustomStringConvertible, adding a description property to FieldKey.

I created a FieldKey named description:

extension
FieldKey
{
	static var	menuID			:	Self { "menuID" }
	static var	description		:	Self { "description" }
}

Which has worked great, until I needed the string from another key for use in the raw SQL API, which doesn't use FieldKey. I was trying to write FieldKey.menuID.description, something that seems completely unambiguous and reasonable.

But the compiler didn’t like it: “Static member 'description' cannot be used on instance of type 'FieldKey'”. Took me 20 minutes to figure out why that wasn’t working.

Given that I can't access static members on an instance variable normally, why is it thinking that’s what I'm trying to do?

Is this a bug, or a deliberate design decision? If the latter, why? Could it be changed?

Hello!

This looks like a bug to me. I've managed to reproduce the error with a minimal example:

// Library

public struct SomeStruct {
    public init() { }
}

extension SomeStruct {
//    public static var description: Int { 42 }
    public var description: String {
        "description"
    }
}

// Program

import Library

@main
struct Program {
    static func main() {
        let staticDescription = SomeStruct.description
        let instanceDescription = SomeStruct().description // ERROR: Static member 'description' cannot be used on instance of type 'SomeStruct'
    }
}

extension SomeStruct {
    static var description: Int { 42 }
    
//    var description: String {
//        "description"
//    }
}

The key detail is that static and instance declarations must be in different modules. If we swap them around (move static property into the library and instance one into the program), it's the staticDescription line that fails instead. If we put both into either library or program, the program compiles successfully. Reproduced on 6.3.2 and the latest main snapshot.

Package with reproduction

I'm sure it's a good idea to report an issue. Even if this behavior is deliberate (which I highly doubt), the diagnostic is misleading.