HealthKit no Xamarin.iOS

O Health Kit fornece um armazenamento de dados seguro para as informações relacionadas à saúde do usuário. Os aplicativos do Health Kit podem, com a permissão explícita do usuário, ler e gravar nesse armazenamento de dados e receber notificações quando dados pertinentes forem adicionados. Os aplicativos podem apresentar os dados ou os usuários podem usar o aplicativo Health fornecido pela Apple para visualizar um painel de todos os seus dados.

Como os dados relacionados à saúde são tão sensíveis e cruciais, o Health Kit é fortemente tipado, com unidades de medida e uma associação explícita com o tipo de informação que está sendo registrada (por exemplo, nível de glicose no sangue ou frequência cardíaca). Além disso, os aplicativos do Health Kit devem usar direitos explícitos, devem solicitar acesso aos tipos específicos de informações e o usuário deve conceder explicitamente ao aplicativo acesso a esses tipos de dados.

Este artigo apresentará:

  • Requisitos de segurança do Health Kit, incluindo provisionamento de aplicativos e solicitação de permissão do usuário para acessar o banco de dados do Health Kit;
  • Sistema de tipos do Health Kit, que minimiza a possibilidade de aplicação ou interpretação incorreta dos dados;
  • Gravando no repositório de dados compartilhado do Health Kit em todo o sistema.

Este artigo não abordará tópicos mais avançados, como consultar o banco de dados, converter entre unidades de medida ou receber notificações de novos dados.

Neste artigo, criaremos um aplicativo de exemplo para registrar a frequência cardíaca do usuário:

Um aplicativo de exemplo para registrar a frequência cardíaca dos usuários

Requisitos

Os itens a seguir são necessários para concluir as etapas apresentadas neste artigo:

  • Xcode 7 e iOS 8 (ou superior) – As APIs mais recentes do Xcode e iOS da Apple precisam ser instaladas e configuradas no computador do desenvolvedor.
  • Visual Studio para Mac ou Visual Studio – a versão mais recente do Visual Studio para Mac deve ser instalada e configurada no computador do desenvolvedor.
  • Dispositivo iOS 8 (ou superior) – Um dispositivo iOS executando a versão mais recente do iOS 8 ou superior para teste.

Importante

O Health Kit foi introduzido no iOS 8. Atualmente, o Health Kit não está disponível no simulador do iOS e a depuração requer conexão com um dispositivo iOS físico.

Criando e provisionando um aplicativo do Health Kit

Antes que um aplicativo Xamarin iOS 8 possa usar a API HealthKit, ele deve ser configurado e provisionado corretamente. Esta seção abordará as etapas necessárias para configurar corretamente seu aplicativo Xamarin.

Os aplicativos do Health Kit exigem:

  • Uma ID de aplicativo explícita.
  • Um Perfil de Provisionamento associado a essa ID de Aplicativo explícita e às permissões do Kit de Integridade.
  • Um Entitlements.plist com uma com.apple.developer.healthkit propriedade do tipo Boolean definida como Yes.
  • Uma Info.plist cuja UIRequiredDeviceCapabilities chave contém uma entrada com o String valor healthkit.
  • Eles Info.plist também devem ter entradas de explicação de privacidade apropriadas: uma String explicação para a chave NSHealthUpdateUsageDescription se o aplicativo for gravar dados e uma String explicação para a chave NSHealthShareUsageDescription se o aplicativo for ler dados do Health Kit.

Para saber mais sobre como provisionar um aplicativo iOS, o artigo Provisionamento de Dispositivo na série Introdução do Xamarin descreve a relação entre Certificados de Desenvolvedor, IDs de Aplicativo, Perfis de Provisionamento e Direitos de Aplicativo.

ID do aplicativo explícito e perfil de provisionamento

A criação de uma ID de Aplicativo explícita e um Perfil de Provisionamento apropriado é feita no Centro de Desenvolvimento do iOS da Apple.

