Get Started with Apex
Get Started with Apex
As a language, Apex is:
- Hosted—Apex is saved, compiled, and executed on the server—the Lightning Platform.
- Object oriented—Apex supports classes, interfaces, and inheritance.
- Strongly typed—Apex validates references to objects at compile time.
- Multitenant aware—Because Apex runs in a multitenant platform, it guards closely against runaway code by enforcing limits, which prevent code from monopolizing shared resources.
- Integrated with the database—It is straightforward to access and manipulate records. Apex provides direct access to records and their fields, and provides statements and query languages to manipulate those records.
- Data focused—Apex provides transactional access to the database, allowing you to roll back operations.
- Easy to use—Apex is based on familiar Java idioms.
- Easy to test—Apex provides built-in support for unit test creation, execution, and code coverage. Salesforce ensures that all custom Apex code works as expected by executing all unit tests prior to any platform upgrades.
- Versioned—Custom Apex code can be saved against different versions of the API.

Apex Language Highlights
Like other object-oriented programming languages, these are some of the language constructs that Apex supports:
- Classes, interfaces, properties, and collections (including arrays).
- Object and array notation.
- Expressions, variables, and constants.
- Conditional statements (if-then-else) and control flow statements (for loops and while loops).
Unlike other object-oriented programming languages, Apex supports:
- Cloud development as Apex is stored, compiled, and executed in the cloud.
- Triggers, which are similar to triggers in database systems.
- Database statements that allow you to make direct database calls and query languages to query and search data.
- Transactions and rollbacks.
- The global access modifier, which is more permissive than the public modifier and allows access across namespaces and applications.
- Versioning of custom code.
In addition, Apex is a case-insensitive language.
Development Tools
You can write Apex and access debugging information directly in the browser by using the
Salesforce user interface. Open the Developer Console under Your Name
or the quick access menu ().
You can also write Apex on a client by using the Salesforce Extensions for Visual Studio Code. See Salesforce Visual Studio Code Extensions.
Data Types Overview
Apex supports the following data types.
- A primitive, such as an Integer, Double, Long, Date, Datetime, String, ID, Boolean, among others.
- An sObject, either as a generic sObject or as a specific sObject, such as an Account, Contact, or MyCustomObject__c (you’ll learn more about sObjects in a later unit.)
- A collection, including:
- A list (or array) of primitives, sObjects, user defined objects, objects created from Apex classes, or collections
- A set of primitives
- A map from a primitive to a primitive, sObject, or collection
- A typed list of values, also known as an enum
- User-defined Apex classes
- System-supplied Apex classes
Apex Collections: List
Lists hold an ordered collection of objects. Lists in Apex are synonymous with arrays and the two can be used interchangeably.
The following two declarations are equivalent. The colors variable is declared using the List syntax.
List<String> colors = new List<String>();
Alternatively, the colors variable can be declared as an array but assigned to a list rather than an array.
String[] colors = new List<String>();
Generally, it’s easier to create a list rather than an array because lists don’t require you to determine ahead of time how many elements you need to allocate.
You can add elements to a list when creating the list, or after creating the list by calling the add() method. This first example shows you both ways of adding elements to a list.
// Create a list and add elements to it in one step List<String> colors = new List<String> { 'red', 'green', 'blue' }; // Add elements to a list after it has been created List<String> moreColors = new List<String>(); moreColors.add('orange'); moreColors.add('purple');
List elements can be read by specifying an index between square brackets, just like with array elements. Also, you can use the get() method to read a list element. This example is based on the lists created in the previous example and shows how to read list elements using either method. The example also shows how to iterate over array elements.
// Get elements from a list String color1 = moreColors.get(0); String color2 = moreColors[0]; System.assertEquals(color1, color2); // Iterate over a list to read elements for(Integer i=0;i<colors.size();i++) { // Write value to the debug log System.debug(colors[i]); }
Beyond the Basics
Apex supports two other collection types: Set and Map. You can learn more about these in the Collections section of the Apex Developer Guide.
Apex Classes
Save an Apex Class
Save the EmailManager class in your organization:
- Open the Developer Console under Your Name or the quick access menu
(
).
- In the Developer Console, click , and enter EmailManager for the class name, and then click OK.
- Replace the default class body with the EmailManager class example.
The EmailManager class has a public method (sendMail()) that sends email and uses built-in Messaging methods of the Apex class library. Also, this class has a private helper method (inspectResults()), which can’t be called externally because it is private but is used only within the class. This helper method inspects the results of the email send call and is called by sendMail().
public class EmailManager { // Public method public void sendMail(String address, String subject, String body) { // Create an email message object Messaging.SingleEmailMessage mail = new Messaging.SingleEmailMessage(); String[] toAddresses = new String[] {address}; mail.setToAddresses(toAddresses); mail.setSubject(subject); mail.setPlainTextBody(body); // Pass this email message to the built-in sendEmail method // of the Messaging class Messaging.SendEmailResult[] results = Messaging.sendEmail( new Messaging.SingleEmailMessage[] { mail }); // Call a helper method to inspect the returned results inspectResults(results); } // Helper method private static Boolean inspectResults(Messaging.SendEmailResult[] results) { Boolean sendResult = true; // sendEmail returns an array of result objects. // Iterate through the list to inspect results. // In this class, the methods send only one email, // so we should have only one result. for (Messaging.SendEmailResult res : results) { if (res.isSuccess()) { System.debug('Email sent successfully'); } else { sendResult = false; System.debug('The following errors occurred: ' + res.getErrors()); } } return sendResult; } }
- Click Ctrl+S to save your class.
Beyond the Basics
The class you just saved makes use of object-oriented programming (OOP). The class encapsulates the methods that are related to managing email. To be a perfect example of OOP, the class would also contain member variables (attributes) and accessor methods to access those attributes, but for simplicity our class doesn’t have these.
Salesforce compiles your class when you save it.
Call a Method to Send an Email
Let’s invoke the public method. We’ll use anonymous Apex execution to do so. Anonymous Apex allows you to run lines of code on the fly and is a handy way to invoke Apex, especially to test out functionality. Debug log results are generated, as with any other Apex execution.
- In the Developer Console, click .
- In the window that opens, enter the following. Replace 'Your email
address' with your email
address.
EmailManager em = new EmailManager(); em.sendMail('Your email address', 'Trailhead Tutorial', '123 body');
- Click Execute.
Now that this method has executed, you should have received an email in your inbox. Check your email!
Inspect Debug Logs
Debug logs are useful for debugging your code. When Apex methods execute, the calls are logged in the debug log. Also, you can write your own debug messages to the log, which helps in debugging your code in case there are errors. The inspectResults() helper method, which is called by sendMail(), writes messages to the log by using the System.debug() method to indicate whether the email send operation was successful or had errors. You can look for these messages in the debug log that was generated when you executed the method.
- In the Developer Console, click the Logs tab and double-click the most recent log in the list.
- Select Debug Only to filter the log so that only log lines for
System.debug() statements are shown.
You’ll see the following message in the filtered log view, assuming the email was sent without errors.
DEBUG|Email sent successfully
Call a Static Method
Because the sendMail() method in our class doesn’t access class member variables, it doesn’t need to be an instance method. Let’s change it to a static method by adding the static keyword to its declaration. Static methods are easier to call than instance methods because they don’t need to be called on an instance of the class but are called directly on the class name.
- In the Developer Console, find the open tab for the EmailManager class and modify the first line of the sendMail() method definition to the following (the only
change is the added static
keyword.)
public static void sendMail(String address, String subject, String body) {
- Save the class by pressing Ctrl+S.
- Modify the statements in your Execute Anonymous window to call the static method on the
class
name.
EmailManager.sendMail('Your email address', 'Trailhead Tutorial', '123 body');
- Click Execute.
Now that this method has executed, you can check your email, and optionally, the debug log as in the previous steps.