- 
                Notifications
    
You must be signed in to change notification settings  - Fork 177
 
Description
To reproduce my issue, I created a simple sample with two files: ComplexView.swift and ComplexView+ViewModel.swift, along with a sample view unit test using ViewInspector. When I run the test, I see many warnings like:
"Accessing StateObject's object without being installed on a View. This will create a new instance each time.
"
import SwiftUI
struct ComplexView: View {
@StateObject var viewModel: ViewModel
public init() {
    _viewModel = StateObject(wrappedValue: ViewModel())
}
#if DEBUG
public init(viewModel: ViewModel) {
self._viewModel = StateObject(wrappedValue: viewModel)
}
#endif
var body: some View {
    VStack {
        TextField("Name", text: $viewModel.name)
        Stepper("Number", value: $viewModel.number)
        Button("Validate") {
            viewModel.validate()
        }
        if viewModel.isValid {
            Text("Valid!").foregroundColor(.green)
        } else {
            Text("Invalid").foregroundColor(.red)
        }
    }
}
}
import SwiftUI
extension ComplexView {
@mainactor final class ViewModel: ObservableObject  {
    // MARK: - Properties
    @Published var name: String = ""
    @Published var number: Int = 0
    @Published var isValid: Bool = false
    init() {}
    func validate() {
        isValid = !name.isEmpty && number > 0
    }
}
}
Then a simple unit test:
import XCTest
import SwiftUI
import ViewInspector
@mainactor
final class ComplexViewTests: XCTestCase {
func testComplexView() async throws {
    let viewModel = ComplexView.ViewModel()
    let view = ComplexView(viewModel: viewModel)
    try await ViewHosting.host(view) {
        let inspected = try view.inspect()
        let nameField = try inspected.find(ViewType.TextField.self)
        try nameField.setInput("Test")
        let stepper = try inspected.find(ViewType.Stepper.self)
        try stepper.increment()
        let button = try inspected.find(button: "Validate")
        try button.tap()
        let validText = try inspected.find(text: "Valid!")
        XCTAssertEqual(try validText.string(), "Valid!")
    }
}
}
When running this test, I get lots of warning:
Accessing StateObject's object without being installed on a View. This will create a new instance each time.
My view has both a default initializer and a debug/test initializer that accepts a view model, similar to the example above. I am using the async ViewHosting.host(_:whileHosted:) API from ViewInspector, but the warning still appears. Is there any way to avoid or suppress this warning when testing views with @StateObject using ViewInspector? Or is this a known limitation of SwiftUI and ViewInspector?
Any advice or workaround would be greatly appreciated!