Salesforce is the world’s most popular and most successful cloud-based customer relationship management (CRM) platform. You can use it to grow your business by better understanding your customers’ needs.
One of the reasons for this success is considered to be Apex. Apex is an object-oriented programming language created by Salesforce that allows you to extend the platform’s already powerful functionality and create your own custom cloud-based software applications.
Apex is specifically designed for accessing and manipulating data. It works with Salesforce’s declarative features and is effective within a multi-tenant environment. You can access various types of metadata, like custom objects and fields, directly from your Apex code.
Just like any object-oriented language, like Java and C++, a big part of Apex’s functionality depends on classes. In this blog post, you’ll learn what classes are and why they are important to use. You’ll also learn about all the different components that make up a class.
What Is an Apex Class?
An Apex class is a blueprint for creating objects in Salesforce, defining their properties (variables) and behaviors (methods) using the Apex programming language. It enables developers to implement business logic, interact with Salesforce data, and build custom applications.
When you start learning a programming language, particularly an object-oriented language, there are two terms you’ll find together most of the time that can be confusing for new programmers: Classes and objects. You can think of a class as a template containing all the necessary information and instructions that you can build upon and create class instances called objects.
For example, think of a class that describes a motorcycle. A motorcycle has a model, color, horsepower, manufacturer, etc. A motorcycle object is based on this class, and you can use it to create different objects that will specify the characteristics mentioned above.
In the example below, you can see a class with a few characteristics and the instantiation of three different motorcycle objects.
class MotorBike {
String manufacturer;
String color;
Integer horsePower;
}
MotorBike XR750 = new MotorBike("Harley Davidson", "red", 82);
MotorBike CB750 = new MotorBike("Honda", "blue", 68);
MotorBike Monster = new MotorBike("Ducati", "white", 98);
Components of an Apex Class
An Apex class consists of components that define an object’s functionality and characteristics. Let’s break down the structure of a class to understand it better.
Class Definition
public class MotorBike {
When you define a class, you need to specify its level of visibility. To do this, you can use an access modifier. By default, the access modifier is private, which means that the class isn’t available to outside classes. In our example, the public keyword indicates that this class is available to other classes in the same namespace. Most class definitions are public. The last access modifier option is the global keyword. With global, your Apex class will be visible everywhere, even to classes of a different namespace.
The next thing you can specify while defining a class, although optional, is its sharing mode.
The with-sharing and without-sharing options are unique to Salesforce Apex classes. They indicate the sharing type for this particular class and are used as a security measure to specify record accessibility. Without sharing ignores sharing rules and is the default option for an Apex class. The virtual keyword modifier indicates that you can extend this class. Finally, the abstract keyword states that your class has methods that don’t include a body.
The last things you need to include in your class definition are the class keyword and the custom name of your class.
Read more about the Apex class definition on the Salesforce website.
Class Variables
A variable holds a value that your programs can access to perform various types of operations. Each variable has a data type that defines what kind of values it can store. The data type specifies the variable’s size and, therefore, the memory storage it requires. Also, it determines the type of manipulations you can apply.
To use a variable, you must declare it first. Below you can see an example of a variable declaration.
public String manufacturer; private String color; private Integer horsePower = 150;
The first keyword in this example is the access modifier. It’s optional, and the concept is similar to what was mentioned earlier for the class definition. Variables are private by default, visible only to Apex code within a defining class. You must specify a variable as public or global to make it visible and accessible to other classes.
In addition to the options we mentioned for the class definition, there’s an extra modifier option for variables called protected. Only inner classes of the defining apex class and those that extend it can access a protected variable.
After the modifier, the mandatory data type keyword follows. Options include String, Integer, Boolean, sObject, and more. You can find all the Apex variable data types on the Salesforce website.
Then you would have to name your variable.
Best Practices for Declaring Variables in Apex
When declaring variables in Apex, follow these best practices to improve code readability, maintainability, and performance:
- Use Descriptive Variable Names – Choose meaningful names that indicate the variable’s purpose.
- Follow Proper Naming Conventions – Use camelCase for variables (e.g.,customerName) and PascalCase (e.g., UserController) for class names.
- Specify the Appropriate Data Type – Declare variables using the most suitable data type (e.g., String, Integer, Boolean) to optimize memory usage.
- Limit Variable Scope – Use the lowest necessary access modifier (private, protected, public) to prevent unintended modifications.
- Initialize Variables When Possible – Assign default values to avoid null reference errors and enhance code stability.
Class Methods
A method is a block of code created within a class. It contains a set of instructions and allows objects to accomplish a particular action. They’re reusable and run only when you call them. Here’s a method example:
public void Accelerate(Integer speed) {
// Write your method logic here!
}
The first keyword is the access modifier. The same modifiers that apply to variables apply to methods as well. Next, you need to specify the return type or the data type your method will return. It can be a primitive data type like integer or double, but it can also be a collection, an object, or even another class. If there’s no value to return, you should use the void keyword.
Then you need to name your method. A descriptive name is the best practice. Inside the parentheses, specify the data type of your input and then its name. You can separate them using commas if you have more than one input. Finally, place your method logic inside the curly brackets.
Class Constructors
Practically, constructors are methods you can use to construct new objects based on your class and configure them, so they’re ready to use. Like with methods, you’ll have to determine a constructor’s logic and inputs. On the other hand, constructors will always return a new object; therefore, you don’t have to include a return type.
It’s important to remember that you don’t need to include a constructor in your class as they’re optional. Apex, by default, will create a constructor that will create an empty object. If you decide to include a constructor in your class, keep in mind that the name of your constructor should match the name of your class.
public MotorBike(String manufacturer, String color, Integer horsePower) {
this.manufacturer = manufacturer;
this.color = color;
this.horsePower = horsePower;
}
Class Properties
Apex properties are like variables but have more capabilities and an increased level of control. With Apex properties, among other things, you can validate data before it changes or trigger an action if that happens.
When creating an Apex property, you can include a get and a set accessor. The get code will run when a property is read and the set code when it gets a new value. A property could contain both accessors or only one of them. Here’s an Apex property example where the access modifier is public, and the return type is an integer:
public Integer horsePower
{
get
{
return horsePower;
}
set
{
horsePower = value;
}
}
Syntax and Structure of Apex Classes
An Apex class follows a specific structure that consists of different components, such as class definition, variables, methods, and constructors. Below is a basic syntax of an Apex class:
public class Motorcycle {
public String model;
public String color;
public Integer horsepower;
// Constructor
public Motorcycle(String model, String color, Integer horsepower) {
this.model = model;
this.color = color;
this.horsepower = horsepower;
}
// Method to display details
public void displayDetails() {
System.out.println(
"Model: " + model + ", Color: " + color + ", Horsepower: " + horsepower
);
}
}
This structure helps maintain clean and modular code, making it easier to manage and scale applications in Salesforce.
Static Variables and Methods
Static variables and methods belong to a class rather than to instances of the class. They are shared across all objects and do not require instantiation.
Static Variables
A static variable is initialized once and remains consistent across all instances of the class. It can be used for values that should remain the same across different instances.
public class Vehicle {
public static Integer totalVehicles = 0;
public Vehicle() {
totalVehicles++;
}
}
Static Methods
A static method operates at the class level and does not require object creation. They are useful for utility functions.
public class MathOperations {
public static Integer add(Integer a, Integer b) {
return a + b;
}
}
Using static methods and variables helps improve memory efficiency and maintain a single source of truth for class-wide values.
Inheritance and Polymorphism in Apex
Inheritance
It allows one class to derive properties and behavior from another class. The extends keyword is used to inherit from a base class.
public class Vehicle {
public String brand;
public class Car extends Vehicle {
public Integer doors;
}
}
Polymorphism
Polymorphism allows different classes to be treated as instances of the same base class, promoting flexibility and reusability.
public virtual class Animal {
public virtual void makeSound() {
System.debug("Some generic animal sound");
}
}
public class Dog extends Animal {
public override void makeSound() {
System.debug("Bark!");
}
}
Using inheritance and polymorphism in Apex enhances code reusability and scalability in large projects.
Interfaces and Abstract Classes
Interfaces
An interface defines methods that a class must implement, ensuring a consistent structure.
public interface Vehicle {
void startEngine();
}
public class Car implements Vehicle {
public void startEngine() {
System.debug("Car engine started");
}
}
Abstract Classes
Abstract classes provide a base structure but can contain implemented methods as well. They must be extended by other classes.
public abstract class Shape {
public abstract double getArea();
}
public class Circle extends Shape {
public Double radius;
public Circle(double radius) {
this.radius = radius;
}
@Override
public double getArea() {
return Math.PI * radius * radius;
}
}
Interfaces and abstract classes help enforce consistency and define common behaviors across multiple implementations.
Exception Handling in Apex Classes
Exception handling is essential for managing errors and ensuring robust applications. Apex provides try, catch, and finally blocks to handle exceptions:
public class ExceptionExample {
public void divideNumbers(Integer a, Integer b) {
try {
Integer result = a / b;
System.debug("Result: " + result);
} catch (Exception e) {
System.debug("Error: " + e.getMessage());
} finally {
System.debug("Execution completed");
}
}
}
Using proper exception handling techniques prevents unexpected crashes and enhances the reliability of your Salesforce applications.
Final Thoughts
Below, you can see a complete example of an Apex class with most of the components we discussed.
// Class definition
public class MotorBike {
// Class variables
private String manufacturer;
private Integer horsePower;
// Constructor with String input and Integer input
public MotorBike(String manufacturer, Integer horsePower) {
this.manufacturer = manufacturer;
this.horsePower = horsePower;
}
// Method with no input, no returns that prints the class variables
public void printVariables() {
System.debug("Manufacturer is: " + manufacturer);
System.debug("The horsepower is: " + horsePower);
}
// Method that returns an integer
public static Integer increasedHorsePower() {
horsePower = horsePower + 10;
return horsePower;
}
}
Salesforce’s Apex classes are one of the most powerful parts of the platform’s functionality. Classes let you define the properties and actions that your objects can perform.
You can learn more about the Apex class and find code examples in Apex’s developer guide. Also, Salesforce has a free online learning platform where you can learn how to use Batch Apex in detail.
Are you using Salesforce? Testim for Salesforce is a powerful AI-powered testing tool that will help you automate and simplify your Salesforce application testing efforts.
Learn more about how Salesforce tests and see how Testim can help.