Antes de usar qualquer uma das APIs Home para Android, é necessário inicializar a casa no
app. Nesta etapa, você vai criar uma instância singleton de
Home para o contexto local.
Apenas uma instância de Home pode estar ativa por vez.
Esse é o ponto de entrada para as APIs Home e também envolve declarar quais características e tipos de dispositivos você pretende usar com as APIs Device & Structure e Automation. Se você está começando a usar o ecossistema do Google Home e não sabe quais características ou tipos de dispositivos registrar, sugerimos alguns dos mais comuns neste guia.
Criar uma instância de casa
Para começar, importe estes pacotes para seu app:
import android.content.Context
import com.google.home.FactoryRegistry
import com.google.home.HomeConfig
import com.google.home.Home
Para inicializar as APIs Home:
Receba uma referência ao contexto
Application. Esse contexto não depende de nenhum ciclo de vida de atividade e vai existir enquanto o app estiver ativo. Para isso, chamegetApplicationContext()em umActivityouService:val context = getApplicationContext()Crie uma instância
FactoryRegistrycom todas as características e tipos de dispositivos que você pretende usar no app.Neste guia, sugerimos alguns comuns (tipos de dispositivos de luz, plugue, sensor, interruptor e termostato, além de traços de presença e do Google Assistente para automações), caso você não saiba o que precisa. Para saber mais, consulte Registro de características e tipos de dispositivos.
val registry = FactoryRegistry( traits = listOf( AirQuality, AreaAttendanceState, AreaPresenceState, AssistantBroadcast, AssistantFulfillment, BooleanState, ColorControl, ExtendedColorControl, FlowMeasurement, IlluminanceMeasurement, LevelControl, Notification, OccupancySensing, OnOff, RelativeHumidityMeasurement, Switch, TemperatureMeasurement, Thermostat), types = listOf( AirQualitySensorDevice, ColorDimmerSwitchDevice, ColorTemperatureLightDevice, ContactSensorDevice, DimmableLightDevice, DimmablePlugInUnitDevice, DimmerSwitchDevice, ExtendedColorLightDevice, FlowSensorDevice, GenericSwitchDevice, HumiditySensorDevice, LightSensorDevice, OccupancySensorDevice, OnOffLightDevice, OnOffLightSwitchDevice, OnOffPluginUnitDevice, OnOffSensorDevice, SpeakerDevice, TemperatureSensorDevice, ThermostatDevice))São necessárias instruções de importação para cada característica individual e tipo de dispositivo registrado aqui. O Android Studio vai pedir que você adicione essas informações.
Instancie um
HomeConfigusando o contexto de corrotinaDispatchers.IOe sua instância de registro.val homeConfig = HomeConfig( coroutineContext = Dispatchers.IO, factoryRegistry = registry)Por fim, crie a instância singleton de
Home, que é o ponto de entrada para as APIs, usando o contexto e oHomeConfig.val homeManager: HomeClient = Home.getClient(context, homeConfig)
Para evitar erros com sessões inválidas, é importante que apenas uma instância singleton
de Home seja criada, envolvendo-a em uma declaração de objeto.
Por exemplo, o app de amostra faz isso desta forma:
internal object HomeClientModule {
@Provides
@Singleton
fun provideHomeClient(@ApplicationContext context: Context): HomeClient {
return Home.getClient(
context,
HomeConfig(
coroutineContext = IODispatcherModule.provideIoDispatcher(),
factoryRegistry = registry,
),
)
}
}
Login do Google iniciado pelo app
Talvez você queira gerenciar as autenticações do Google do usuário no seu app. Isso permite usar a mesma conta de usuário em vários serviços do Google, como Google Home, Drive, Maps e outros.
Com o login do Google iniciado pelo app, você pode receber uma instância HomeClient
explicitamente vinculada a um usuário específico, ignorando o seletor de Conta do Google
e a tela de consentimento quando a conta já está autorizada.
Além disso, essa abordagem impede que os usuários vejam duas telas diferentes de seleção de conta: uma do login do app e outra do Google Home.
Para isso, consulte Autenticar usuários com o recurso Fazer login com o Google e siga estas etapas:
Criar um ID do cliente do aplicativo da Web OAuth
- Abra o console do Google Cloud
- Acesse a página "Credenciais" do Console do Google Cloud.
- Selecione um projeto atual ou crie um novo.
- Configure a tela de permissão OAuth (se ainda não tiver feito isso)
- Antes de criar credenciais, verifique se a tela de permissão OAuth está configurada com os detalhes do app, incluindo URLs da Política de Privacidade e dos Termos de Serviço.
- Crie um ID do cliente OAuth (tipo "Aplicativo da Web")
- Na página "Credenciais", clique em
+ CREATE CREDENTIALSe selecione ID do cliente OAuth no menu suspenso. - Em Tipo de aplicativo, selecione Aplicativo da Web.
- Insira um nome para seu cliente da Web (por exemplo, "My App Web Backend").
- Clique em "Criar".
- Na página "Credenciais", clique em
- Recuperar o ID do cliente
- Depois da criação, o console vai mostrar seu novo ID do cliente. Esse é o valor que você vai usar no seu aplicativo Android (por exemplo, "{project number}-.....apps.googleusercontent.com")
- Recomendamos que você armazene o Client-ID externamente (por exemplo, em
build.gradle) em vez de codificá-lo diretamente.
Instanciar uma solicitação de Login do Google
Use o ID do app da Web para criar uma solicitação de login do Google:
// Your Google Cloud console Web Client ID for Google Sign-In
val serverClientId = BuildConfig.DEFAULT_WEB_CLIENT_ID
// Build the request for Google ID token
val googleIdOption = GetGoogleIdOption.Builder()
.setFilterByAuthorizedAccounts(false) // Show all Google Accounts on the device
.setServerClientId(serverClientId) // embed WebClientID in token
.build()
// Build the GetCredentialRequest
val request = GetCredentialRequest.Builder().addCredentialOption(googleIdOption).build()
Criar o fluxo "Fazer login com o Google"
Para implementar o fluxo de login, use CredentialManager para executar uma
solicitação Sign in with Google. Depois que o usuário selecionar uma conta, extraia
o e-mail dele do token de ID do Google resultante para criar um
android.accounts.Account. Essa conta é usada para inicializar uma instância HomeClient especificamente vinculada a esse usuário conectado.
try {
// CredentialManager is responsible for interacting with various credential providers on the device
val credentialManager = CredentialManager.create(context)
// Credential returns when user has selected an account and the getCredential call completes
val result = credentialManager.getCredential(context = context, request = request)
val credential = result.credential
if (
credential is CustomCredential &&
credential.type == GoogleIdTokenCredential.TYPE_GOOGLE_ID_TOKEN_CREDENTIAL
) {
try {
val googleCredential = GoogleIdTokenCredential.createFrom(credential.data)
googleCredential.id.let { userEmail ->
Log.i(TAG, "Email found in Google ID Token: $email")
/*
Why "com.google"?
The string "com.google" is a standard identifier used in Android's android.accounts.
Account system to represent accounts managed by Google. This is often used when
interacting with Android's Account Manager or when using Google-specific APIs. So,
even if the email ends in "@gmail.com", the underlying account type or provider is
still considered "com.google" within the Android system.
*/
val account = Account(userEmail, "com.google")
Log.d(TAG,"Switched account to : $userEmail")
// Get the new Home Client Instance with the userEmail
}
Log.i(TAG, "Account switch complete. Emitting navigation event.")
} catch (e: Exception) {
Log.e(TAG,"Could not convert CustomCredential to Google ID Token", e)
}
}
} catch (e: Exception) {
Log.e(TAG, "Google Sign-In failed with unexpected error", e)
}
Receber uma nova instância do HomeClient
Siga as mesmas etapas descritas em
Criar uma instância de casa, mas em vez de chamar
Home.getClient(context, homeConfig) na etapa 4, chame
Home.getClient(context, userAccount,
homeConfig),
em que o segundo parâmetro é um Lazy<UserAccount>. Isso retorna uma instância de
HomeClientWithProvidedAccount,
uma subclasse de HomeClient, que está explicitamente vinculada à Conta do Google
especificada:
val client =
Home.getClient(
context = context.applicationContext,
account =
lazy {
// 1. Create the Account object.
val androidAccount = Account(userEmail,
GoogleAuthUtil.GOOGLE_ACCOUNT_TYPE)
// 2. Wrap it in UserAccount.GoogleAccount.
UserAccount.GoogleAccount(androidAccount)
},
homeConfig = HomeConfig()
)
Se o usuário especificado não estiver autorizado, peça permissão chamando os seguintes métodos na instância HomeClientWithProvidedAccount:
registerActivityResultCallerForPermissions()com uma referência ao ActivityResultCaller que você quer usar.requestPermissions(). Isso abre a tela de consentimento do GHP, em que o usuário pode conceder a permissão.
É possível criar um HomeClient com um
UserAccount e chamar
requestPermissions() com forceLaunch==true para iniciar a tela de consentimento
de novo e permitir que o usuário atualize a concessão de permissões:
val client =
Home.getClient(
context = context.applicationContext,
account =
lazy {
UserAccount.GoogleAccount(androidAccount)
},
homeConfig = HomeConfig()
)
client.registerActivityResultCallerForPermissions(this)
client.requestPermissions(forceLaunch= true)
Consulte a API Permissions para mais informações sobre como gerenciar permissões das APIs Home.
Atualize toda a atividade com o novo HomeClient
Depois de ter uma nova instância HomeClient, atualize toda a atividade para se inscrever novamente e buscar as estruturas, os dispositivos e outros dados pertinentes completos associados a essa conta de usuário.
Registro de características e tipos de dispositivos
A classe FactoryRegistry ajuda os desenvolvedores a otimizar o tamanho binário do app, permitindo que eles indiquem explicitamente quais características e tipos de dispositivos são usados pelo app.
As permissões e o registro de fábrica são separados. Portanto, características e tipos não registrados que estão disponíveis para seu app usando permissões, mas não incluídos no registro de fábrica, não podem ser acessados usando a API Automation nem são retornados nas chamadas de método em massa traits() ou types().