Map – retainAll: Another way to avoid Null Pointer Exception while dealing with Map

Map<Id, Contact> mapAccIdToCont = getAccountToContactMap();//Predefined Map
List<Id> lstAccId = getAccountIds();//Predefined Account Id List

//1. Assume mapAccIdToCont has 50 Account Ids
//2. Assume lstAccId has 100 Account Ids
//3. Assume mapAccIdToCont.keySet() and lstAccId has common Account Ids. But not all of the Ids in mapAccIdToCont.keySet() are available in lstAccId

//Iterating over the list of AccountIds and accessing values from the Map may lead to Null Pointer Exception, if the null check is not done properly using the keywords like "containsKey". Using "retainAll", we can avoid such circumstances.

Set<Id> setAccId = new Set<Id>(lstAccountId).retainAll(mapAccIdToCont.keySet());//Forming a set of Account Ids from lstAccountId. These account ids are also available in the Map

Extract fields of a specific Data Type from a sObject

Schema.DescribeSObjectResult objectDescribe = Case.SObjectType.getDescribe();
Map<String, Schema.SObjectField> fieldMap = objectDescribe.fields.getMap();

for( String fieldName : fieldMap.keySet() ) {
    Schema.SObjectField field = fieldMap.get(fieldName);
    Schema.DescribeFieldResult fieldDescribe = field.getDescribe();
    
    if (String.valueOf(fieldDescribe.getType()) == 'DATETIME') {
        System.debug(fieldName);
    }
}

SOQL FIELDS() Function

FIELDS(ALL) – Select all the fields of an object.
FIELDS(CUSTOM) – Select all the custom fields of an object.
FIELDS(STANDARD) – Select all the standard fields of an object.

In each case, FIELDS() respects field-level security so it only shows the fields that you have permission to access.

FIELDS() is limited to returning 200 records.

FIELDS(ALL) and FIELDS(CUSTOM) are not supported in Apex due to being unbounded, having sets of fields that the API can’t determine in advance.

https://developer.salesforce.com/docs/atlas.en-us.soql_sosl.meta/soql_sosl/sforce_api_calls_soql_select_fields.htm?_ga=2.106773379.1216528802.1671603324-1158522964.1660054937

Safe Navigation Operator

The safe navigation operator (?.) can be used to replace explicit, sequential checks for null references. This new operator short-circuits expressions that attempt to operate on a null value and returns null instead of throwing a NullPointerException.

If the left-hand side of the chain expression evaluates to null, the right-hand side is not evaluated. Use the safe navigation operator (?.) in method, variable, and property chaining. The part of the expression that is not evaluated can include variable references, method references, or array expressions.

Following example first evaluates a, and returns null if a is null. Otherwise the return value is a.b

a?.b // Evaluates to: a == null ? null : a.b

Enforce Field- and Object-Level Security with Security.StripInaccessible

This allows developers to remove all fields from the records that the running user does not have access to. This makes it easier to allow graceful degradation of application behavior on security violation by omitting fields rather than failing.

Use the stripInaccessible method to strip fields that the current user can’t access from query and subquery results. Use the method to remove inaccessible fields from sObjects before a DML operation to avoid exceptions. Also, use the stripInaccessible method to sanitize sObjects that have been deserialized from an untrusted source.

The stripInaccessible method checks the source records for fields that don’t meet the field- and object-level security check for the current user and creates a return list of sObjects. The return list is identical to the source records, except that fields inaccessible to the current user are removed.

Following example removes fields from the query result that the current user does not have update access to.

SObjectAccessDecision securityDecision = Security.stripInaccessible(
	AccessType.UPDATABLE,
	[SELECT Name, BudgetedCost, ActualCost FROM Campaign]
);

Following example performs a query and then removes inaccessible fields from the query result.

List<Contact> records = [
	SELECT 
		Id, Name, Phone, HomePhone 
	FROM 
		Contact
];
SObjectAccessDecision securityDecision = Security.stripInaccessible(
	AccessType.READABLE, 
	records
);

For more information, check https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_classes_with_security_stripInaccessible.htm

Enable Field- and Object-Level Permissions Checking Using WITH SECURITY_ENFORCED in SOQL Queries

List<Contact> contactsWithSecrets = [
	SELECT 
		Name, Social_Security_Number__c
	FROM 
		Contact 
	WITH SECURITY_ENFORCED
];

If fields or objects referenced in the SELECT clause using WITH SECURITY_ENFORCED are inaccessible to the user, the query throws an exception indicating insufficient permissions and no data is returned.

There is a new restriction while querying Polymorphic lookup fields using WITH SECURITY_ENFORCED. Polymorphic lookup fields are relationship fields that can point to more than one entity.

1. Traversing a polymorphic field’s relationship is not supported in queries using WITH SECURITY_ENFORCED.
2. Using TYPEOF expressions with an ELSE clause is not supported in queries using WITH SECURITY_ENFORCED.
3. The Owner, CreatedBy, and LastModifiedBy polymorphic lookup fields are exempt from this restriction, and do allow polymorphic relationship traversal.

It is recommended, using WITH SECURITY_ENFORCED in Apex classes or triggers with an API version 45.0 or later.