插入 SwiftData

问题描述 投票:0回答:1

我正在尝试编写一些代码,如果新项目尚不存在,则将其插入到 SwiftData 中。我遇到了关于

ModelContext
的错误,但我无法解决。

以下代码是精简版本,足以产生错误。我已经删除了测试现有项目的逻辑,直到我能够解决这个问题。

抱歉这么长:

import SwiftUI
import SwiftData

@Model
class TestData {
    @Attribute(.unique) var id: String
    var value: String
    init(id: String, value: String) {
        self.id = id
        self.value = value
    }
}

struct EditTestItem: View {
    @Bindable var testData: TestData
    var body: some View {
        VStack {
            HStack {
                Text($testData.id)
                TextField("Enter Data Here", text: $testData.value)
            }
        }
        .modelContainer(for: TestData.self)
    }
}

struct TestContent: View {
    var testIDValue: String = ""
    @Environment(\.modelContext) private var modelContext
    @Query var testData: [TestData]
    var testItem: TestData
        
    init(testID: String) {
        testItem = TestData(id: testID, value: "New value: \(testID)")

        let _ = modelContext.insert(testItem)
                    
        do {
            try modelContext.save()
        } catch {
            print("\(#line) oops")
        }
    }
        
    var body: some View {
        VStack {
            VStack {
                Text(testIDValue)
                Text("\(testData.count)")
                EditTestItem(testData: testItem)
            }
            Button("Save", action: {
                try? modelContext.save()
            })
        }
        .modelContainer(for: TestData.self)
        .onAppear {

        }
    }
}

#Preview {
    TestContent(testID: "b")
        .modelContainer(for: TestData.self)
        .frame(width: 400)
}

错误包括:

访问安装在视图之外的环境的值。这将始终读取默认值并且不会更新。

在视图环境中设置 .modelContext 以使用查询

肯定不是添加数据。

正确的做法是什么?

swiftui swiftdata
1个回答
0
投票

这是适合我的测试代码,将

TestData
替换为 我的
Product
模型仅供我测试。

struct ContentView: View {
    @Environment(\.modelContext) private var modelContext
    @Query var testData: [Product]
    
    var testIDValue: String = ""
    var testItem: Product
        
    init() {
        let testID: String = "12345" // <-- for testing
        testItem = Product(sku: testID, name: testID)
    }
        
    var body: some View {
        VStack {
            VStack {
                Text(testIDValue) // <--
                Text("\(testData.count)")
                EditTestItem(testData: testItem)
            }
            Button("Save", action: {
                do {
                    try modelContext.save()
                } catch {
                    print("\(#line) oops")
                }
            })
            List {
                ForEach(testData){ product in
                    Text(product.sku)
                }
            }
        }
        .modelContainer(for: Product.self)
        
        // .task {
        .onAppear {
            let _ = modelContext.insert(testItem)
            do {
                try modelContext.save()
            } catch {
                print("\(#line) oops")
            }
        }
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.