Suas IDs de aplicativo atuais estão listadas na seção Certificados, Identificadores e Perfis do Centro de Desenvolvimento. Muitas vezes, essa lista mostrará valores de ID de , indicando que o nome da ID - do *aplicativo pode ser usado com qualquer número de sufixos. Essas IDs de aplicativo curinga não podem ser usadas com o Health Kit.

Para criar uma ID de aplicativo explícita, clique no + botão no canto superior direito para levá-lo à página Registrar ID do aplicativo iOS:

Registrando um aplicativo no Portal do Desenvolvedor da Apple

Conforme mostrado na imagem acima, depois de criar uma descrição do aplicativo, use a seção ID do aplicativo explícito para criar uma ID para seu aplicativo. Na seção Serviços de Aplicativos, marque Kit de Integridade na seção Habilitar Serviços.

Quando terminar, pressione o botão Continuar para registrar o ID do aplicativo em sua conta. Você será levado de volta à página Certificados, Identificadores e Perfis . Clique em Perfis de Provisionamento para levá-lo à lista de seus perfis de provisionamento atuais e clique no + botão no canto superior direito para levá-lo à página Adicionar Perfil de Provisionamento do iOS. Selecione a opção Desenvolvimento de aplicativos iOS e clique em Continuar para acessar a página Selecionar ID do aplicativo. Aqui, selecione a ID do aplicativo explícita que você especificou anteriormente:

Selecione a ID do aplicativo explícita

Clique em Continuar e trabalhe nas telas restantes, onde você especificará seu (s) certificado(s) de desenvolvedor, dispositivo(s) e um nome para este perfil de provisionamento:

Gerando o perfil de provisionamento

Clique em Gerar e aguarde a criação do seu perfil. Baixe o arquivo e clique duas vezes nele para instalar no Xcode. Você pode confirmar sua instalação em Preferências > do Xcode > Contas > Ver detalhes... Você deve ver seu perfil de provisionamento recém-instalado e ele deve ter o ícone do Health Kit e de quaisquer outros serviços especiais em sua linha Direitos:

Exibindo o perfil no Xcode

Associando a ID do aplicativo e o perfil de provisionamento ao seu aplicativo Xamarin.iOS

Depois de criar e instalar um Perfil de Provisionamento apropriado, conforme descrito, normalmente seria hora de criar uma solução no Visual Studio para Mac ou no Visual Studio. O acesso ao Health Kit está disponível para qualquer projeto iOS C# ou F#.

Em vez de percorrer o processo de criação de um projeto do Xamarin iOS 8 manualmente, abra o aplicativo de exemplo anexado a este artigo (que inclui um Storyboard e um código predefinidos). Para associar o aplicativo de exemplo ao Perfil de Provisionamento habilitado para o Health Kit, no Painel de Soluções, clique com o botão direito do mouse no Projeto e abra a caixa de diálogo Opções. Alterne para o painel Aplicativo iOS e insira a ID do aplicativo explícita que você criou anteriormente como o identificador de pacote do aplicativo:

Insira a ID do aplicativo explícita

Agora mude para o painel iOS Bundle Signing . Seu Perfil de Provisionamento recém-instalado, com sua associação à ID explícita do Aplicativo, agora estará disponível como o Perfil de Provisionamento:

Selecione o perfil de provisionamento

Se o Perfil de Provisionamento não estiver disponível, verifique novamente o Identificador de Pacote no painel Aplicativo iOS versus o especificado no Centro de Desenvolvimento do iOS e se o Perfil de Provisionamento está instalado (Detalhes de Exibição de Contas > de Preferências > do Xcode>...).

Quando o Perfil de provisionamento habilitado para kit de integridade estiver selecionado, clique em OK para fechar a caixa de diálogo Opções do projeto.

Valores Entitlements.plist e Info.plist

O aplicativo de exemplo inclui um Entitlements.plist arquivo (que é necessário para aplicativos habilitados para Kit de Integridade) e não está incluído em todos os modelos de projeto. Se o seu projeto não incluir direitos, clique com o botão direito do mouse no seu projeto, escolha Arquivo > Novo arquivo... > iOS > Entitlements.plist para adicionar um manualmente.

