Martin
Martin

Reputation: 12215

How to infer type in static generic method with the type of the caller in Swift

I'm declaring this method on a protocol extention

protocol Storable { ... }

extention Storable {
    static func get<T: Decodable>(by identifier: String, completion: @escaping (T?) -> Void)
    ...
}

Now I'm using the method on a type which implements Storable.

struct User: Storable {
    ...
}

User.get(by: "userId", completion: { user in
    print(user)
} 

But the compiler says: Generic parameter 'T' could not be inferred

I want to tell to the compiler "T is the class who calls the static method"

I succeed to compile with :

static func get<T>(by identifier: String, type: T.Type, completion: @escaping (T?) -> Void) where T: Decodable

and 

User.get(by: "mprot", type: User.self) { ... }

But it seems redundant :(

Upvotes: 0

Views: 179

Answers (2)

Deryck Lucian
Deryck Lucian

Reputation: 475

T must not be optional. You should have:

static func get<T: Decodable>(by identifier: String, completion: @escaping (T) -> ())

been called

User.get(by: "userId", completion: { (value: User) in ... })

Upvotes: 0

OOPer
OOPer

Reputation: 47896

I want to tell to the compiler "T is the class who calls the static method"

Assuming you want to apply your get only when T is the class who calls the static method, how is this?

protocol Storable {
    //...
}

extension Storable where Self: Decodable {
    static func get(by identifier: String, completion: @escaping (Self?) -> Void) {
        //...
    }
}

struct User: Storable, Decodable {
    //...
}

This will be compiled successfully:

    User.get(by: "userId", completion: { user in
        print(user)
    })

Upvotes: 1

Related Questions