Ce guide explique aux développeurs comment intégrer leurs recommandations de contenus vidéo à l'aide du SDK Engage pour renseigner les expériences de recommandation sur les surfaces Google, comme la télévision, le mobile et la tablette.
La fonctionnalité de recommandation utilise le cluster "Recommendation" pour afficher des films et des séries TV de plusieurs applications dans un même groupe d'UI. Chaque développeur partenaire peut diffuser au maximum 25 entités dans chaque cluster de recommandations. Il peut y avoir un maximum de 7 clusters de recommandations par requête.
Travail préalable
Avant de commencer, suivez les étapes ci-dessous. 1. Vérifiez que votre application cible le niveau d'API 19 ou supérieur pour cette intégration.
Ajoutez la bibliothèque
com.google.android.engage
à votre application.Des SDK distincts doivent être utilisés pour l'intégration: un pour les applications mobiles et un pour les applications TV.
Pour mobile
dependencies { implementation 'com.google.android.engage:engage-core:1.5.5 }
pour TV
dependencies { implementation 'com.google.android.engage:engage-tv:1.0.2 }
Définissez l'environnement de service Engage sur "production" dans le fichier
AndroidManifest.xml
.Pour l'APK mobile
<meta-data android:name="com.google.android.engage.service.ENV" android:value="PRODUCTION"> </meta-data>
For tv apk
<meta-data android:name="com.google.android.engage.service.ENV" android:value="PRODUCTION"> </meta-data>
Exécutez la publication sur un service de premier plan.
Publiez les données de recommandations au maximum une fois par jour, déclenchées par l'un des éléments suivants :
- Première connexion de l'utilisateur de la journée. (ou)
- Lorsque l'utilisateur commence à interagir avec l'application.
Intégration
AppEngagePublishClient
publie le cluster de recommandations. Utilisez la méthode publishRecommendationClusters
pour publier un objet "recommendations".
Utilisez isServiceAvailable()
2 pour vérifier si le service est disponible pour l'intégration.
val client = AppEngagePublishClient(context)
client.isServiceAvailable().addOnCompleteListener { task ->
if (task.isSuccessful) {
// Handle IPC call success
if(task.result) {
// Service is available on the device, proceed with content publish
// calls.
client.publishRecommendationClusters(recommendationRequest)
} else {
// Service is not available
}
} else {
// The IPC call itself fails, proceed with error handling logic here,
// such as retry.
}
}
Clusters "Recommandations" et demande de publication
Les clusters sont des regroupements logiques des entités. Les exemples de code suivants expliquent comment créer les clusters en fonction de vos préférences et comment créer une requête de publication pour tous les clusters.
// cluster for popular movies
val recommendationCluster1 = RecommendationCluster
.Builder()
.addEntity(movie)
.addEntity(tvShow)
.setTitle("Popular Movies")
.build()
// cluster for top searches
val recommendationCluster2 = RecommendationCluster
.Builder()
.addEntity(movie)
.addEntity(tvShow)
.setTitle("Top Searches")
.build()
// creating a publishing request
val recommendationRequest = PublishRecommendationClustersRequest
.Builder()
.setSyncAcrossDevices(true)
.setAccountProfile(accountProfile)
.addRecommendationCluster(recommendationCluster1)
.addRecommendationCluster(recommendationCluster2)
.build()
Créer un profil de compte
Pour personnaliser votre expérience sur Google TV, fournissez des informations sur votre compte et votre profil. Utilisez AccountProfile
pour fournir:
- ID de compte: identifiant unique représentant le compte de l'utilisateur dans votre application. Il peut s'agir de l'ID de compte réel ou d'une version obscurcie de manière appropriée.
- ID de profil (facultatif): si votre application accepte plusieurs profils dans un même compte, fournissez un identifiant unique pour le profil utilisateur spécifique.
- Locale(facultatif): vous pouvez éventuellement indiquer la langue préférée de l'utilisateur.
Ce champ est utile si vous envoyez
MediaActionFeedEntity
dansRecommendationRequest
.
// If app only supports account
val accountProfile = AccountProfile.Builder()
.setAccountId("account_id")
.build();
// If app supports both account and profile
val accountProfile = AccountProfile.Builder()
.setAccountId("account_id")
.setProfileId("profile_id")
.build();
// set Locale
val accountProfile = AccountProfile.Builder()
.setAccountId("account_id")
.setProfileId("profile_id")
.setLocale("en-US")
.build();
Lorsque le service reçoit la requête, les actions suivantes ont lieu dans une seule transaction:
- Les données
RecommendationsCluster
existantes du développeur partenaire sont supprimées. - Les données de la requête sont analysées et stockées dans
RecommendationsCluster
mis à jour. En cas d'erreur, la requête entière est rejetée, et l'état existant est maintenu.
Synchronisation entre appareils
L'indicateur SyncAcrossDevices
contrôle si les données de regroupement des recommandations d'un utilisateur sont partagées avec Google TV et disponibles sur tous ses appareils, tels que les téléviseurs, les téléphones et les tablettes. Pour que la recommandation fonctionne, elle doit être définie sur "true".
Obtenir le consentement
L'application multimédia doit fournir un paramètre clair pour activer ou désactiver la synchronisation entre les appareils. Expliquez les avantages à l'utilisateur, stockez ses préférences une fois et appliquez-les dans la requête publishRecommendations
en conséquence. Pour exploiter pleinement la fonctionnalité inter-appareils, vérifiez que l'application obtient le consentement de l'utilisateur et active SyncAcrossDevices
sur true
.
Supprimer les données de découverte de vidéos
Pour supprimer manuellement les données d'un utilisateur du serveur Google TV avant la période de conservation standard de 60 jours, utilisez la méthode client.deleteClusters()
. À la réception de la requête, le service supprime toutes les données de découverte de vidéos existantes pour le profil du compte ou pour l'ensemble du compte.
L'énumération DeleteReason
définit la raison de la suppression des données.
Le code suivant supprime les recommandations à la déconnexion.
// If the user logs out from your media app, you must make the following call
// to remove recommendations data from the current google TV device,
// otherwise, the recommendations data persists on the current
// google TV device until 60 days later.
client.deleteClusters(
new DeleteClustersRequest.Builder()
.setAccountProfile(AccountProfile())
.setReason(DeleteReason.DELETE_REASON_USER_LOG_OUT)
.build()
)
// If the user revokes the consent to share data with Google TV,
// you must make the following call to remove recommendations data from
// all current google TV devices. Otherwise, the recommendations data persists
// until 60 days later.
client.deleteClusters(
new DeleteClustersRequest.Builder()
.setAccountProfile(AccountProfile())
.setReason(DeleteReason.DELETE_REASON_LOSS_OF_CONSENT)
.build()
)
Créer des entités
Le SDK a défini différentes entités pour représenter chaque type d'élément. Les entités suivantes sont acceptées pour le cluster "Recommandations" :
MediaActionFeedEntity
MovieEntity
TvShowEntity
Description
Fournissez une brève description pour chaque entité. Cette description s'affichera lorsque les utilisateurs passeront le pointeur sur l'entité, leur fournissant des informations supplémentaires.
URI de lecture spécifiques à la plate-forme
Créez des URI de lecture pour chaque plate-forme compatible: Android TV, Android ou iOS. Cela permet au système de sélectionner l'URI approprié pour la lecture vidéo sur la plate-forme concernée.
Dans le cas rare où les URI de lecture sont identiques pour toutes les plates-formes, répétez-les pour chaque plate-forme.
// Required. Set this when you want recommended entities to show up on
// Google TV
val playbackUriTv = PlatformSpecificUri
.Builder()
.setPlatformType(PlatformType.TYPE_ANDROID_TV)
.setActionUri(Uri.parse("https://www.example.com/entity_uri_for_tv"))
.build()
// Optional. Set this when you want recommended entities to show up on
// Google TV Android app
val playbackUriAndroid = PlatformSpecificUri
.Builder()
.setPlatformType(PlatformType.TYPE_ANDROID_MOBILE)
.setActionUri(Uri.parse("https://www.example.com/entity_uri_for_android"))
.build()
// Optional. Set this when you want recommended entities to show up on
// Google TV iOS app
val playbackUriIos = PlatformSpecificUri
.Builder()
.setPlatformType(PlatformType.TYPE_IOS)
.setActionUri(Uri.parse("https://www.example.com/entity_uri_for_ios"))
.build()
val platformSpecificPlaybackUris =
Arrays.asList(playbackUriTv, playbackUriAndroid, playbackUriIos)
// Provide appropriate rating for the system.
val contentRating = new RatingSystem
.Builder()
.setAgencyName("MPAA")
.setRating("PG-13")
.build()
Images poster
Les images de l'affiche nécessitent un URI et des dimensions en pixels (hauteur et largeur). Ciblez différents facteurs de forme en fournissant plusieurs images de type "affiche", mais vérifiez que toutes les images conservent un format 16:9 et une hauteur minimale de 200 pixels pour un affichage correct de l'entité "Recommandations", en particulier dans l'espace de divertissement de Google. Les images dont la hauteur est inférieure à 200 pixels ne sont pas nécessairement affichées.
Image image1 = new Image.Builder()
.setImageUri(Uri.parse("http://www.example.com/entity_image1.png");)
.setImageHeightInPixel(300)
.setImageWidthInPixel(169)
.build()
Image image2 = new Image.Builder()
.setImageUri(Uri.parse("http://www.example.com/entity_image2.png");)
.setImageHeightInPixel(640)
.setImageWidthInPixel(360)
.build()
// And other images for different form factors.
val images = Arrays.asList(image1, image2)
Motif de la recommandation
Vous pouvez éventuellement fournir une raison de recommandation qui peut être utilisée par Google TV pour expliquer pourquoi suggérer un film ou une série TV spécifique à l'utilisateur.
//Allows us to construct reason: "Because it is top 10 on your Channel"
val topOnPartner = RecommendationReasonTopOnPartner
.Builder()
.setNum(10) //any valid integer value
.build()
//Allows us to construct reason: "Because it is popular on your Channel"
val popularOnPartner = RecommendationReasonPopularOnPartner
.Builder()
.build()
//Allows us to construct reason: "New to your channel, or Just added"
val newOnPartner = RecommendationReasonNewOnPartner
.Builder()
.build()
//Allows us to construct reason: "Because you watched Star Wars"
val watchedSimilarTitles = RecommendationReasonWatchedSimilarTitles
.addSimilarWatchedTitleName("Movie or TV Show Title")
.addSimilarWatchedTitleName("Movie or TV Show Title")
.Builder()
.build()
//Allows us to construct reason: "Recommended for you by ChannelName"
val recommendedForUser = RecommendationReasonRecommendedForUser
.Builder()
.build()
val watchAgain = RecommendationReasonWatchAgain
.Builder()
.build()
val fromUserWatchList = RecommendationReasonFromUserWatchlist
.Builder()
.build()
val userLikedOnPartner = RecommendationReasonUserLikedOnPartner
.Builder()
.setTitleName("Movie or TV Show Title")
.build()
val generic = RecommendationReasonGeneric.Builder().build()
Fenêtre de durée d'affichage
Si une entité ne doit être disponible que pendant une durée limitée, définissez un délai d'expiration personnalisé. Sans délai d'expiration explicite, les entités expirent automatiquement et sont effacées au bout de 60 jours. Définissez donc une heure d'expiration uniquement lorsque les entités doivent expirer plus tôt. Spécifiez plusieurs périodes de disponibilité de ce type.
val window1 = DisplayTimeWindow
.Builder()
.setStartTimeStampMillis(now()+ 1.days.toMillis())
.setEndTimeStampMillis(now()+ 30.days.toMillis())
val window2 = DisplayTimeWindow
.Builder()
.setEndTimeStampMillis(now()+ 30.days.toMillis())
val availabilityTimeWindows: List<DisplayTimeWindow> = listof(window1,window2)
DataFeedElementId
Si vous avez intégré votre catalogue multimédia ou votre flux d'actions multimédias à Google TV, vous n'avez pas besoin de créer d'entités distinctes pour les films ou les séries TV. Vous pouvez plutôt créer une entité MediaActionFeed qui inclut le champ DataFeedElementId obligatoire. Cet ID doit être unique et correspondre à celui du flux d'actions multimédias, car il permet d'identifier le contenu du flux ingéré et d'effectuer des recherches de contenu multimédia.
val id = "dataFeedEleemntId"
MovieEntity
Voici un exemple de création d'un MovieEntity
avec tous les champs obligatoires:
val movieEntity = MovieEntity.Builder()
.setName("Movie name")
.setDescription("A sentence describing movie.")
.addPlatformSpecificPlaybackUri(platformSpecificPlaybackUris)
.addPosterImages(images)
// Suppose the duration is 2 hours, it is 72000000 in milliseconds
.setDurationMills(72000000)
.build()
Vous pouvez fournir des données supplémentaires telles que les genres, les classifications de contenu, la date de sortie, le motif de recommandation et les périodes de disponibilité, qui peuvent être utilisées par Google TV à des fins d'affichage ou de filtrage améliorés.
val genres = Arrays.asList("Action", "Science fiction");
val rating1 = RatingSystem.Builder().setAgencyName("MPAA").setRating("pg-13").build();
val contentRatings = Arrays.asList(rating1);
//Suppose release date is 11-02-2025
val releaseDate = 1739233800000L
val movieEntity = MovieEntity.Builder()
...
.addGenres(genres)
.setReleaseDateEpochMillis(releaseDate)
.addContentRatings(contentRatings)
.setRecommendationReason(topOnPartner or watchedSimilarTitles)
.addAllAvailabilityTimeWindows(availabilityTimeWindows)
.build()
TvShowEntity
Voici un exemple de création d'un TvShowEntity
avec tous les champs obligatoires:
val tvShowEntity = TvShowEntity.Builder()
.setName("Show title")
.setDescription("A sentence describing TV Show.")
.addPlatformSpecificPlaybackUri(platformSpecificPlaybackUris)
.addPosterImages(images)
.build();
Vous pouvez fournir des données supplémentaires, telles que les genres, les classifications de contenu, le motif de recommandation, le prix de l'offre, le nombre de saisons ou la période de disponibilité, qui peuvent être utilisées par Google TV à des fins d'affichage ou de filtrage améliorés.
val genres = Arrays.asList("Action", "Science fiction");
val rating1 = RatingSystem.Builder()
.setAgencyName("MPAA")
.setRating("pg-13")
.build();
val price = Price.Builder()
.setCurrentPrice("$14.99")
.setStrikethroughPrice("$16.99")
.build();
val contentRatings = Arrays.asList(rating1);
val seasonCount = 5;
val tvShowEntity = TvShowEntity.Builder()
...
.addGenres(genres)
.addContentRatings(contentRatings)
.setRecommendationReason(topOnPartner or watchedSimilarTitles)
.addAllAvailabilityTimeWindows(availabilityTimeWindows)
.setSeasonCount(seasonCount)
.setPrice(price)
.build()
MediaActionFeedEntity
Voici un exemple de création d'un MediaActionFeedEntity
avec tous les champs obligatoires:
val mediaActionFeedEntity = MediaActionFeedEntity.Builder()
.setDataFeedElementId(id)
.build()
Vous pouvez fournir des données supplémentaires, telles que la description, le motif de la recommandation et la période d'affichage, qui peuvent être utilisées par Google TV à des fins d'affichage amélioré ou de filtrage.
val mediaActionFeedEntity = MediaActionFeedEntity.Builder()
.setName("Movie name or TV Show name")
.setDescription("A sentence describing an entity")
.setRecommendationReason(topOnPartner or watchedSimilarTitles)
.addPosterImages(images)
.build()
En suivant ces étapes, les développeurs peuvent intégrer des recommandations de contenus vidéo à Google TV, ce qui améliore la découverte et l'engagement des utilisateurs, et leur offre une expérience de visionnage cohérente et personnalisée sur tous leurs appareils.