Por fim, você Entitlements.plist deve ter o seguinte par de chave e valor:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>com.apple.developer.HealthKit</key>
    <true/>
</dict>
</plist>

Da mesma forma, o Info.plist para o aplicativo deve ter um valor associado healthkit à UIRequiredDeviceCapabilities chave:

<key>UIRequiredDeviceCapabilities</key>
<array>
<string>armv7</string>
    <string>healthkit</string>
</array>

O aplicativo de exemplo fornecido com este artigo inclui um pré-configurado Entitlements.plist que inclui todas as chaves necessárias.

Kit de integridade de programação

O repositório de dados do Health Kit é um repositório de dados privado e específico do usuário que é compartilhado entre aplicativos. Como as informações de saúde são tão confidenciais, o usuário deve tomar medidas positivas para permitir o acesso aos dados. Esse acesso pode ser parcial (gravação, mas não leitura, acesso para alguns tipos de dados, mas não para outros, etc.) e pode ser revogado a qualquer momento. Os aplicativos do Health Kit devem ser escritos defensivamente, com o entendimento de que muitos usuários hesitarão em armazenar suas informações relacionadas à saúde.

Os dados do Health Kit são limitados aos tipos especificados pela Apple. Esses tipos são estritamente definidos: alguns, como o tipo sanguíneo, são limitados aos valores particulares de uma enumeração fornecida pela Apple, enquanto outros combinam uma magnitude com uma unidade de medida (como gramas, calorias e litros). Mesmo os dados que compartilham uma unidade de medida compatível são distinguidos por seus HKObjectType; por exemplo, o sistema de tipos detectará uma tentativa equivocada de armazenar um HKQuantityTypeIdentifier.NumberOfTimesFallen valor em um campo esperando um HKQuantityTypeIdentifier.FlightsClimbed mesmo que ambos usem a HKUnit.Count unidade de medida.

Os tipos armazenáveis no repositório de dados do Health Kit são todas subclasses do HKObjectType. HKCharacteristicType objetos armazenam sexo biológico, tipo sanguíneo e data de nascimento. Mais comuns, porém, são HKSampleType os objetos, que representam dados amostrados em um momento específico ou durante um período de tempo.

Gráfico de objetos HKSampleType

HKSampleType é abstrato e tem quatro subclasses concretas. Atualmente, existe apenas um tipo de dado, que é a Análise do HKCategoryType Sono. A grande maioria dos dados no Health Kit é do tipo HKQuantityType e armazena seus dados em HKQuantitySample objetos, que são criados usando o padrão de design familiar do Factory:

A grande maioria dos dados no Health Kit é do tipo HKQuantityType e armazena seus dados em objetos HKQuantitySample

HKQuantityType Os tipos variam de HKQuantityTypeIdentifier.ActiveEnergyBurned a HKQuantityTypeIdentifier.StepCount.

Solicitando permissão do usuário

Os usuários finais devem tomar medidas positivas para permitir que um aplicativo leia ou grave dados do Health Kit. Isso é feito por meio do aplicativo Saúde que vem pré-instalado em dispositivos iOS 8. Na primeira vez que um aplicativo Health Kit é executado, o usuário recebe uma caixa de diálogo de Acesso à Saúde controlada pelo sistema:

O usuário é apresentado a uma caixa de diálogo de Acesso à Saúde controlada pelo sistema

Posteriormente, o usuário pode alterar as permissões usando a caixa de diálogo Fontes do aplicativo Saúde :

O usuário pode alterar as permissões usando a caixa de diálogo Fontes dos aplicativos de saúde

Como as informações de saúde são extremamente confidenciais, os desenvolvedores de aplicativos devem escrever seus programas defensivamente, com a expectativa de que as permissões sejam recusadas e alteradas enquanto o aplicativo estiver em execução. O idioma mais comum é solicitar permissões no UIApplicationDelegate.OnActivated método e, em seguida, modificar a interface do usuário conforme apropriado.

Passo a passo de permissões

No projeto provisionado pelo Health Kit, abra o AppDelegate.cs arquivo. Observe a instrução usando HealthKit; na parte superior do arquivo.

