&& Schema.SObjectType.Account.fields.OwnerId.isAccessible() && Schema.SObjectType.Account.fields.Support__c.isAccessible() && Schema.SObjectType.Account.fields.OwnerId.getReferenceTo()[0].getDescribe().isAccessible() ) { return [SELECT Name, Owner.Name FROM Account WHERE Support__c = 'Premier']; } else { throw new AuraHandledException('Access Denied'); } Now AppExchange security review endorsed! GA! Available Now Simplifies to 14 chars, 96% security less code return [SELECT Name, Owner.Name FROM Account WHERE Support__c = 'Premier' WITH USER_MODE];
User does NOT need the PermissionSet pre-applied • Apply bounded, admin-visible escalations instead of using full system mode • Also available for Security.stripInaccessible • Dev Preview for scratch orgs. ◦ Use scratch feature: "ApexUserModeWithPermset” Method names and API contract are in a dev preview state and likely to change based on feedback When User-mode isn't enough System Mode Full flexibility of the highest privileged user User Mode Full user security model enforcement User Mode + Perm Set Selective Privilege Escalation Winter `24 Dev Preview AccessLevel appEscalated = AccessLevel.USER_MODE.withPermissionSetId('0PSxx00000006xQ'); Database.insert(new Account(Name = 'GenWatt Throwback'), appEscalated); We need your feedback! http://sfdc.co/user-mode-group
integer position; public QueryChunkingQueuable() { locator = Database.getCursor('SELECT Id FROM Contact WHERE LastActivityDate = LAST_N_DAYS:400'); position = 0; } public void execute(QueueableContext ctx) { List<Contact> scope = locator.fetch(position, 200); position += scope.size(); // do something, like archive or delete them if(position < locator.getNumRecords() ) { // process the next chunk System.enqueueJob(this); } } } Query Cursors Method names and API contract are in a draft state and likely to change fully Serializable as Apex job state new method to grab a chunk of records by position Coming Soon Future created from SOQL query total record count
with nulls • Everything in Apex can be null • "If null, use a default value" • Will complement the existing Safe Navigation Operator (?.) • Fun Fact: 13% of unhandled Apex exceptions are NullPointerExceptions String suppliedTitle = null; String pageTitle = suppliedTitle ?? 'Default Title'; Returns the right operand if the left operand is null Left operand Right Operand Spring `24 GA
when working with nulls' String city = [Select BillingCity From Account Where Id = '001xx000000001oAAA']?.BillingCity; String json = '{"Matches": + city?.countMatches('San Francisco') + '}'; Spring `24 GA String city = [Select BillingCity From Account Where Id = '001xx000000001oAAA']?.BillingCity; String json = '{"Matches": + (city?.countMatches('San Francisco') ?? 0) + '}'; // {"Matches": 0} // {"Matches": null}
// Set request payload to translate... HttpResponse response = new Http().send(request); Blob translationZip = response.getBodyAsBlob(); ZipReader reader = new ZipReader(translationZip); ZipEntry frTranslation = reader.getEntry('translations/fr.json'); Blob frTranslationData = reader.extractEntry(frTranslation); string jsonData = EncodingUtil.base64Decode(frTranslationData); Map<String,Object> rawObj = (Map<String,Object>) JSON.deserializeUntyped(jsonData); // Plus a ZipWriter Spring `24 Dev Preview Method names and API contract are in a draft state and subject to change Lightweight native zip reading
that admins know and love • Evaluate dynamic formulas at runtime • Pass in Apex Objects or SObjects to evaluate the formula against • Avoid building rules engines with unique syntax - stick with something users know • Stop abusing formula fields to get a formula value in Apex • Use cases: ◦ Conditional execution of triggers (think: trigger framework features) ◦ Per-product pricing validation rules ◦ We want to hear about yours! Coming Soon Spring `24 Dev Preview We need your feedback! http://sfdc.co/ApexFormula
Boolean result2 = ff.evaluate(new Account(Site='Test')); Assert.isFalse(result2); class BatchProcessingCriteria { DateTime createdDate { get; set; } Integer slaMonths { get { return 2; }} public BatchProcessingCriteria(DateTime cd) createdDate = cd;} } System.Formula<BatchProcessingCriteria, DateTime> slaFormula = System.compileFormula<BatchProcessingCriteria, DateTime>('AddMonths(createdDate, slaMonths)'); DateTime slaDateTime = slaFormula.evaluate(new BatchProcessingCriteria(DateTime.now())); Spring `24 Dev Preview Method names and API contract are in a draft state and subject to change
DataWeave in Apex • [Dev Preview] User-Mode DB Ops with Permission Sets • [GA] Queueable Deduplication and Depth • [GA] List Comparator and Collator • Einstein for Developers • [Dev Preview] Zip Support in Apex • Null Coalescing Operator • UUID Support • Post Savepoint Rollback Callouts • User-Mode DB Ops with Permission Sets • Better Testing for PostInstall • Further Queueable Enhancements • Formula Eval in Apex • Generics