What must be stored to keep a Combine subscription alive?
iOS interview question for Intermediate practice.
Answer
To keep a Combine subscription active and continuously receiving values from a publisher, you must store the AnyCancellable instance that is returned by terminating subscriber operators like .sink(...) or .assign(to:on:). Mechanism: When you subscribe using .sink or .assign, the operation returns an AnyCancellable object. This object controls the subscription's lifetime. As long as a strong reference to the AnyCancellable exists, the subscription remains active. If the AnyCancellable instance is deallocated (e.g., because the property storing it goes out of scope or the owning object is deallocated), it automatically cancels the subscription upon its deinit. Common Practice: Store the AnyCancellable instances in a collection property, typically a Set<AnyCancellable, within the class that owns the subscription (like a view model or view controller). swift import Combine class MyViewModel: ObservableObject { private var cancellables = Set<AnyCancellable() // Store subscriptions func setupSubscription(publisher: AnyPublisher<String, Never) { publisher .sink { value in print("Received: \(value)") } .store(in: &cancellables) // Store the AnyCancellable in the set } // When MyViewModel instance deinitializes, 'cancellables' // is destroyed, cancelling all stored subscriptions. } Forgetting to store the AnyCancellable will cause the subscription to be cancelled and deallocated almost immediately after it's created, meaning you likely won't receive any values.
Explanation
Storing AnyCancellable instances in a Set<AnyCancellable property is a common pattern. When the object owning the set is deallocated, the set is deallocated, automatically cancelling all stored subscriptions.