Escrever consultas SOQL
Objetivos de aprendizagem
Após concluir esta unidade, você estará apto a:
- Escrever consultas SOQL no Apex.
- Executar consultas SOQL utilizando o Editor de consulta no Developer Console.
- Executar consultas SOQL integradas ao Apex utilizando Apex anônimo.
- Registros relacionados a consultas.
Introdução ao SOQL
Para ler um registro do Salesforce, você precisa escrever uma consulta. O Salesforce fornece o Salesforce Object Query Language (SOQL), que você pode usar para ler registros salvos. A SOQL é semelhante à linguagem SQL padrão, mas é personalizada para a Lightning Platform.
Como o Apex tem acesso direto aos registros do Salesforce que são armazenados no banco de dados, você pode incorporar consultas SOQL em seu código do Apex e obter resultados de forma simples. Quando a SOQL é incorporada ao Apex, ela é referenciada como SOQL embutida.
Para incluir consultas SOQL dentro do seu código do Apex, coloque a instrução SOQL entre colchetes e atribua o valor de retorno a uma matriz de sObjects. Por exemplo, o seguinte recupera todos os registros de conta que tenham dois campos – nome e telefone – e retorna uma matriz de sObjects da conta.
Account[] accts = [SELECT Name,Phone FROM Account];
Pré-requisitos
Algumas consultas nesta unidade esperam que a organização tenha contas e contatos. Antes de executar as consultas, crie alguns dados de amostra.
- No Console do desenvolvedor, abra a janela Executar anônimo no menu Depurar.
- Insira o trecho de código abaixo na janela e clique em Executar.
// Add account and related contact Account acct = new Account( Name='SFDC Computing', Phone='(415)555-1212', NumberOfEmployees=50, BillingCity='San Francisco'); insert acct; // Once the account is inserted, the sObject will be // populated with an ID. // Get this ID. ID acctID = acct.ID; // Add a contact to this account. Contact con = new Contact( FirstName='Carol', LastName='Ruiz', Phone='(415)555-1212', Department='Wingo', AccountId=acctID); insert con; // Add account with no contact Account acct2 = new Account( Name='The SFDC Query Man', Phone='(310)555-1213', NumberOfEmployees=50, BillingCity='Los Angeles', Description='Expert in wing technologies.'); insert acct2;
Usar o editor de consulta
O Developer Console fornece o console do Editor de consulta, que permite executar consultas SOQL e exibir os resultados. O Editor de consulta oferece uma forma rápida de inspecionar o banco de dados. É uma boa maneira de testar as consultas SOQL antes de adicioná-las ao seu código do Apex. Ao usar o Editor de consulta, é obrigatório fornecer apenas a instrução SOQL, sem o código do Apex que a rodeia.
Tente executar o seguinte exemplo de SOQL:
- No Console do desenvolvedor, clique na guia Editor de consulta.
- Copie e cole o seguinte no primeiro campo do Editor de consulta e, em seguida, clique em Executar.
SELECT Name,Phone FROM Account
Todos os registros de conta da sua organização são exibidos na seção Query Results (Resultados da consulta) como linhas com campos.
Sintaxe básica SOQL
Esta é a sintaxe de uma consulta SOQL básica:
SELECT fields FROM ObjectName [WHERE Condition]
A cláusula WHERE é opcional. Vamos começar com uma consulta muito simples. Por exemplo, a consulta a seguir recupera contas e obtém os campos Nome e Telefone para cada conta.
SELECT Name,Phone FROM Account
A consulta tem duas partes:
-
SELECT Name,Phone
: Esta parte lista os campos que você gostaria de recuperar. Os campos são especificados depois da palavra-chave SELECT em uma lista delimitada por vírgula. Ou você pode especificar apenas um campo; nesse caso, nenhuma vírgula é necessária (por exemplo,SELECT Phone
(Selecionar telefone).
-
FROM Account
(Da conta): Esta parte especifica o objeto personalizado ou padrão que você deseja recuperar. Neste exemplo, é Conta. Para um objeto personalizado chamado Invoice_Statement, é Invoice_Statement__c.
Filtrar resultados de consultas com condições
Se você tiver mais de uma conta na organização, todas elas serão retornadas. Se quiser limitar as contas retornadas para contas que cumprem uma determinada condição, você pode adicionar essa condição dentro da cláusula WHERE. O exemplo a seguir recupera apenas as contas cujos nomes são SFDC Computing. Observe que as comparações nas strings não diferenciam caracteres maiúsculos e minúsculos.
SELECT Name,Phone FROM Account WHERE Name='SFDC Computing'
A cláusula WHERE pode conter várias condições que são agrupadas usando operadores lógicos (AND, OR) e parênteses. Por exemplo, esta consulta retorna todas as contas com o nome SFDC Computing que tenham mais de 25 funcionários:
SELECT Name,Phone FROM Account WHERE (Name='SFDC Computing' AND NumberOfEmployees>25)
Temos agora outro exemplo com uma condição mais complexa. Esta consulta retorna todos esses registros:
- Todas as contas SFDC Computing
- Todas as contas com mais de 25 funcionários cuja cidade de faturamento seja Los Angeles
SELECT Name,Phone FROM Account WHERE (Name='SFDC Computing' OR (NumberOfEmployees>25 AND BillingCity='Los Angeles'))
Ordenar os resultados da consulta
Quando uma consulta é executada, ela não retorna os registros do Salesforce em uma ordem específica, então não dá para confiar que a ordem dos registros da matriz retornada seja a mesma sempre que a consulta for executada. No entanto, você pode optar por classificar o registro retornado adicionando uma cláusula ORDER BY e especificando o campo pelo qual o conjunto de registros deve ser classificado. O exemplo a seguir classifica todas as contas recuperadas com base no campo de nome.
SELECT Name,Phone FROM Account ORDER BY Name
A ordem de classificação padrão é a ordem alfabética, especificada como ASC. A instrução anterior é equivalente a:
SELECT Name,Phone FROM Account ORDER BY Name ASC
Para inverter a ordem, use a palavra-chave DESC para ordem decrescente:
SELECT Name,Phone FROM Account ORDER BY Name DESC
Você pode classificar a maioria dos campos, inclusive campos numéricos e de texto. Não é possível classificar campos como o rich text e listas de opções de seleção múltipla.
Experimente estas instruções SOQL no Editor de consulta e veja como a ordem do registro retornado muda de acordo com o campo de nome.
Limitar o número de registros retornados
Você pode limitar o número de registros retornados a um número arbitrário, adicionando a cláusula LIMIT n
, em que n é o número de registros que você deseja obter. Limitar o conjunto de resultados é útil quando os tipos de registros retornados não importam, e você apenas deseja trabalhar com um subconjunto de registros. Por exemplo, esta consulta recupera a primeira conta que é retornada. Observe que o valor retornado é uma conta e não uma matriz quando LIMIT 1
é usado.
Account oneAccountOnly = [SELECT Name,Phone FROM Account LIMIT 1];
Juntar todas as peças
É possível combinar as cláusulas opcionais em uma consulta, na seguinte ordem:
SELECT Name,Phone FROM Account WHERE (Name = 'SFDC Computing' AND NumberOfEmployees>25) ORDER BY Name LIMIT 10
Execute a seguinte consulta SOQL no Apex usando a janela Execute Anonymous (Executar anônimo) do Developer Console. Em seguida, inspecione as instruções de depuração no registro de depuração. Uma conta de exemplo será retornada.
Account[] accts = [SELECT Name,Phone FROM Account WHERE (Name='SFDC Computing' AND NumberOfEmployees>25) ORDER BY Name LIMIT 10]; System.debug(accts.size() + ' account(s) returned.'); // Write all account array info System.debug(accts);
Acessar variáveis em consultas SOQL
As instruções SOQL no Apex podem referenciar expressões e variáveis de código do Apex se forem precedidas por dois pontos (:). O uso de uma variável local dentro de uma instrução SOQL é chamado de vínculo.
Este exemplo mostra como usar a variável targetDepartment
na cláusula WHERE.
String targetDepartment = 'Wingo'; Contact[] techContacts = [SELECT FirstName,LastName FROM Contact WHERE Department=:targetDepartment];
Consultar registros relacionados
Os registros no Salesforce podem ser ligados uns aos outros por meio de relacionamentos: relacionamentos de pesquisa ou relacionamentos entre mestre e detalhes. Por exemplo, o Contato possui um relacionamento de pesquisa com a Conta. Ao criar ou atualizar um contato, você pode associá-lo a uma conta. Os contatos associados à mesma conta aparecem em uma lista relacionada na página da conta. Assim como é possível visualizar os registros relacionados na interface de usuário do Salesforce, você pode consultar os registros relacionados na SOQL.
Para obter registros filhos relacionados a um registro pai, adicione uma consulta interna para os registros filhos. A cláusula FROM da consulta interna é executada em relação ao nome do relacionamento e não ao nome de um objeto do Salesforce. O exemplo a seguir contém uma consulta interna para obter todos os contatos que estão associados a cada conta retornada. A cláusula FROM especifica o relacionamento Contatos, que é um relacionamento padrão na Conta que liga contas e contatos.
SELECT Name, (SELECT LastName FROM Contacts) FROM Account WHERE Name = 'SFDC Computing'
O próximo exemplo incorpora a consulta SOQL de exemplo no Apex e mostra como obter os registros filhos do resultado da SOQL usando o nome do relacionamento Contatos no sObject.
Account[] acctsWithContacts = [SELECT Name, (SELECT FirstName,LastName FROM Contacts) FROM Account WHERE Name = 'SFDC Computing']; // Get child records Contact[] cts = acctsWithContacts[0].Contacts; System.debug('Name of first associated contact: ' + cts[0].FirstName + ', ' + cts[0].LastName);
Você pode percorrer um relacionamento de um objeto filho (contato) a um campo de seu pai (Account.Name) usando a notação de ponto. Por exemplo, o trecho de código Apex a seguir consulta os registros de contatos cujo primeiro nome é Carol e consegue recuperar o nome da conta associada da Carol percorrendo o relacionamento entre contas e contatos.
Contact[] cts = [SELECT Account.Name FROM Contact WHERE FirstName = 'Carol' AND LastName='Ruiz']; Contact carol = cts[0]; String acctName = carol.Account.Name; System.debug('Carol\'s account name is ' + acctName);
Consultar registros em lotes usando loops for SOQL
Com um loop for SOQL, você pode incluir uma consulta SOQL em um loop for
. Os resultados de uma consulta SOQL podem ser iterados dentro do loop. Os loops for SOQL usam um método diferente para recuperar registros; os registros são recuperados por meio de agrupamento eficiente, com chamadas para a consulta e métodos queryMore da API SOAP. Usando os loops for SOQL, você pode evitar bater o limite de tamanho do heap.
Os loops for
SOQL iteram sobre todos os registros sObject retornados por uma consulta SOQL. A sintaxe de um loop for
SOQL pode ser:
for (variable : [soql_query]) { code_block }
ou
for (variable_list : [soql_query]) { code_block }
Tanto variable
quanto variable_list
devem ser do mesmo tipo que os sObjects retornados pela soql_query
.
É preferível usar o formato de lista sObject do loop for SOQL, pois o loop é executado uma vez para cada lote de 200 sObjects. Dessa forma, você pode trabalhar em lotes de registros e executar operações DML em lote, o que ajuda a evitar atingir os limites de administrador.
insert new Account[]{new Account(Name = 'for loop 1'), new Account(Name = 'for loop 2'), new Account(Name = 'for loop 3')}; // The sObject list format executes the for loop once per returned batch // of records Integer i=0; Integer j=0; for (Account[] tmp : [SELECT Id FROM Account WHERE Name LIKE 'for loop _']) { j = tmp.size(); i++; } System.assertEquals(3, j); // The list should have contained the three accounts // named 'yyy' System.assertEquals(1, i); // Since a single batch can hold up to 200 records and, // only three records should have been returned, the // loop should have executed only once
Recursos