Combine AnyCancellable.store(in:) EXC_BAD_ACCESS

I'm seeing a strange and random crash with my combine networking after updating Xcode to version 14.3 (14E222b) a few days ago. The code below is crashing with EXC_BAD_ACCESS on .store(in:) and wasn't on the previous version of Xcode.

private var cancellables = Set<AnyCancellable>()

func request() async {
    URLSession.shared
        .dataTaskPublisher(for: URL(string: "")!)
        .map{$0.data}
        .decode(type: Type.self, decoder: JSONDecoder())
        .receive(on: DispatchQueue.main)
        .sink(receiveCompletion: {
            print ("Received completion: \($0).")
        }, receiveValue: { data in
            print(data)
        })
        .store(in: &cancellables) // <- CRASHING HERE
}

Answered by MobileTen in 749650022

Making request async is the issue. This version works without issue in playgrounds:

import UIKit
import Combine

struct User: Codable {
    let userId: Int
    let id: Int
    let title: String
    let completed: Bool
}

struct Download {
    private var cancellables = Set<AnyCancellable>()
    mutating func request() {
        URLSession.shared
            .dataTaskPublisher(for: URL(string: "https://jsonplaceholder.typicode.com/todos/1")!)
            .map{$0.data}
            .decode(type: User.self, decoder: JSONDecoder())
            .receive(on: DispatchQueue.main)
            .sink(receiveCompletion: {
                print ("Received completion: \($0).")
            }, receiveValue: { data in
                print(data)
            })
            .store(in: &cancellables) 
    }

}
    
var download = Download()
download.request()

or making request async as follows in playgrounds:

import UIKit
import Combine

struct User: Codable {
    let userId: Int
    let id: Int
    let title: String
    let completed: Bool
}

struct Download {
    private var cancellables = Set<AnyCancellable>()
    mutating func request() async -> User {
        
        return await withCheckedContinuation { continuation in
            
            URLSession.shared
                .dataTaskPublisher(for: URL(string: "https://jsonplaceholder.typicode.com/todos/1")!)
                .map{$0.data}
                .decode(type: User.self, decoder: JSONDecoder())
                .receive(on: DispatchQueue.main)
                .sink(receiveCompletion: {
                    print ("Received completion: \($0).")
                }, receiveValue: { data in
                        continuation.resume(returning: data)
                })
                .store(in: &cancellables)
        }
        
    }

}
    
Task {
    var download = Download()
    let  user = await download.request()
    print(user)
}
Accepted Answer

Making request async is the issue. This version works without issue in playgrounds:

import UIKit
import Combine

struct User: Codable {
    let userId: Int
    let id: Int
    let title: String
    let completed: Bool
}

struct Download {
    private var cancellables = Set<AnyCancellable>()
    mutating func request() {
        URLSession.shared
            .dataTaskPublisher(for: URL(string: "https://jsonplaceholder.typicode.com/todos/1")!)
            .map{$0.data}
            .decode(type: User.self, decoder: JSONDecoder())
            .receive(on: DispatchQueue.main)
            .sink(receiveCompletion: {
                print ("Received completion: \($0).")
            }, receiveValue: { data in
                print(data)
            })
            .store(in: &cancellables) 
    }

}
    
var download = Download()
download.request()

or making request async as follows in playgrounds:

import UIKit
import Combine

struct User: Codable {
    let userId: Int
    let id: Int
    let title: String
    let completed: Bool
}

struct Download {
    private var cancellables = Set<AnyCancellable>()
    mutating func request() async -> User {
        
        return await withCheckedContinuation { continuation in
            
            URLSession.shared
                .dataTaskPublisher(for: URL(string: "https://jsonplaceholder.typicode.com/todos/1")!)
                .map{$0.data}
                .decode(type: User.self, decoder: JSONDecoder())
                .receive(on: DispatchQueue.main)
                .sink(receiveCompletion: {
                    print ("Received completion: \($0).")
                }, receiveValue: { data in
                        continuation.resume(returning: data)
                })
                .store(in: &cancellables)
        }
        
    }

}
    
Task {
    var download = Download()
    let  user = await download.request()
    print(user)
}

I'm not having an issue while using async in another project I'm working on using a different API. The application it's crashing on never experienced this before, but after the recent update to Xcode it's crashing. It's not a constant crash, it's not predictable.

Combine AnyCancellable.store(in:) EXC_BAD_ACCESS
 
 
Q