You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Combine框架下sink如何忽略receiveValue仅监听completion回调

方案1:使用原生ignoreOutput操作符

你之前认为ignoreOutput不符合预期属于使用误区,ignoreOutput会将上游Publisher的Output类型映射为Never,此时Combine原生提供了仅接收完成事件的sink重载,完全符合你想要的调用形式:

CurrentValueSubject<Void, Error>(())
    .eraseToAnyPublisher()
    .ignoreOutput()
    .sink { completion in
        switch completion {
        case .failure(let error):
            print(error)
            print("FAILURE")
        case .finished:
            print("SUCCESS")
        }
    }

方案2:自定义Publisher扩展

如果你不想额外加ignoreOutput操作符,可以直接扩展Publisher实现仅处理完成事件的sink方法:

extension Publisher {
    func sink(completion: @escaping (Subscribers.Completion<Failure>) -> Void) -> AnyCancellable {
        return sink(
            receiveCompletion: completion,
            receiveValue: { _ in }
        )
    }
}

扩展后即可直接使用你理想中的调用形式,不需要额外中间操作:

CurrentValueSubject<Void, Error>(())
    .eraseToAnyPublisher()
    .sink { completion in
        switch completion {
        case .failure(let error):
            print(error)
            print("FAILURE")
        case .finished:
            print("SUCCESS ")
        }
    }

更适配场景的Publisher选型

你的场景是单次异步网络请求,仅存在成功/失败两种结果,不需要存储当前值,用Future比CurrentValueSubject更合适,不需要声明无意义的Void初始值:

// 网络请求封装示例
func requestNetwork() -> Future<Void, Error> {
    return Future { promise in
        // 此处替换为实际网络请求逻辑
        let isSuccess = Bool.random()
        if isSuccess {
            promise(.success(()))
        } else {
            promise(.failure(NSError(domain: "Network", code: -1, userInfo: nil)))
        }
    }
}

// 调用示例
requestNetwork()
    .ignoreOutput()
    .sink { completion in
        switch completion {
        case .failure(let error):
            print(error)
            print("FAILURE")
        case .finished:
            print("SUCCESS")
        }
    }

内容的提问来源于stack exchange,提问作者Richard Topchii

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 22:15:03