O código a seguir está relacionado às permissões do Health Kit:

private HKHealthStore healthKitStore = new HKHealthStore ();

public override void OnActivated (UIApplication application)
{
        base.OnActivated(application);
        ValidateAuthorization ();
}

private void ValidateAuthorization ()
{
        var heartRateId = HKQuantityTypeIdentifierKey.HeartRate;
        var heartRateType = HKObjectType.GetQuantityType (heartRateId);
        var typesToWrite = new NSSet (new [] { heartRateType });
        var typesToRead = new NSSet ();
        healthKitStore.RequestAuthorizationToShare (
                typesToWrite, 
                typesToRead, 
                ReactToHealthCarePermissions);
}

void ReactToHealthCarePermissions (bool success, NSError error)
{
        var access = healthKitStore.GetAuthorizationStatus (HKObjectType.GetQuantityType (HKQuantityTypeIdentifierKey.HeartRate));
        if (access.HasFlag (HKAuthorizationStatus.SharingAuthorized)) {
                HeartRateModel.Instance.Enabled = true;
        } else {
                HeartRateModel.Instance.Enabled = false;
        }
}

Todo o código nesses métodos pode ser feito embutido no OnActivated, mas o aplicativo de exemplo usa métodos separados para tornar sua intenção mais clara: ValidateAuthorization() tem as etapas necessárias para solicitar acesso aos tipos específicos que estão sendo gravados (e lidos, se o aplicativo desejar) e ReactToHealthCarePermissions() é um retorno de chamada que é ativado depois que o usuário interage com a caixa de diálogo de permissões no Health.app.

O trabalho é ValidateAuthorization() construir o conjunto que HKObjectTypes o aplicativo gravará e solicitar autorização para atualizar esses dados. No aplicativo de exemplo, o HKObjectType é para a chave KHQuantityTypeIdentifierKey.HeartRate. Este tipo é adicionado ao conjunto typesToWrite, enquanto o conjunto typesToRead é deixado vazio. Esses conjuntos e uma referência ao retorno de ReactToHealthCarePermissions() chamada são passados para HKHealthStore.RequestAuthorizationToShare().

O ReactToHealthCarePermissions() retorno de chamada será chamado depois que o usuário tiver interagido com a caixa de diálogo de permissões e receber duas informações: um bool valor que será true se o usuário tiver interagido com a caixa de diálogo de permissões e um NSError que, se não for nulo, indica algum tipo de erro associado à apresentação da caixa de diálogo de permissões.

Importante

Para ser claro sobre os argumentos para esta função: os parâmetros de sucesso e erro não indicam se o usuário concedeu permissão para acessar os dados do Health Kit! Indicam apenas que o utilizador teve a oportunidade de permitir o acesso aos dados.

Para confirmar se o aplicativo tem acesso aos dados, o HKHealthStore.GetAuthorizationStatus() é usado, passando HKQuantityTypeIdentifierKey.HeartRate. Com base no status retornado, o aplicativo habilita ou desabilita a capacidade de inserir dados. Não existe uma experiência de usuário padrão para lidar com uma negação de acesso e há muitas opções possíveis. No aplicativo de exemplo, o status é definido em um HeartRateModel objeto singleton que, por sua vez, gera eventos relevantes.

Modelo, Visualização e Controlador

Para revisar o HeartRateModel objeto singleton, abra o HeartRateModel.cs arquivo:

using System;
using HealthKit;
using Foundation;

namespace HKWork
{
        public class GenericEventArgs<T> : EventArgs
        {
                public T Value { get; protected set; }
                public DateTime Time { get; protected set; }

                public GenericEventArgs (T value)
                {
                        this.Value = value;
                        Time = DateTime.Now;
                }
        }

        public delegate void GenericEventHandler<T> (object sender,GenericEventArgs<T> args);

        public sealed class HeartRateModel : NSObject
        {
                private static volatile HeartRateModel singleton;
                private static object syncRoot = new Object ();

                private HeartRateModel ()
                {
                }

