Mapper les LCA

Pour vous assurer que seuls les utilisateurs autorisés à accéder à un élément peuvent le voir dans un résultat de recherche, vous devez indexer les éléments avec leurs listes de contrôle d'accès (LCA) à partir du dépôt d'entreprise. Vous devez modéliser les LCA de votre dépôt et les inclure lors de l'indexation des éléments de ce dernier. Le SDK Content Connector propose un vaste choix de méthodes suffisamment performantes pour modéliser les LCA de la plupart des dépôts.

Créer une LCA

La création d'une LCA comprend deux étapes:

  1. Créez un objet Principal à l'aide des méthodes statiques de la classe ACL.
  2. Utilisez la classe Acl.Builder pour créer la LCA à l'aide du principal.

Pour modéliser et créer des LCA, vous avez besoin de maîtriser d'autres notions comme l'héritage et les conteneurs. Celles-ci sont abordées dans la suite de ce document.

Créer un compte principal à l'aide d'un ID externe

Dans Google Cloud Search, les utilisateurs et les groupes doivent être associés à des adresses e-mail Google. Or, lors de l'indexation des éléments du dépôt, il se peut que des connecteurs de contenu soient associés à des adresses autres que Google. Toutefois, le SDK Content Connector vous permet d'indexer un élément à l'aide d'un ID externe (autorisant l'accès d'un utilisateur ou d'un groupe aux éléments du dépôt), au lieu d'une adresse e-mail. Utilisez la méthode getUserPrincipal() ou la méthode getGroupPrincpal() pour créer des principaux contenant des ID externes. La classe ACL contient plusieurs autres méthodes statiques utilisées pour créer des objets Principal.

Héritage des LCA

La notion d'héritage des LCA renvoie au fait d'accorder une autorisation, pour un élément et un utilisateur donnés, après avoir combiné les LCA de l'élément et celles de sa chaîne d'héritage. Les règles utilisées pour prendre une décision d'autorisation dépendent du dépôt et des propriétés de l'élément.

Définir l'héritage

Chaque élément peut avoir des comptes principaux autorisés directs et des comptes principaux refusés directs, spécifiés à l'aide des méthodes setReaders() et setDeniedReaders(). Le terme "compte principal autorisé direct" désigne un utilisateur identifié dans une LCA lui accordant un accès direct à un élément spécifique. À l'inverse, un compte principal refusé direct fait référence à un utilisateur identifié dans une LCA qui lui refuse cet accès.

Un élément peut également hériter de comptes principaux autorisés indirects et de comptes principaux refusés indirects via la méthode setInheritFrom(). Le terme "compte principal autorisé indirect" désigne un utilisateur disposant d'un accès indirect à un élément spécifique grâce à l'héritage de la LCA. Un compte principal refusé indirect est un utilisateur qui se voit refuser cet accès par ce même mécanisme d'héritage.

La figure 1 explique le mécanisme d'héritage des comptes principaux autorisés et refusés indirects via la méthode setInheritFrom().

Représentation des connexions entre les éléments
Figure 1. La méthode setInheritFrom().

Ces contrôles d'accès sont représentés sur la figure 1:

  • L'utilisateur 1 est un compte principal autorisé direct de l'élément A.
  • L'utilisateur 2 est un compte principal autorisé direct de l'élément B.
  • L'élément B hérite de la LCA de l'élément A.

Voici les règles qui découlent des contrôles d'accès:

  • L'utilisateur 1 n'a pas besoin d'être défini explicitement comme compte principal de l'élément B pour être un compte principal autorisé indirect de cet élément. Il hérite en effet de l'accès pour les raisons suivantes : il a été désigné comme compte principal autorisé direct de l'élément A et l'élément B hérite de la LCA de l'élément A.
  • L'utilisateur 2 n'est pas un compte principal autorisé indirect de l'élément A.

Définir le type d'héritage

Si vous définissez l'héritage à l'aide de la méthode setInheritFrom(), vous devez définir le type d'héritage à l'aide de la méthode setInheritanceType(). Le type d'héritage détermine comment la LCA d'un élément enfant est combinée avec celle de l'élément parent. Acl.InheritanceType met en œuvre trois types d'héritage:

  • BOTH_PERMIT : définissez le type d'héritage sur BOTH_PERMIT pour permettre à un utilisateur d'accéder à l'élément uniquement lorsque la LCA de l'élément enfant et la LCA héritée de l'élément parent lui accordent cet accès.

  • CHILD_OVERRIDE : définissez le type d'héritage sur CHILD_OVERRIDE pour que la LCA de l'élément enfant prévale sur la LCA héritée de l'élément parent en cas de conflit entre les deux listes. En supposant que la LCA de l'élément parent refuse l'accès à l'utilisateur (lecteur refusé) et que celui-ci dispose d'un accès à l'élément enfant comme lecteur, l'utilisateur peut encore accéder à l'élément. À l'inverse, s'il est un lecteur refusé de l'élément enfant, il n'a pas d'autorisation d'accès même si la LCA de l'élément parent la lui accorde.

  • PARENT_OVERRIDE : définissez le type d'héritage sur PARENT_OVERRIDE pour que la LCA de l'élément parent prévale sur celle de l'élément enfant en cas de conflit entre les deux listes. En supposant que la LCA de l'élément enfant refuse l'accès à l'utilisateur (lecteur refusé) et que celui-ci dispose d'un accès à l'élément parent comme lecteur, l'utilisateur peut encore accéder à l'élément. À l'inverse, s'il est un lecteur refusé de l'élément parent, il n'a pas d'autorisation d'accès même si la LCA de l'élément enfant la lui accorde.

L'ordre dans lequel une chaîne d'héritage de LCA est évaluée influe sur la décision finale (autorisation ou refus). Dans Cloud Search, l'évaluation de la chaîne s'effectue de la feuille vers la racine. Plus précisément, la décision d'ACL pour une chaîne commence par l'évaluation d'un enfant avec ses parents, et peut aller jusqu'au parent racine.

Par exemple, si l'élément enfant a le type d'héritage CHILD_OVERRIDE et que l'utilisateur a accès à l'élément enfant, Drive n'a pas besoin d'évaluer l'élément parent. Toutefois, si l'élément enfant possède PARENT_OVERRIDE ou BOTH_PERMIT, Drive continue d'évaluer l'héritage plus haut dans la chaîne.

Conteneurs et suppression d'éléments

Lorsque vous indexez un élément, vous pouvez le marquer comme conteneur à l'aide de la méthode setContainer() de la classe IndexingItemBuilder. La relation conteneur/contenu établit la hiérarchie physique des éléments et garantit leur suppression correcte. Lorsqu'un conteneur est supprimé, les éléments qu'il contient le sont également.

Les relations de conteneur sont totalement indépendantes des règles d'héritage des LCA. Par exemple, un fichier d'un système de fichiers peut se trouver dans un dossier à supprimer, mais hériter de la LCA d'un autre dossier. La suppression d'un dossier ne supprime pas les éléments qui héritent de la LCA de ce dossier, sauf si ces éléments figurent également dans l'arborescence de conteneurs.

Ces contrôles d'accès sont représentés sur la figure 2:

  • L'utilisateur 1 est un compte principal autorisé direct de l'élément A.
  • L'utilisateur 2 est un compte principal autorisé direct de l'élément B.
  • L'utilisateur 3 est un compte principal autorisé direct de l'élément C.
  • L'élément C hérite de la LCA de l'élément A.
  • L'élément B désigne l'élément A comme son conteneur.
  • L'élément C désigne l'élément B comme son conteneur.

Voici les règles qui découlent des contrôles d'accès:

  • L'accès indirect est accordé par la méthode setInheritFrom(). Par conséquent, l'utilisateur 1 peut accéder à l'élément C, car ce dernier hérite de la LCA de l'élément A.
  • L'accès indirect ne découle pas du fait que l'élément C soit contenu dans l'élément B. Par conséquent, l'utilisateur 2 n'a pas accès à l'élément C.
Représentation des connexions entre les éléments
Figure 2 Méthode setInheritFrom() utilisée.

La séparation de l'héritage des LCA de la hiérarchie de structuration vous permet de modéliser de nombreuses structures existantes.

Après la suppression d'un élément:

  • tout élément contenant un élément supprimé est exclu de l'index de recherche (sa suppression de la source de données de Google est alors programmée) ;
  • tout élément ayant désigné l'élément supprimé via la méthode setInheritFrom() est exclu de l'index de recherche.

Si une ressource contient un élément supprimé à l'aide de la méthode setInheritFrom(), mais qu'aucun conteneur n'est défini à l'aide de setContainer() ou que son arborescence de conteneurs n'inclut aucun élément supprimé, cet élément et ses données restent présents dans la source de données de Google. C'est alors à vous de supprimer l'élément.

La figure 3 illustre la procédure de suppression pour une arborescence d'éléments.

Représentation des connexions entre les éléments
Figure 3. Suppression d'un élément et héritage des LCA

Ces contrôles d'accès sont représentés sur la figure 3:

  • L'utilisateur 1 est un compte principal autorisé direct de l'élément A.
  • L'utilisateur 2 est un compte principal autorisé direct de l'élément D.
  • Les éléments D et E héritent tous deux de la LCA de l'élément A.
  • L'élément D désigne l'élément A comme son conteneur.
  • Les éléments A et E sont des éléments de niveau racine, car ils n'ont pas d'élément conteneur.

L'opération de suppression est répercutée en cascade au niveau des références de conteneur. Ainsi, en cas de suppression de l'élément A:

  • plus aucun descendant de la référence setInheritFrom() n'est accessible, et ce pour tous les utilisateurs ;
  • Aucun utilisateur ne peut accéder à l'élément A.
  • l'élément D est implicitement supprimé (aucun utilisateur ne peut y accéder) ;
  • l'élément E n'est pas supprimé, car l'opération de suppression n'est répercutée qu'au niveau des références de conteneur ;
  • l'élément E est exclu de l'index de recherche (aucun utilisateur ne peut lancer une recherche sur cet élément).