14

Suppose you have a custom object Custom_obj__c Trigger.New means it is a List<Custom_obj__c> and Trigger.NewMap means it is a map<Id, Custom_obj__c> In before insert context your Trigger.NewMap will always be null because in before context records are not submitted to the database, so the Id is not generated yet. That's why in before insert ...


12

It is quite possible, and in fact recommended (if you need trigger logic on both events). See also: Trigger Frameworks and Apex Trigger Best Practices Triggers (Apex Developer Guide) A common pattern is to have three separate layers of code: the trigger itself, a handler, and a service layer. Here's the trigger framework I prefer. Trigger trigger ...


12

Apex Code is single-threaded. This means that your code runs sequentially, from top to bottom, until the end of the method. If you have validation occurring first, followed by other updates, your code will run to its end. Once it ends, if any records received an error (via addError), and allOrNone is "false", then those records are set aside, any work done ...


10

You can add an error to a specific field using the addError method as follows: SObject someRecord; someRecord.SomeField__c.addError('Custom Message'); //or someRecord.someField__c.addError(someException); Note that you cannot add it to a field dynamically. This error mapping can only be done with a hard-coded field. See also: Provide an additional ...


9

== is for equality checks, = is for assignment. As such: If (soAccount.ISLock__c = True){ will assign the value of true to IsLock__c, and this statement will always be true. For this reason, I always recommend that you avoid comparing to true/false values, because it can prevent typos like this from compiling. If (soAccount.IsLock__c){


8

This is a good time to learn about the Lazy Load pattern. You can write your cache in such a way that you only consume the query if you actually need the data. Now if you make a reference to this Apex Class to perform some logic that has no need for the query, you will not touch your governor limits. public with sharing class MyService { public static ...


8

You have a typo: Trigger.oldMap.get.(cl.id).Initial_Estimate__c should be: Trigger.oldMap.get(cl.id).Initial_Estimate__c You probably also need to apply an explicit cast, like: ((Claim__c) Trigger.oldMap.get(cl.id)).Initial_Estimate__c You'll find this sort of issue easily by using an appropriate IDE. For example, I found it be copy/pasting your code ...


7

I have used the below code to get the IP address of the logged/current user. Hope this helps. Thanks Map<String, String> headersMap = ApexPages.currentPage().getHeaders(); // True-Client-IP has the value when the request is coming via the caching integration. String ipAddress = headersMap.get('True-Client-IP'); if (String.isEmpty(...


7

trigger.new is simply a list of the records being processed by the trigger, so if all you need to do is loop through them then you can use that. trigger.newMap just allows you to target specific records by Id should you not need to process everything, or if you need to map other records back to these.


7

Yes static variables are meant for same purpose . Create a static list in your helper class and use same in your before trigger and after trigger public class cachequery { public static List<Account> lstaccount= [Select Id,Name from Account LIMIT 10]; } The sample trigger to provide an idea trigger T1 on Account (before insert, after insert) { ...


7

If you care about order of execution, triggers are far from obsolete, and this consideration still offers a compelling argument for why you would choose an Apex Trigger over Process Builder. If you need to do data transformations before a Validation Rule, or before you execute cross-object logic, you should certainly still use an Apex Trigger. The thing is, ...


7

The problem is this line here: objOpp = new Opportunity(id = mapOfOpportunity.get(eachKey)[0].Id); You're adding an error to a record that exists only in memory. Errors will only surface when you use addError on a record that is inside of Trigger.new or Trigger.old. You probably want to use the following code instead: objOpp = mapOfOpportunity.get(...


6

I just checked lastmodified by id is null on a before insert event and this makes sense. For example (hastily written trigger based approach, not best practice!): trigger eventTrigger on Event (before insert) { system.debug(logginglevel.WARN, '^^^ event last modified: '+trigger.new[0].LastModifiedById); system.debug(logginglevel.WARN, '^^^ userinfo:...


6

You can't set cross object fields on trigger context records. When you specify Case__r on a record in your trigger.new collection, it is null. Hence trying to set its Status results in an attempt to de-reference a null variable. for (Accounting_Instructions__c record : trigger.new) { // below is the same as record.Case__r.Status = 'Open' Case ...


6

Yes and no No need for seperate block for update and insert they are doing almost (thanks DerekF for pointing out the additional if) the same thing and they can be consolidated pretty efficiently. Also if (doctorIds != null && doctorIds.size() > 0) { list < Bank_Account__c > banklist = [select Id, Name, Doctor__c, Category__c from ...


6

It isn't working because the Asset Id field is null in the before insert context. Records do not have Ids until after insert. Beyond that, you're updating an Account record in your Asset trigger, but you aren't performing a DML update for those Accounts. You can only avoid DML in triggers in before contexts on the same SObject (so in your Asset trigger, ...


6

This is happening because Trigger.new is not available on before delete context. You'll want to use Trigger.old instead. Check this document about Trigger Context Variables.


6

The problem is that you are calling addError on Trigger.OldMap instead of Trigger.NewMap. When declaring the signature for checkForStageDuration you have it (oldMap, newMap) but when you are passing in parameters in your trigger, you are passing in (newMap, oldMap).


6

You're seeing recursion because your recursion guard is in the wrong place. When this gets executed: AankoopDetailTriggerHandler.isBeforeInsert(trigger.new); if(AankoopDetailTriggerHandler.aankRecursion) return; AankoopDetailTriggerHandler.aankRecursion = true; what happens is something like this: Insert goes off before ...


6

You can make use of dynamic SOQL: String type = 'Abc__c'; Map<Id, SObject> m = new Map<Id, SObject>(Database.query('SELECT Id FROM ' + type)); Also see the SObject documentation for methods to access the data. By taking these approaches, the types involved only matter at runtime, not at compile time. But you naturally do lose compile-time type ...


6

It is possible to get the object's type from the ID then use this in the dynamic SOQL. For example: Id id = Id.valueOf(tool.cId__c); String objectAPIName = id.getSobjectType().getDescribe().name; List<SObject> matches = Database.query('SELECT Id FROM ' + objectAPIName + ' WHERE Id = :id'); Bulkification is possible, but worst case you need n ...


5

Your trigger can't work with "before insert", because you can't query for records that haven't been assigned an Id, which won't happen until "after insert". You'll probably want to start of like this: trigger X on Y (after insert, before update) { if(Trigger.isInsert) { update Trigger.new.deepClone(true); return; } // Rest of ...


5

You are trying to add the Id of an Order to OrderIds before you insert the orders. sObjects don't have Ids before you insert them* I'd suggest taking your insert OrderToInsert; DML statement outside of the for loop. Then, after you insert your new orders, loop through your OrderToInsert list, and add the Ids to OrderIds at that point. *Well...they can if ...


5

Judging by the exception, I'd say that the problem is that you are running this code on an older version of the api that doesn't support the Approval.lock() method. In a different post, I found that for some reason the code will compile and gives a runtime error. If for some reason the lock methods weren't intended to work on trigger context variables, the ...


5

Your expression is almost correct. I would use <a.+<\/a>. You don't know if href will be the first property (or if there will be multiple spaces after a), and you don't want to skip links that don't conform to your definition if you can avoid it. Another thing you need to correct is to actually instantiate a Pattern (not a Matcher). Pattern ...


5

You can just query the PricebookEntry records instead: Set<Id> entryIds = new Set<Id>(); for (QuoteLineItem item : trigger.new) entryIds.add(item.PricebookEntryId); Map<Id, PricebookEntry> entries = new Map<Id, PricebookEntry>([ SELECT UnitPrice FROM PricebookEntry WHERE Id IN :entryIds ]); for (QuoteLineItem item : trigger.new) ...


5

they will execute linear in your trigger. So: public void beforeUpdate( sObject oldObj, sObject newObj ){ // will execute first method1( oldObj, newObj ); // will execute second method2( oldObj, newObj ); } If you use a trigger factory to call a trigger handler and execute bulk methods first, you will see the bulk execution pass your ...


5

See Case IsClosed Trigger Bug? This is not a bug. Currently the setting of this value is not done until the save which comes after the before trigger in the event timeline. There are two workarounds available for you I believe: 1) Execute your logic in an after trigger. This occurs after the save and thus the value should be set. 2) Query ...


5

A typical reason for this is that you have Lead Assignment rules. Once those execute, a new owner is assigned and hence the Lead object is updated. You can see this in the debug log if you enable Workflow INFO and Apex Code DEBUG Or, you may have workflow rules or Process Builder rules that do updates on the Lead. The object will have changed and per SFDC ...


5

Trigger.new is generic List while iterating you have to typecast it into List. So your for loop will be, for(Relatie__c rc :(List<Relatie__c >) Trigger.New){ } That being said, I found few issues with your code. If you are using Trigger.new in Handler you don't need to pass it as a parameter You are doing SOQL in for loops. Thus the code is not ...


Only top voted, non community-wiki answers of a minimum length are eligible