                public static HeartRateModel Instance {
                        get {
                                //Double-check lazy initialization
                                if (singleton == null) {
                                        lock (syncRoot) {
                                                if (singleton == null) {
                                                        singleton = new HeartRateModel ();
                                                }
                                        }
                                }

                                return singleton;
                        }
                }

                private bool enabled = false;

                public event GenericEventHandler<bool> EnabledChanged;
                public event GenericEventHandler<String> ErrorMessageChanged;
                public event GenericEventHandler<Double> HeartRateStored;

                public bool Enabled { 
                        get { return enabled; }
                        set {
                                if (enabled != value) {
                                        enabled = value;
                                        InvokeOnMainThread(() => EnabledChanged (this, new GenericEventArgs<bool>(value)));
                                }
                        }
                }

                public void PermissionsError(string msg)
                {
                        Enabled = false;
                        InvokeOnMainThread(() => ErrorMessageChanged (this, new GenericEventArgs<string>(msg)));
                }

                //Converts its argument into a strongly-typed quantity representing the value in beats-per-minute
                public HKQuantity HeartRateInBeatsPerMinute(ushort beatsPerMinute)
                {
                        var heartRateUnitType = HKUnit.Count.UnitDividedBy (HKUnit.Minute);
                        var quantity = HKQuantity.FromQuantity (heartRateUnitType, beatsPerMinute);

                        return quantity;
                }
                        
                public void StoreHeartRate(HKQuantity quantity)
                {
                        var bpm = HKUnit.Count.UnitDividedBy (HKUnit.Minute);
                        //Confirm that the value passed in is of a valid type (can be converted to beats-per-minute)
                        if (! quantity.IsCompatible(bpm))
                        {
                                InvokeOnMainThread(() => ErrorMessageChanged(this, new GenericEventArgs<string> ("Units must be compatible with BPM")));
                        }

                        var heartRateId = HKQuantityTypeIdentifierKey.HeartRate;
                        var heartRateQuantityType = HKQuantityType.GetQuantityType (heartRateId);
                        var heartRateSample = HKQuantitySample.FromType (heartRateQuantityType, quantity, new NSDate (), new NSDate (), new HKMetadata());

                        using (var healthKitStore = new HKHealthStore ()) {
                                healthKitStore.SaveObject (heartRateSample, (success, error) => {
                                        InvokeOnMainThread (() => {
                                                if (success) {
                                                        HeartRateStored(this, new GenericEventArgs<Double>(quantity.GetDoubleValue(bpm)));
                                                } else {
                                                        ErrorMessageChanged(this, new GenericEventArgs<string>("Save failed"));
                                                }
                                                if (error != null) {
                                                        //If there's some kind of error, disable 
                                                        Enabled = false;
                                                        ErrorMessageChanged (this, new GenericEventArgs<string>(error.ToString()));
                                                }
                                        });
                                });
                        }
                }
        }
}

A primeira seção é o código clichê para criar eventos e manipuladores genéricos. A parte inicial da HeartRateModel classe também é clichê para criar um objeto singleton thread-safe.

Em seguida, HeartRateModel expõe 3 eventos:

  • EnabledChanged - Indica que o armazenamento da frequência cardíaca foi ativado ou desativado (observe que o armazenamento está inicialmente desativado).
  • ErrorMessageChanged - Para este aplicativo de exemplo, temos um modelo de tratamento de erros muito simples: uma string com o último erro .
  • HeartRateStored - Aumenta quando uma frequência cardíaca é armazenada no banco de dados do Health Kit.

Observe que sempre que esses eventos são disparados, isso é feito por meio de NSObject.InvokeOnMainThread(), o que permite que os assinantes atualizem a interface do usuário. Como alternativa, os eventos podem ser documentados como gerados em threads em segundo plano e a responsabilidade de garantir a compatibilidade pode ser deixada para seus manipuladores. As considerações de thread são importantes em aplicativos do Kit de Integridade porque muitas das funções, como a solicitação de permissão, são assíncronas e executam seus retornos de chamada em threads não principais.

O código específico do Heath Kit está HeartRateModel nas duas funções HeartRateInBeatsPerMinute() e StoreHeartRate().

