Création de requêtes de relation avec des objets standard
Objectifs de formation
Une fois cette unité terminée, vous pourrez :
- Décrire deux types de requêtes de relation
- Identifier la relation entre deux objets
- Créer une requête enfant-parent à l’aide de la notation par point
- Créer une requête parent-enfant à l’aide d’une sous-requête
- Utiliser une sous-requête pour filtrer les résultats d’une requête
Vidéo de démonstration Trail Together
Vous souhaitez être guidé pas à pas par un expert pendant que vous travaillez sur cette étape ? Regardez cette vidéo qui fait partie de la série Trail Together sur Trailhead Live.
(Ce clip commence à 36 min 18 s, au cas où vous voudriez revenir en arrière et regarder à nouveau le début de l’étape.)
À propos des requêtes de relation
En tant qu’administrateur Salesforce, vous connaissez déjà les champs de formule qui extraient des données d’enregistrements associés. Vous pouvez désormais appliquer votre connaissance sur les relations d’objet à l’écriture de requêtes SOQL.
Bien que la clause FROM soit limitée à un seul objet, nous pouvons accéder à deux objets associés en utilisant une requête de relation. Une requête de relation s’appuie sur la relation entre deux objets différents pour renvoyer les champs de ces deux objets. Vous pouvez la considérer comme une requête inter-objets.
Prenons cette exigence :
« Obtenir une liste de tous les contacts avec le nom de compte de chaque contact. »
Nous pouvons interroger l’objet Contact, mais il ne contient pas de champ « Nom du compte ». Le nom de compte est en fait le champ « Nom » du compte associé au contact. Dans une organisation, vous utilisez un champ de formule pour accéder à un champ de n’importe quel objet associé. Dans Apex, vous utilisez une requête de relation, mais le type de requête de relation dépend de la façon dont les deux objets sont associés.
Pour obtenir des enregistrements pour :
- un objet enfant et inclure des champs d’un objet parent associé, utilisez une requête enfant-parent ;
- un objet parent et inclure des champs d’un objet enfant associé, utilisez une requête parent-enfant.
Avant de pouvoir décider du type de requête à utiliser, nous devons savoir comment nos deux objets (Contact et Compte) sont associés. Qui est le parent et qui est l’enfant ?
Identification de la relation entre des objets
En tant qu’administrateur, vous connaissez les relations principal-détails dans une organisation. Une relation principal-détails est une relation parent-enfant. L’objet principal est le parent et l’objet de détail est l’enfant. Si les deux objets que vous souhaitez inclure dans une requête ont une relation principal-détails, vous savez alors lequel est le parent et lequel est l’enfant.
Si vous ne connaissez pas les deux objets que vous souhaitez inclure dans une requête, ou si vous ne savez pas comment ils sont associés, explorez-les dans le gestionnaire d’objet. Commencez par l’objet qui est le plus susceptible d’être l’enfant et examinez ses champs et relations. Recherchez un nom de champ qui pourrait être lié à l’objet parent.
Par exemple, Contact comprend un champ AccountId avec le type de données Référence(Compte). Rappelez-vous, lorsque l’on code, nous avons besoin du nom de champ (AccountId) et non de l’étiquette de champ (Nom du compte).
Dans les détails du champ AccountId, le nom de la relation enfant est Contacts, au pluriel. Par défaut, pour les objets standard, le nom de la relation est le nom de l’objet enfant au pluriel.
Le nom de la relation enfant permet de confirmer que Contact est un enfant de Compte. Il nous donne également le nom de la relation dont nous avons besoin pour une requête parent-enfant (que nous aborderons plus loin dans cette unité).
Création d’une requête enfant-parent
Nous savons maintenant que Contact et Compte ont une relation enfant-parent. Contact est l’enfant et Compte est le parent. Pour renvoyer tous les contacts (enfants) et le nom de compte (parent) de chaque contact, nous avons besoin d’une requête enfant-parent.
Dans une requête enfant-parent, vous interrogez l’objet enfant et récupérez les champs d’un objet parent en utilisant la notation par point, comme suit :
SELECT Name, Account.Name FROM Contact
Cette instruction SELECT interroge l’objet Contact. Dans la clause SELECT, Name
est le champ Nom du contact et Account.Name
est le champ Nom du compte associé au contact.
Exécution de la requête enfant-parent
- Dans l’éditeur de requête de la Developer Console, saisissez ce qui suit :
SELECT Name, Account.Name FROM Contact
- Cliquez sur Execute (Exécuter).
Les six premières lignes de vos résultats doivent être les suivantes :
Résultats de requête – Total des lignes : 20 |
|
Nom |
Account.Name |
Rose Gonzales |
Edge Communications |
Sean Forbes |
Edge Communications |
Jack Rogers |
Burlington Textiles Corp of America |
Pat Stumuller |
Pyramid Construction Inc. |
Andy Young |
Dickenson plc |
Tim Barr |
Grand Hotels & Resorts Ltd |
La deuxième colonne affiche le nom du compte de l’objet Compte parent du contact.
Création d’une requête parent-enfant
Voyons maintenant comment interroger un objet parent et obtenir des champs à partir de son objet enfant. Dans une requête parent-enfant, nous utilisons une sous-requête pour obtenir des champs de l’objet enfant. Une sous-requête est une instruction SELECT entre parenthèses et imbriquée dans une autre requête.
Imaginons que notre exigence soit :
« Pour chaque compte, renvoyer le nom du compte et le nom de chaque contact associé. »
Lorsque nous lisons « de chaque [...] associé », nous savons que nous avons besoin d’une requête de relation. Étant donné que Contact est un enfant de Compte, nous avons besoin d’une requête de relation parent-enfant, qui contient une sous-requête de l’objet enfant.
La première partie de l’exigence, « Pour chaque compte, renvoyer le nom du compte » devient la requête principale, qui forme la partie externe de la totalité de la requête. La deuxième partie de l’exigence, « le nom de chaque contact associé » devient la sous-requête, la requête interne imbriquée dans la requête principale.
Nous définissons d’abord la requête principale : SELECT Name FROM Account
Ensuite, nous définissons la sous-requête entre parenthèses : (SELECT Name FROM Contact)
Enfin, nous plaçons la sous-requête comme s’il s’agissait du deuxième champ de la requête principale. Nous ajoutons une virgule après Name, puis insérons la sous-requête, comme suit :
Dans une sous-requête, au lieu du nom du champ de l’objet associé, nous utilisons le nom de la relation enfant. Donc, pour terminer, nous modifions la sous-requête afin d’utiliser le nom de la relation enfant Contacts
, au lieu du nom de l’objet Contact
, comme suit :
Cette requête renvoie le nom du compte et les noms des contacts de tous les comptes. Décomposons ces différents éléments.
Cette requête s’exécute en trois parties :
- La requête sélectionne un compte et obtient le champ Nom du compte. Il s’agit de la requête principale (la requête externe).
- Ensuite, la requête examine les contacts associés au compte et obtient le champ Nom de chacun d’eux. Il s’agit de la sous-requête (la requête interne).
- Enfin, elle passe au compte suivant et répète le processus jusqu’à ce qu’elle ait sélectionné tous les comptes.
Exécution de la requête parent-enfant
- Dans l’éditeur de requête, saisissez :
SELECT Name, (SELECT Name FROM Contacts) FROM Account
- Cliquez sur Execute (Exécuter).
Les six premières lignes de vos résultats doivent être les suivantes :
Résultats de requête – Total des lignes : 12 |
|
Nom |
Contacts |
Edge Communications |
[{"Nom":"Rose Gonzalez"},{"Nom":"Sean Forbes"}] |
Burlington Textiles Corp of America |
[{"Nom":"Jack Rogers"}] |
Pyramid Construction Inc. |
[{"Nom":"Pat Stumuller"}] |
Dickenson plc |
[{"Nom":"Andy Young"}] |
Grand Hotels & Resorts Ltd |
[{"Nom":"John Bond"},{"Nom":"Tim Barr"}] |
United Oil & Gas Corp. |
[{"Nom":"Arthur Song"},{"Nom":"Avi Green"},{"Nom":"Lauren Boyle"},{"Nom":"Stella Pavlova"}] |
Intéressant ! La fenêtre Résultats de requête affiche les noms de compte et une collection d’enregistrements de contacts enfant associés à chaque compte. Ce type de collection vous est probablement familier, car nous avons parlé des cartes dans le module Programmation orientée objet pour les administrateurs.
Si vous ne vous souvenez pas de ce qu’est une carte, ne vous inquiétez pas, voici un rappel. Une collection de cartes contient des paires clé-valeur séparées par une virgule. La clé est le nom du champ, par exemple Nom. La clé est suivie de sa valeur, par exemple Jake Llorrac. Les paires clé-valeur sont renvoyées par l’instruction SELECT imbriquée qui interroge les contacts associés au compte.
Filtrage à l’aide d’une sous-requête
Imaginons que nous recherchions uniquement les comptes avec un contact associé dont le nom de famille est Forbes. Ce n’est pas facile, car nous voulons filtrer l’objet parent, Compte, en fonction d’une valeur de l’objet enfant, Contact. De la même manière que nous avons imbriqué une sous-requête dans la requête principale, nous pouvons utiliser une sous-requête (de l’objet enfant) dans la clause WHERE de la requête principale. Les résultats de la sous-requête ont un rôle de filtre sur la requête principale. Si vous connaissez les filtres croisés, l’ajout de la clause WHERE dans la sous-requête équivaut à l’utilisation d’un filtre croisé dans un rapport.
Nous commençons avec notre requête existante :SELECT Name, (SELECT Name FROM Contacts) FROM Account
Ensuite, nous avons besoin d’une sous-requête qui récupère le champ AccountId des contacts dont le nom de famille est Forbes :
(SELECT AccountId FROM Contact WHERE LastName = 'Forbes')
Vous vous demandez peut-être pourquoi nous avons besoin du champ AccountId du contact. Nous vérifions le champ AccountId du contact pour trouver les contacts associés à un compte. Un contact est associé à un compte lorsque le champ AccountId de l’objet Contact et le champ ID de l’objet compte ont la même valeur (Contact.AccountId = Account.Id
). Nous interrogeons donc l’objet Contact et renvoyons sa valeur AccountId. Pour sélectionner le compte associé au contact, nous cherchons le compte qui affiche cette valeur dans son champ ID.
Enfin, nous ajoutons une clause WHERE à la requête principale. Nous souhaitons sélectionner un enregistrement de compte uniquement si son ID se trouve dans le champ AccountId d’un contact renvoyé par la sous-requête. Par conséquent, nous ajoutons WHERE Id IN
suivi de la sous-requête, comme suit :
SELECT Name, (SELECT Name FROM Contacts) FROM Account WHERE Id IN (SELECT AccountId FROM Contact WHERE LastName = 'Forbes')
Cette requête effectue quatre actions.
- La requête recherche les contacts dont le nom est Forbes et renvoie la valeur du champ AccountId de chaque contact. (Cette action est effectuée par la sous-requête de la clause WHERE.)
- Ensuite, elle recherche la valeur de ce champ AccountId dans le champ ID d’un compte et obtient le nom de ce compte. (Cette action est effectuée par la clause WHERE principale.)
- Ensuite, la requête examine les contacts associés au compte et obtient le nom de chaque contact. (Cette action est effectuée par la sous-requête de la requête principale.)
- Enfin, la requête principale renvoie le nom de chaque compte qui a un contact associé dont le nom de famille est Forbes et, pour chacun de ces comptes, le nom de tous les contacts associés.
Exécution de la requête filtrée
- Dans l’éditeur de requête, saisissez :
SELECT Name, (SELECT Name FROM Contacts) FROM Account WHERE Id IN (SELECT AccountId FROM Contact WHERE LastName = 'Forbes')
- Cliquez sur Execute (Exécuter).
Vos résultats doivent se présenter comme suit :
Récapitulatif
Vous savez maintenant comment choisir et créer le bon type de requête de relation pour les objets standard. Dans l’unité suivante, vous découvrirez les requêtes de relation pour les objets personnalisés.