Home > database >  convenience method for combine publishers
convenience method for combine publishers

Time:08-27

I find myself wanting the same functionality in Combine quite often, so I wanted to make a convenience method like so...

public extension Published.Publisher {
    func sinkChanges(receiveValue: @escaping (Self.Output) -> Void) -> AnyCancellable {
        self.dropFirst()
            .removeDuplicates()
            .sink(receiveValue: closure)
    }
}

However I'm pretty new to the syntax and I get the error

Referencing instance method 'removeDuplicates()' on 'Publisher' requires that 'Publishers.Drop<Published<Value>.Publisher>.Output' (aka 'Value') conform to 'Equatable'

I understand why and what I have to do, just no idea syntactically where it goes...

My best guess so far was public extension Published.Publisher where Output: Equatable { but it didn't like that... what should I be searching for?

CodePudding user response:

TL;DR. Your best guess is correct.


As you might've noticed (and according to documentation), the method removeDuplicates() is only available, when Output conforms to Equatable. If you want to use this method in your extension, you must guarantee that. And to do that, you can add a constraint exactly as you described:

import Combine

public extension Published.Publisher where Output: Equatable {
  func sinkChanges(receiveValue: @escaping (Output) -> Void) -> AnyCancellable {
    dropFirst().removeDuplicates().sink(receiveValue: receiveValue)
  }
}

There's nothing wrong with extension constraints, it's a language feature. Here's one post about it.

  • Related