Questa guida contiene le istruzioni per gli sviluppatori per condividere i dati di abbonamento e diritti dell'app con Google TV utilizzando l'SDK Engage. Gli utenti possono trovare i contenuti a cui hanno diritto e consentire a Google TV di fornire consigli sui contenuti altamente pertinenti direttamente nelle esperienze Google TV su TV, dispositivi mobili e tablet.
Prerequisiti
L'onboarding del feed delle azioni multimediali è necessario prima di poter utilizzare l'API per i diritti del dispositivo. Se non lo hai ancora fatto, completa la procedura di onboarding del feed Azioni multimediali.
Preparazione
Prima di iniziare, completa i seguenti passaggi: Verifica che la tua app abbia come target il livello API 19 o versioni successive per questa integrazione
Aggiungi la libreria
com.google.android.engage
alla tua app:Esistono SDK separati da utilizzare nell'integrazione: uno per le app mobile e uno per le app TV.
Per dispositivi mobili
dependencies { implementation 'com.google.android.engage:engage-core:1.5.5 }
per TV
dependencies { implementation 'com.google.android.engage:engage-tv:1.0.2 }
Imposta l'ambiente di servizio Engage su produzione nel file
AndroidManifest.xml
.Per l'apk mobile
<meta-data android:name="com.google.android.engage.service.ENV" android:value="PRODUCTION"> </meta-data>
APK per TV
<meta-data android:name="com.google.android.engage.service.ENV" android:value="PRODUCTION"> </meta-data>
Prima di inviare l'APK a Google, imposta l'ambiente del servizio di coinvolgimento su produzione nel file AndroidManifest.xml. Per prestazioni ottimali e compatibilità futura, pubblica i dati solo quando l'app è in primo piano e l'utente interagisce attivamente con essa, ad esempio all'avvio dell'app, dopo l'accesso o durante l'utilizzo attivo. La pubblicazione da processi in background è sconsigliata.
Pubblica le informazioni sull'abbonamento nei seguenti eventi:
- L'utente accede alla tua app.
- L'utente passa da un profilo all'altro (se i profili sono supportati).
- L'utente acquista un nuovo abbonamento.
- L'utente esegue l'upgrade di un abbonamento esistente.
- L'abbonamento dell'utente scade.
Integrazione
Questa sezione fornisce gli esempi di codice e le istruzioni necessarie per
implementare AccountProfile
e SubscriptionEntity
per gestire vari
tipi di abbonamento.
Account e profilo utente
Per consentire le funzionalità personalizzate su Google TV, fornisci le informazioni
dell'account. Utilizza AccountProfile
per fornire:
- ID account: un identificatore univoco che rappresenta l'account dell'utente. Può trattarsi dell'ID account effettivo o di una versione offuscata in modo appropriato.
// Set the account ID to which the subscription applies.
// Don't set the profile ID because subscription applies to account level.
val accountProfile = AccountProfile.Builder()
.setAccountId("user_account_id")
.setProfileId("user_profile id")
.build();
Abbonamento al livello comune
Per gli utenti con abbonamenti di base ai servizi dei fornitori di contenuti multimediali, ad esempio un servizio con un livello di abbonamento che concede l'accesso a tutti i contenuti a pagamento, fornisci questi dettagli essenziali:
Tipo di abbonamento:indica chiaramente il piano di abbonamento specifico dell'utente.
SUBSCRIPTION_TYPE_ACTIVE
: L'utente ha un abbonamento a pagamento attivo.SUBSCRIPTION_TYPE_ACTIVE_TRIAL
: L'utente ha un abbonamento di prova.SUBSCRIPTION_TYPE_INACTIVE
: l'utente ha un account, ma non ha un abbonamento o una prova attivi.
Tempo di scadenza:tempo facoltativo in millisecondi. Specifica la data di scadenza dell'abbonamento.
Nome pacchetto del fornitore:specifica il nome del pacchetto dell'app che gestisce l'abbonamento.
Esempio per il feed del fornitore di contenuti multimediali di esempio.
"actionAccessibilityRequirement": [
{
"@type": "ActionAccessSpecification",
"category": "subscription",
"availabilityStarts": "2022-06-01T07:00:00Z",
"availabilityEnds": "2026-05-31T07:00:00Z",
"requiresSubscription": {
"@type": "MediaSubscription",
// Don't match this string,
// ID is only used to for reconciliation purpose
"@id": "https://www.example.com/971bfc78-d13a-4419",
// Don't match this, as name is only used for displaying purpose
"name": "Basic common name",
"commonTier": true
}
L'esempio seguente crea un SubscriptionEntity
per un utente:
val subscription = SubscriptionEntity
.Builder()
setSubscriptionType(
SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE
)
.setProviderPackageName("com.google.android.example")
// Optional
// December 30, 2025 12:00:00AM in milliseconds since epoch
.setExpirationTimeMillis(1767052800000)
.build();
Abbonamento Premium
Se l'app offre pacchetti di abbonamento premium a più livelli, che includono contenuti o funzionalità estesi oltre al livello comune, rappresentalo aggiungendo uno o più diritti all'abbonamento.
Questo diritto include i seguenti campi:
- Identificatore:stringa identificatore obbligatoria per questo diritto. Questo valore deve corrispondere a uno degli identificatori dei diritti (tieni presente che non si tratta del campo ID) forniti nel feed del fornitore di contenuti multimediali pubblicato su Google TV.
- Nome:si tratta di informazioni ausiliarie utilizzate per la corrispondenza dei diritti. Sebbene sia facoltativo, fornire un nome di diritto leggibile migliora la comprensione dei diritti degli utenti sia per gli sviluppatori che per i team di assistenza. Ad esempio: Sling Orange.
- Expiration TimeMillis: specifica facoltativamente la scadenza in millisecondi per questo diritto, se diversa dalla scadenza dell'abbonamento. Per impostazione predefinita, il diritto scadrà con la scadenza dell'abbonamento.
Per il seguente snippet di feed del fornitore di contenuti multimediali di esempio:
"actionAccessibilityRequirement": [
{
"@type": "ActionAccessSpecification",
"category": "subscription",
"availabilityStarts": "2022-06-01T07:00:00Z",
"availabilityEnds": "2026-05-31T07:00:00Z",
"requiresSubscription": {
"@type": "MediaSubscription",
// Don't match this string,
// ID is only used to for reconciliation purpose
"@id": "https://www.example.com/971bfc78-d13a-4419",
// Don't match this, as name is only used for displaying purpose
"name": "Example entitlement name",
"commonTier": false,
// match this identifier in your API. This is the crucial
// entitlement identifier used for recommendation purpose.
"identifier": "example.com:entitlementString1"
}
L'esempio seguente crea un SubscriptionEntity
per un utente abbonato:
// Subscription with entitlements.
// The entitlement expires at the same time as its subscription.
val subscription = SubscriptionEntity
.Builder()
.setSubscriptionType(
SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE
)
.setProviderPackageName("com.google.android.example")
// Optional
// December 30, 2025 12:00:00AM in milliseconds
.setExpirationTimeMillis(1767052800000)
.addEntitlement(
SubscriptionEntitlement.Builder()
// matches with the identifier in media provider feed
.setEntitlementId("example.com:entitlementString1")
.setDisplayName("entitlement name1")
.build()
)
.build();
// Subscription with entitlements
// The entitement has different expiration time from its subscription
val subscription = SubscriptionEntity
.Builder()
.setSubscriptionType(
SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE
)
.setProviderPackageName("com.google.android.example")
// Optional
// December 30, 2025 12:00:00AM in milliseconds
.setExpirationTimeMillis(1767052800000)
.addEntitlement(
SubscriptionEntitlement.Builder()
.setEntitlementId("example.com:entitlementString1")
.setDisplayName("entitlement name1")
// You may set the expiration time for entitlement
// December 15, 2025 10:00:00 AM in milliseconds
.setExpirationTimeMillis(1765792800000)
.build())
.build();
Abbonamento al pacchetto di servizi collegati
Sebbene gli abbonamenti appartengano in genere al fornitore di contenuti multimediali dell'app di origine, un abbonamento può essere attribuito a un pacchetto di servizi collegato specificando il nome del pacchetto di servizi collegato all'interno dell'abbonamento.
Il seguente esempio di codice mostra come creare un abbonamento utente.
// Subscription for linked service package
val subscription = SubscriptionEntity
.Builder()
.setSubscriptionType(
SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE
)
.setProviderPackageName("com.google.android.example")
// Optional
// December 30, 2025 12:00:00AM in milliseconds since epoch
.setExpirationTimeMillis(1767052800000)
.build();
Inoltre, se l'utente ha un altro abbonamento a un servizio sussidiario, aggiungi un altro abbonamento e imposta il nome del pacchetto del servizio collegato di conseguenza.
// Subscription for linked service package
val linkedSubscription = Subscription
.Builder()
.setSubscriptionType(
SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE
)
.setProviderPackageName("linked service package name")
// Optional
// December 30, 2025 12:00:00AM in milliseconds since epoch
.setExpirationTimeMillis(1767052800000)
.addBundledSubscription(
BundledSubscription.Builder()
.setBundledSubscriptionProviderPackageName(
"bundled-subscription-package-name"
)
.setSubscriptionType(SubscriptionType.SUBSCRIPTION_TYPE_ACTIVE)
.setExpirationTimeMillis(111)
.addEntitlement(
SubscriptionEntitlement.Builder()
.setExpirationTimeMillis(111)
.setDisplayName("Silver subscription")
.setEntitlementId("subscription.tier.platinum")
.build()
)
.build()
)
.build();
Se vuoi, aggiungi i diritti anche a un abbonamento al servizio collegato.
Fornisci il set di abbonamenti
Esegui il job di pubblicazione dei contenuti mentre l'app è in primo piano.
Utilizza il metodo publishSubscriptionCluster()
della classe
AppEngagePublishClient
per pubblicare un oggetto SubscriptionCluster
.
Utilizza isServiceAvailable
per verificare se il servizio è
disponibile per l'integrazione.
client.publishSubscription(
PublishSubscriptionRequest.Builder()
.setAccountProfile(accountProfile)
.setSubscription(subscription)
.build();
)
Utilizza setSubscription()
per verificare che l'utente debba avere un solo abbonamento al servizio.
Utilizza addLinkedSubscription()
o addLinkedSubscriptions()
, che accettano un elenco
di abbonamenti collegati, per consentire all'utente di avere zero o più abbonamenti
collegati.
Quando il servizio riceve la richiesta, viene creato un nuovo inserimento e quello precedente viene eliminato automaticamente dopo 60 giorni. Il sistema utilizza sempre l'ultima voce. In caso di errore, l'intera richiesta viene rifiutata e lo stato esistente viene mantenuto.
Mantenere l'abbonamento aggiornato
- Per fornire aggiornamenti immediati in caso di modifiche, chiama
publishSubscriptionCluster()
ogni volta che lo stato dell'abbonamento di un utente cambia come attivazione, disattivazione, upgrade e downgrade. Per fornire una convalida regolare per una precisione continua, chiama
publishSubscriptionCluster()
almeno una volta al mese.Per eliminare i dati di scoperta dei video, elimina manualmente i dati di un utente dal server Google TV prima del periodo di conservazione standard di 60 giorni utilizzando il metodo
client.deleteClusters()
. In questo modo vengono eliminati tutti i dati esistenti sulla scoperta dei video per il profilo dell'account o per l'intero account, a seconda delDeleteReason
specificato.Snippet di codice per rimuovere l'abbonamento dell'utente
// If the user logs out from your media app, you must make the following call // to remove subscription and other video discovery data from the current // google TV device. client.deleteClusters( new DeleteClustersRequest.Builder() .setAccountProfile( AccountProfile .Builder() .setAccountId() .setProfileId() .build() ) .setReason(DeleteReason.DELETE_REASON_USER_LOG_OUT) .build() ) ``` Following code snippet demonstrates removal of user subscription when user revokes the consent. ```Kotlin // If the user revokes the consent to share across device, make the call // to remove subscription and other video discovery data from all google // TV devices. client.deleteClusters( new DeleteClustersRequest.Builder() .setAccountProfile( AccountProfile .Builder() .setAccountId() .setProfileId() .build() ) .setReason(DeleteReason.DELETE_REASON_LOSS_OF_CONSENT) .build() ) ``` Following code demonstrates how to remove subscription data on user profile deletion. ```Kotlin // If the user delete a specific profile, you must make the following call // to remove subscription data and other video discovery data. client.deleteClusters( new DeleteClustersRequest.Builder() .setAccountProfile( AccountProfile .Builder() .setAccountId() .setProfileId() .build() ) .setReason(DeleteReason.DELETE_REASON_ACCOUNT_PROFILE_DELETION) .build() )
Test
Questa sezione fornisce una guida passo passo per testare l'implementazione degli abbonamenti. Verifica l'accuratezza dei dati e il corretto funzionamento prima del lancio.
Elenco di controllo per la pubblicazione dell'integrazione
La pubblicazione deve avvenire quando l'app è in primo piano e l'utente interagisce attivamente con essa.
Pubblica quando:
- L'utente accede per la prima volta.
- L'utente cambia profilo (se i profili sono supportati).
- L'utente acquista un nuovo abbonamento.
- L'utente esegue l'upgrade dell'abbonamento.
- L'abbonamento dell'utente scade.
Controlla se l'app chiama correttamente le API
isServiceAvailable()
epublishClusters()
in logcat, negli eventi di pubblicazione.Verifica che i dati siano visibili nell'app di verifica. L'abbonamento deve essere visualizzato come riga separata. Quando viene richiamata l'API Publish, i dati dovrebbero essere visualizzati nell'app di verifica.
- Verifica che il flag del servizio Engage NON sia impostato sulla produzione nel file manifest di Android dell'app.
- Installa e apri l'app Engage Verification.
- Se il valore di
isServiceAvailable
èfalse
nell'app di verifica, fai clic sul pulsanteToggle
all'interno dell'app di verifica per impostarlo sutrue
. - Inserisci il nome del pacchetto dell'app. I dati pubblicati vengono visualizzati automaticamente.
Vai all'app ed esegui ciascuna delle seguenti azioni:
- Accedi.
- passare da un profilo all'altro (se supportato).
- Acquista un nuovo abbonamento.
- Eseguire l'upgrade di un abbonamento esistente.
- Scadenza dell'abbonamento.
Verifica l'integrazione
Per testare l'integrazione, utilizza l'app di verifica.
L'app di verifica è un'applicazione Android che gli sviluppatori possono utilizzare per verificare che l'integrazione funzioni. L'app include funzionalità per aiutare gli sviluppatori a verificare i dati e trasmettere intent. Consente di verificare l'accuratezza dei dati e la corretta funzionalità prima del lancio.
- Per ciascun evento, verifica se l'app ha richiamato l'API
publishSubscription
. Verifica i dati pubblicati nell'app di verifica. Verifica che tutto sia verde nell'app di verifica Se tutte le informazioni dell'entità sono corrette, viene visualizzato un segno di spunta verde "Tutto ok" in tutte le entità.
Figura 1. Abbonamento riuscito I problemi vengono evidenziati anche nell'app di verifica
Figura 2.Abbonamento non riuscito Per visualizzare i problemi nell'abbonamento incluso, utilizza il telecomando della TV per selezionare l'abbonamento incluso specifico e fai clic per visualizzare i problemi. Potresti dover prima impostare lo stato attivo sulla riga e spostarti verso destra per trovare la scheda Abbonamento in bundle. I problemi vengono evidenziati in rosso, come mostrato nella Figura 3. Inoltre, utilizza il telecomando per scorrere verso il basso e visualizzare i problemi relativi ai diritti all'interno dell'abbonamento in bundle
Figura 3.Errori relativi all'abbonamento Per visualizzare i problemi relativi al diritto, utilizza il telecomando della TV per concentrarti su quel diritto specifico e fai clic per visualizzare i problemi. I problemi sono evidenziati in rosso.
Figura 4.Dettagli errore abbonamento
Scarica
Prima di scaricare, devi accettare i seguenti Termini e condizioni.