New answers tagged

3

This has a ton of problems with it. You check for nulls for things that will never be null, you skip iterating over empty lists (which is harmless), you call a massive loop for every record when a map would have sufficed, etc. It's no wonder that this could have problems running in bulk. I'm not sure how much work needs to be done to optimize, as you've not ...


0

The documentation for apex properties does not mention using automatic property syntax for static variables. This means you will want to have a private static variable to contain the value of boolvar. global without sharing class ClassA { private static boolean boolvarValue; global static boolean boolvar{ get {return boolvarValue;} set { boolvarValue =...


1

The Map surveyIdToSum is a Map from Site_Survey_Response__c Ids to Site_Survey_Response__c. However survey.Id is the Id of a Site_Survey__c. This is a different object, so it's Id won't be used as a key for surveyIdToSum. Hence aggSum is null, so calling aggSum.get(...) is giving you a NullPointer.


1

If zero rows would be returned, there's no entry in the map for the record, so you need to check for that first: private static void updateRiskScoreTotalOnSiteSurvey(List<Site_Survey__c> newSurveys) { Map<Id, AggregateResult> surveyIdToSum = new Map<Id, AggregateResult>([ SELECT Site_Survey__c Id, SUM(Score__c) riskScoreTotal ...


1

Okay I figured it out, I was using a SingleEmailMessage object, and according to this documentation I have to add an attachment using the following code: email.setFileAttachments(new Messaging.EmailFileAttachment[] {efa}); instead of doing Mail. attachment This worked!


0

Your requirement isn't entirely clear, however I'm guessing what you actually want to do is along the following lines: public class custom_UpdateFinservInternalRef { @InvocableMethod(Label='Copy value to Internal referrer field2' Description='Gets value from custom Internal Referrer field and writes to FSC Internal Referrer field') public static void ...


3

Salesforce was founded in 1999, and by 2000 was branded as the "No Software" CRM solution. For the first eight years or so, there was no code-based alternatives, and it worked well enough for many small-to-medium-sized orgs. Apex was largely made as a stopgap for those large orgs with highly specialized processes, which took many years and ...


0

sfdcfox's answer about needing it to be a rich-text field is correct. If you do change the field type though, your trigger would still not work for two reasons: The value you're setting for the href attribute is not contained in double quotes You're not checking to see if Location is already a link (any subsequent edit would make your Location be <a href=...


1

You can only create hyperlinks in fields that support it (they must be Rich Text Fields). As such, you're only going to get HTML in your Location field, as it is a normal Text field.


1

You never reset the field before adding the new values, so it accumulates every time you run the trigger. Also, this code is not properly bulkified. Here's a fixed version: trigger pullCommentsApproval on Return_Shipment__c (before update) { Map<Id, Return_Shipment__c> oppMap = new Map<Id, Return_Shipment__c>([ Select (Select ...


1

Triggers run when the given event occurs. You defined your trigger to run every time an update occurs. Your trigger always overwrites the values regardless as to whether they have values or not. If you want fixed values only on create then use before insert, not before update. However, this is a broken approach since it will always discard entered values on ...


3

This happens if you have a class named Opportunity. In such case, Opportunity opp is a reference to the custom class Opportunity, while Trigger.New holds references to Schema.Opportunity. Writing for (Schema.Opportunity opp : Trigger.new) { will fix the error. Docs: you must fully qualify your uses of Schema namespace elements when they have naming ...


4

When used in bulk, yes, it could hit the SOQL governor limit. You should use the normal Aggregate-Query-Update pattern. Set<Id> contactIds = new Set<Id>(); // Put contactIds in to Set for(Case record: Trigger.new) { contactIds.add(record.ContactId); } // Use AggregateQuery to find cases with 2+ for same Contact contactIds.retainAll( new Map&...


0

I'm not sure if this top voted answer workaround is valid anymore. It didn't work for my below Exec. anonymous code. Feel free to copy-paste and try. Map<Id, ContentVersion> mapCV = new Map<Id, ContentVersion>(); Set<Id> setId = mapCV.keyset(); List<ContentDocumentLink> listCDL = [SELECT LinkedEntityId, ContentDocumentId, Visibility ...


1

This code is not an Apex trigger, and in fact doesn't do anything. Loan_Application__c lapp = new Loan_Application__c(); getcusid=lapp.Saltedge_Customer_Id__c; Creating a new Loan_Application__c instance does not have any relationship to user interaction. No data will be populated there. I would recommend completing the following Trailhead ...


7

"It's not working" doesn't tell us much about what the issue is (we don't know how it's supposed to work unless you tell us or if it's simple enough). A reasonable guess here would be something along the lines of "my code is running before update, but not after update". In addition, your description of "recursive" may not be ...


0

For future wanderers - you can run addError() on a particular field of a record and messages from different fields don't override each other.


1

The solution here is to look at the Individual Record Type Mapper. Be sure that it's listed as follows: Label:Person Account Individual Record Type Mapper Name: PersonAccount Account Record Type: PersonAccount Note the SPACE in Label and lack of space in the other two.


1

Uploaded files go into the ContentVersion object. (isn't that obvious! just kidding). They are connected to an object via the ContentVersionLink object. The ContentVersion has an attribute called Title, and that should be where you can update the filename. https://developer.salesforce.com/docs/atlas.en-us.230.0.object_reference.meta/object_reference/...


3

As far as I'm aware, the only statuses that should cause AsyncException to be thrown are as follows: COMPLETE ERROR DELETED You can't abort something that is already finished, has errored (which also implies finished), or deleted. I know for certain that I've aborted WAITING, ACQUIRED, and EXECUTING jobs. I can't really verify PAUSED, BLOCKED, or ...


1

Figured it out. Some observations for others in the future: Any image/file upload is done via the Automated Process User End Chat does not set the MessagingSession Status to Ended, the MessagingSession trigger does not fire here Closing the MessagingSession tab does change the status Ended, and the MessagingSession trigger fires For point 3, the trigger ...


2

This is one of those rare cases where I'd probably say: just try-catch and ignore any exceptions. If it fails to abort, it should be harmless, so I see no reason to worry about error handling here. private void reschedule(CronTrigger me, ISchedulable item, MySchedulableContext context) { try { System.abortJob(me.Id); } catch(Exception e) { ...


0

Yes. Salesforce implements transaction-level database isolation. This means that two records inserted in two different transactions wouldn't be able to "see" each other until the transaction completes, but within one transaction (including all cascading triggers, etc), you can query those results in an after DML trigger or later. If this were not ...


0

Does a trigger execution happen on a separate thread? No. All synchronous Apex is executed in a single thread for each transaction. Note that threads are rarely a useful framework for describing Salesforce execution contexts because you have no control over threading; rather it's usually more helpful to think in terms of transactions and synchronous versus ...


0

Be aware that there are limits on future methods that you must consider when setting up such processing. Note that there are limits on the number of future methods that can be invoked, as per the documentation: Maximum number of methods with the future annotation allowed per Apex invocation: 50 (synchronous), 0 in batch and future contexts; 1 in queueable ...


0

You can't get a return value, because future methods are called asynchronously. You would want to pass in the original case Id so you can update the record. @future public static void createExternalCase(Id caseId) { Case record = [SELECT ... FROM Case WHERE Id = :caseId]; String externalId = Utils.createExternalCase(); record.external_resource_id__c = ...


1

To add an error to record in a trigger, you must use the records in Trigger.new/Trigger.newMap/Trigger.old/Trigger.oldMap. You're looping over the wrong variable to use for the error. public with sharing class DuplicateAccount { public static void DuplicateAccountHandler(List<Account> listAccount){ Set<String> accountName = new Set<...


1

you must be marking the opp field Final_Approved__c as true on last approval by approval field update. In this case your approval field update is hapenning before approval data is commited to the data base i.e before save point. to fix this, in case when your field Final_Approved__c is true you can run the future method from the trigger which will run after ...


1

Your current Apex Trigger on Return_Shipment__c will only perform before update trigger when it detects that your "Final_Approved__c" field = TRUE. Since you are SOQL-ing out the Return_Shipment__c Approval, just run an IF check for ProcessSteps.Comment != Null. In that IF loop, copy the ProcessSteps.Comment to Return_Shipment__c.Approver_Comments(...


1

The syntax for a for loop over an iterable (like sets and lists) is for(<Type> <loop variable name> :<iterable>) for(Quote_Request__c c; trigger.new;) is not proper syntax (those semicolons are incorrect). What you're looking to write here is instead for(Quote_Request__c c :trigger.new) though I would recommend coming up with a more ...


1

If you simply search Apex Triggers, you will find this documentation useful Triggers: There are two types of triggers: Before triggers are used to update or validate record values before they’re saved to the database. After triggers are used to access field values that are set by the system (such as a record's Id or LastModifiedDate field), and to affect ...


1

Usually, you change records itself in before context and update related records and some other non-related staff in after context. Therefore, for your scenario, I would recommend using after update. Strictly speaking, there is no difference for your case, but it's just a good conversion to follow


0

you should not put the values into map directly first check if map has key or not (if true) then add the values to that key You should add ParentIdSet.add(e.Employer__c.Id);** in palce of ParentIdSet.add(e.Employer__c); for(Employer__c eobj : elist){ if( parentMapObj.Containskey(eobj.Id)) { parentMapobj.get(eobj.Id).add(eobj); }...


0

This is a simple case of allowing for not having a parent ID in the map. In the first iteration you only get employers (parents) for employees with a phone number change, but in the last loop you assume you can find the employer (parent) for all employees. Update the latter loop like: for(Employee__c emobj : trigger.new){ Employer__c employer = ...


0

In this situation, where you're targeting subscribers who all exist in the All Subscribers list (or else you wouldn't have click info for them), you don't actually need an email address in your data extension. The documentation will say it's needed but I've tested sending to a data extension with no email field (just the subscriber key text field) and it ...


1

As mentioned in post you can try the below snippet FeedItem post = new FeedItem(); post.ParentId = acc.Id ; post.createdById = '0057F0000088Oh8'; //Replace this id with Used id of INTERFACE post.Body = 'Msg body'; insert post;


0

As shown here, the trigger shouldn't work for any of the scenarios (except Scenario 2, which if I understand correctly is the OOTB behavior) due to what I think is just a typo: if (tsk.OwnerId == Trigger.Oldmap.get(tsk.WhatId).OwnerId) { tsk.OwnerId = Trigger.Oldmap.get(tsk.WhatId).OwnerId; The if condition should be !=.


2

Assuming your platform event is selected as publish after commit , then the original transaction for lead has already been committed into the database, and thus any exception into platform event trigger won't rollback anything that caused it to fire in the first place.


1

Trigger.old is Map of Case Id and Case instance. To retrieve the field values, you will need to specify the ID as index and then the field name to get the corresponding values. Trigger.oldMap.get(Case_ID).FieldName Trigger.oldMap - A map of IDs to the old versions of the sObject records. Trigger.newMap - A map of IDs to the new versions of the sObject ...


4

Those maps are keyed by record Ids. So when looking for differences between the values of of the fields in the old and new records use this pattern: // n = new version of record // o = old version of record for (Case n : Trigger.new) { Case o = Trigger.oldMap.get(n.Id); if (n.Case_Closed_by_User__c != o.Case_Closed_by_User__c) { ... } ...


0

I think you are just missing the field that it is telling you about: Quote__c. This is likely an Id field and is probably the Master-Detail field from Quote to QuoteHistoryTracking. Add it like this: hisTrackList.add( new Quote_History_Tracking__c( Quote__c = newCM.Id, QuoteID__c = newCM.Id, Field_Name__c = 'Description' //...etc ) );


0

Enriching the list with additional Objects: AcceptedEventRelation AccountCleanInfo AccountContactRelation AccountContactRole AccountFeed AccountHistory AccountOwnerSharingRule AccountPartner AccountShare AccountTag AccountTeamMember AccountTerritoryAssignmentRule AccountTerritoryAssignmentRuleItem AccountTerritorySharingRule ActionLinkGroupTemplate ...


2

You are likely running into this - Apex Platform Event Triggers executes as 'Automated Process' user. The key parts from that help article are: When an Apex-trigger is configured as the subscriber of a platform event, the trigger executes as 'Automated Process' instead of the causing user (the user who created the platform event). and In some cases SOQL ...


-1

For some reason this didn't work for me. This worked in its place public static Boolean isSandbox() { Boolean org = ([SELECT IsSandbox FROM Organization LIMIT 1].IsSandbox); if(org){ return true; } else{ return false; } } To use the code in another class or trigger: trigger fancyname on sObjname ...


0

Given our back-and-forth in the comments, it sounds like all of this can happen in an opportunity process builder, without any cross-object updates. Create an opportunity record update process In the first diamond, place the following formula: NOT(ISBLANK(recurring_donation__c)) && CloseDate < TODAY() In the list of actions, add an action to ...


1

Since you are already using in your SOQL statement a GROUP BY and ORDER BY clause, an alternative approach is to add LIMIT and OFFSET: Integer batchSize = 2000; Integer nrOfRecordsProcessed = 0; Integer rowsReturned = batchSize; while (rowsReturned == batchSize) { rowsReturned = 0; for(AggregateResult ar : [select ABC__c, Name, max(Revision__c) maxRev ...


0

You can block the submitter from approving the request by following these steps: Create two text fields on the object to be approved, to capture submitter_id and approver_id. Create field updates from approval processes to update those field values during submission and approval steps (based on current user id). create a validation rule which will block ...


0

You use a field mapping technique, then you can use Dynamic Apex methods to get the values dynamically. Here's a simplified version: public with sharing class BankerCheck { static Map<String, String> fieldMap = new Map<String, String> { 'BankerHome__c' => 'Home', 'BankerWork__c' => 'Work', 'BankerCell__c' => '...


2

You've got a trigger handler so you're abstracting away part of the logic which is a great practice. Due to that abstraction, TriggerService.beforeDelete doesn't care what context it's running in, it just knows to accept a List<Call__c> and a Map<Id, Call__c>. You can pass in any parameters you want that meet that requirement - they don't have to ...


1

If Line 51 is indeed Integer noOfDays = oldOppr.daysBetween(newOppr); the problem should be pretty clear from the debug logs you already have in place: system.debug('oldOppr===='+oldOppr); system.debug('newOppr===='+newOppr); That should immediately show you where you have a null value that you need to write appropriate business logic to deal with. You ...


Top 50 recent answers are included