HeartRateInBeatsPerMinute() converte seu argumento em um kit HKQuantityde saúde fortemente tipado . O tipo da quantidade é aquele especificado pelo HKQuantityTypeIdentifierKey.HeartRate e as unidades da quantidade são HKUnit.Count divididas por HKUnit.Minute (em outras palavras, a unidade é batimentos por minuto).

A StoreHeartRate() função usa um HKQuantity (no aplicativo de exemplo, um criado por HeartRateInBeatsPerMinute() ). Para validar seus dados, ele usa o HKQuantity.IsCompatible() método, que retorna true se as unidades do objeto podem ser convertidas nas unidades do argumento. Se a quantidade foi criada com HeartRateInBeatsPerMinute() this obviamente retornará true, mas também retornaria true se a quantidade fosse criada como, por exemplo, Batidas por hora. Mais comumente, HKQuantity.IsCompatible() pode ser usado para validar massa, distância e energia que o usuário ou um dispositivo pode inserir ou exibir em um sistema de medição (como unidades imperiais), mas que pode ser armazenado em outro sistema (como unidades métricas).

Uma vez validada a compatibilidade da quantidade, o HKQuantitySample.FromType() método de fábrica é usado para criar um objeto fortemente tipado heartRateSample . HKSample os objetos têm uma data de início e término; Para leituras instantâneas, esses valores devem ser os mesmos, como no exemplo. O exemplo também não define nenhum dado de chave-valor em seu HKMetadata argumento, mas pode-se usar um código como o código a seguir para especificar a localização do sensor:

var hkm = new HKMetadata();
hkm.HeartRateSensorLocation = HKHeartRateSensorLocation.Chest;

Depois que o heartRateSample for criado, o código criará uma nova conexão com o banco de dados com o bloco using. Dentro desse bloco, o HKHealthStore.SaveObject() método tenta a gravação assíncrona no banco de dados. A chamada resultante para a expressão lambda aciona eventos relevantes, ou HeartRateStored ErrorMessageChanged.

Agora que o modelo foi programado, é hora de ver como o controlador reflete o estado do modelo. Abra o arquivo HKWorkViewController.cs. O construtor simplesmente conecta o HeartRateModel singleton a métodos de manipulação de eventos (novamente, isso pode ser feito em linha com expressões lambda, mas métodos separados tornam a intenção um pouco mais óbvia):

public HKWorkViewController (IntPtr handle) : base (handle)
{
     HeartRateModel.Instance.EnabledChanged += OnEnabledChanged;
     HeartRateModel.Instance.ErrorMessageChanged += OnErrorMessageChanged;
     HeartRateModel.Instance.HeartRateStored += OnHeartBeatStored;
}

Aqui estão os manipuladores relevantes:

void OnEnabledChanged (object sender, GenericEventArgs<bool> args)
{
        StoreData.Enabled = args.Value;
        PermissionsLabel.Text = args.Value ? "Ready to record" : "Not authorized to store data.";
        PermissionsLabel.SizeToFit ();
}

void OnErrorMessageChanged (object sender, GenericEventArgs<string> args)
{
        PermissionsLabel.Text = args.Value;
}

void OnHeartBeatStored (object sender, GenericEventArgs<double> args)
{
        PermissionsLabel.Text = String.Format ("Stored {0} BPM", args.Value);
}

Obviamente, em um aplicativo com um único controlador, seria possível evitar a criação de um objeto de modelo separado e o uso de eventos para fluxo de controle, mas o uso de objetos de modelo é mais apropriado para aplicativos do mundo real.

Executando o aplicativo de exemplo

O Simulador iOS não suporta o Health Kit. A depuração deve ser feita em um dispositivo físico que executa o iOS 8.

Anexe um dispositivo de desenvolvimento iOS 8 provisionado corretamente ao seu sistema. Selecione-o como o destino de implantação no Visual Studio para Mac e, no menu, escolha Executar > Depuração.

Importante

