Swiftui 如何获取用于iOS 14小部件的HomeKit值?

Swiftui 如何获取用于iOS 14小部件的HomeKit值?,swiftui,ios14,entitlements,homekit,widgetkit,Swiftui,Ios14,Entitlements,Homekit,Widgetkit,我正在编写一个HomeKit应用程序,它成功地在应用程序中显示我支持的附件的实时数据。我可以读取单个值(HMCharacteristic.readValue)或使用通知保持更新(HMCharacteristic.enableNotification) 现在我想实现在用户主屏幕上显示这些数据的小部件。这包括四个步骤: 动态意图从HMHomeManager获取所有注册(和支持的)附件,并允许用户选择其中一个显示在小部件上 在IntentTimelineProvider的getTimeline功能中,

我正在编写一个HomeKit应用程序,它成功地在应用程序中显示我支持的附件的实时数据。我可以读取单个值(
HMCharacteristic.readValue
)或使用通知保持更新(
HMCharacteristic.enableNotification

现在我想实现在用户主屏幕上显示这些数据的小部件。这包括四个步骤:

  • 动态意图从
    HMHomeManager
    获取所有注册(和支持的)附件,并允许用户选择其中一个显示在小部件上
  • IntentTimelineProvider
    getTimeline
    功能中,我可以再次使用
    HMHomeManager
    检索我要在小部件上显示的附件(基于附件的UUID,该UUID存储在
    getTimeline
    配置
    参数中-意图)
  • 仍然在
    getTimeline
    功能中,我可以从
    HMHomeManager
    中选择显示附件小部件所需的服务和特性
  • 直到这里一切都很好

  • 但是,当我尝试从使用
    HMCharacteristic.readValue
    之前选择的特征中读取值时,回调包含一个错误声明
  • Error Domain=HMErrorDomain Code=80“缺少API的权限。”

    小部件的Info.plist包含“隐私-HomeKit使用说明”字段,目标具有HomeKit功能

    经过一些研究,我提出了以下理论:显然,整个WidgetKitAPI都在后台运行我的代码。而且HomeKit似乎不允许从后台环境进行访问。嗯,它确实允许访问家庭/服务/特征,但不允许对特征进行读写(我想是为了确保应用程序开发人员使用HomeKit自动化,而不是试图实现由iPhone上运行的应用程序的某些后台进程控制的自定义自动化)

    我的(简化)
    getTimeline
    code:

    func getTimeline(for configuration: SelectAccessoryIntent, in context: Context, completion: @escaping (Timeline<Entry>) -> ()) {
            // id stores the uuid of the accessory that was chosen by the user using the dynamic Intent
            if let id = configuration.accessory?.identifier {
                // Step 2.: fetch the accessory
                // hm is a HMHomeManager
                let hm = HomeStore.shared.homeManager
                // take a short nap until the connection to the local HomeKit instance is established (otherwise hm.homes will create an empty array on first call)
                sleep(1)
                
                let accessories = hm.homes.flatMap({ h in h.accessories })
                
                if let a = accessories.filter({ a in a.uniqueIdentifier.uuidString == id }).first {
                    // a holds our HMAccessory
                    
                    // Step 3.: select the characteristic I want
                    // obviously the real code chooses a specific characteristic
                    let s: HMService = a.services.first!
                    let c: HMCharacteristic = s.characteristics.first!
                    
                    // Step 4.: read the characteristic's value
                    c.readValue(completionHandler: {err in
                        if let error = err {
                            print(error)
                        } else {
                            print(c.value ?? "nil")
                        }
                        
                        // complete with timeline
                        completion(Timeline(entries: [RenderAccessoryEntry(date: Date(), configuration: configuration, value: c.value)], policy: .atEnd))
                    })
                }
            }
        }
    }
    
    func getTimeline(对于配置:SelectAccessoryIntent,在context:context中,完成:@escaping(Timeline)->()){
    //id存储用户使用动态意图选择的附件的uuid
    如果let id=配置.附件?.标识符{
    //步骤2:取出附件
    //hm是一名家庭经理
    设hm=HomeStore.shared.homeManager
    //在与本地HomeKit实例建立连接之前小睡片刻(否则hm.homes将在第一次调用时创建一个空数组)
    睡眠(1)
    let accessories=hm.homes.flatMap({h in h.accessories})
    如果让a=accessories.filter({a in a.uniqueIdentifier.uuidString==id}){
    //a装着我们的配件
    //步骤3:选择我想要的特征
    //显然,真正的代码选择了一个特定的特性
    让我们:HMService=a.services.first!
    让c:HMCharacteristic=s.characteristics.first!
    //步骤4:读取特征值
    c、 readValue(completionHandler:{err in
    如果let error=err{
    打印(错误)
    }否则{
    打印(c.值??“零”)
    }
    //完成时间线
    完成(时间线(条目:[RenderAccessoryEntry(日期(),配置:配置,值:c.value)],策略:.atEnd))
    })
    }
    }
    }
    }
    
    我的问题是:

    第一:我的理论正确吗

    如果是:我能做什么?是否有任何权利允许我在后台或类似情况下访问HomeKit?我是否需要在别处执行
    readValue
    调用?或者,在当前版本的HomeKit/WidgetKit/iOS中使用HomeKit API和WidgetKit是不可能的,我能做的最好的事情就是希望他们在将来的某个时候引入此功能


    如果没有:我缺少什么?

    家庭工具包的权利似乎没有资格在后台获取请参见:听到这个消息很难过,但谢谢分享。我想我们最好还是等一等。。。