Erros relacionados ao provisionamento surgirão neste ponto. Para solucionar erros, examine a seção Criando e provisionando um aplicativo do Health Kit acima. Os componentes são:

  • Centro de Desenvolvimento do iOS – ID explícita do aplicativo e perfil de provisionamento habilitado para o kit de integridade.
  • Opções do projeto - Identificador de pacote (ID explícita do aplicativo) e perfil de provisionamento.
  • Código-fonte - Entitlements.plist & Info.plist

Supondo que as disposições tenham sido definidas corretamente, seu aplicativo será iniciado. Quando chegar ao seu OnActivated método, ele solicitará a autorização do Health Kit. Na primeira vez que isso for encontrado pelo sistema operacional, o usuário verá a seguinte caixa de diálogo:

O usuário verá esta caixa de diálogo

Ative seu aplicativo para atualizar os dados de frequência cardíaca e seu aplicativo reaparecerá. O ReactToHealthCarePermissions retorno de chamada será ativado de forma assíncrona. Isso fará com que a HeartRateModel’s Enabled propriedade seja alterada, o que gerará o evento, o EnabledChanged que fará com que o HKPermissionsViewController.OnEnabledChanged() manipulador de eventos seja executado, o que habilita o StoreData botão. O diagrama a seguir mostra a sequência:

Este diagrama mostra a sequência de eventos

Pressione o botão Gravar . Isso fará com que o StoreData_TouchUpInside() manipulador seja executado, que tentará analisar o valor do campo de heartRate texto, convertê-lo em um HKQuantity por meio da função discutida HeartRateModel.HeartRateInBeatsPerMinute() anteriormente e passar essa quantidade para HeartRateModel.StoreHeartRate(). Conforme discutido anteriormente, isso tentará armazenar os dados e gerará um HeartRateStored evento ou ErrorMessageChanged .

Clique duas vezes no botão Início no seu dispositivo e abra o aplicativo Saúde. Clique na guia Fontes e você verá o aplicativo de exemplo listado. Escolha-o e não permita a permissão para atualizar os dados de frequência cardíaca. Clique duas vezes no botão Início e volte para o aplicativo. Mais uma vez, ReactToHealthCarePermissions() será chamado, mas desta vez, como o acesso é negado, o botão StoreData será desabilitado (observe que isso ocorre de forma assíncrona e a alteração na interface do usuário pode ser visível para o usuário final).

Tópicos avançados

A leitura de dados do banco de dados do Health Kit é muito semelhante à gravação de dados: especifica-se os tipos de dados que se está tentando acessar, solicita-se autorização e, se essa autorização for concedida, os dados estão disponíveis, com conversão automática para unidades de medida compatíveis.

Há várias funções de consulta mais sofisticadas que permitem consultas baseadas em predicados e consultas que executam atualizações quando dados relevantes são atualizados.

Os desenvolvedores de aplicativos do Health Kit devem revisar a seção Health Kit das Diretrizes de revisão de aplicativos da Apple.

Uma vez que os modelos de segurança e sistema de tipos são compreendidos, armazenar e ler dados no banco de dados compartilhado do Health Kit é bastante simples. Muitas das funções do Health Kit operam de forma assíncrona e os desenvolvedores de aplicativos devem escrever seus programas adequadamente.

No momento da redação deste artigo, atualmente não há equivalente ao Health Kit no Android ou Windows Phone.

Resumo

Neste artigo, vimos como o Health Kit permite que os aplicativos armazenem, recuperem e compartilhem informações relacionadas à saúde, além de fornecer um aplicativo Health padrão que permite ao usuário acessar e controlar esses dados.

Também vimos como a privacidade, a segurança e a integridade dos dados são preocupações primordiais para informações relacionadas à saúde e os aplicativos que usam o Health Kit devem lidar com o aumento da complexidade nos aspectos de gerenciamento de aplicativos (provisionamento), codificação (sistema de tipos do Health Kit) e experiência do usuário (controle do usuário de permissões por meio de caixas de diálogo do sistema e aplicativo Health).

Por fim, examinamos uma implementação simples do Health Kit usando o aplicativo de exemplo incluído que grava dados de pulsação no repositório do Health Kit e tem um design com reconhecimento assíncrono.