Apex Trigger问题:无法根据Case关闭数量更新Account Rating
问题排查与修复方案
核心问题分析
代码执行但未更新Account Rating,核心是以下逻辑漏洞导致:
Insert/Undelete/Delete场景完全未触发处理
处理类中所有收集AccountId的逻辑都被if(oldMap != null)包裹,而Insert、Undelete、Delete场景下传入的oldMap为null,导致这三个场景下根本不会将AccountId加入待处理集合,后续查询和更新自然不执行。Update场景逻辑不符合需求且存在冗余
- 需求仅要求Case状态变为关闭时处理,但当前代码在Account变更时也会触发更新,属于超出需求的冗余逻辑;
- Update场景中第三个
else if(cc.IsClosed == true)分支永远不会触发,因为前面已经判断了oldCases.IsClosed != cc.IsClosed(仅状态变化时进入),逻辑冲突。
变量命名混淆
caseIDs集合实际存储的是AccountId,命名错误易引发逻辑误解,建议改为accountIds。
修正后的处理类代码
public with sharing class AccountRatingUpdateViaCaseStatusClass { public static void checkCaseStatus(List<Case> caseList, Map<Id, Case> oldMap){ System.debug('rsn Trigger is executing : ' + Trigger.isExecuting); Set<Id> accountIds = new Set<Id>(); if(!caseList.isEmpty()){ for(Case cc : caseList){ // 处理Update场景:仅当Case从未关闭变为关闭时 if(oldMap != null){ Case oldCase = oldMap.get(cc.Id); if(!oldCase.IsClosed && cc.IsClosed){ System.debug('rsn 2: Case status changed to closed - Case: ' + cc.Id); accountIds.add(cc.AccountId); } // 若需要处理Account变更逻辑(原需求未提及,可选保留) /* else if(cc.AccountId != oldCase.AccountId){ System.debug('rsn 1: Account changed for Case - Old Account: ' + oldCase.AccountId + ', New Account: ' + cc.AccountId); accountIds.add(oldCase.AccountId); accountIds.add(cc.AccountId); } */ } // 处理Insert/Undelete场景:Case本身为关闭状态 else if(cc.IsClosed){ System.debug('rsn 3: Case is closed on insert/undelete - Case: ' + cc.Id); accountIds.add(cc.AccountId); } // 处理Delete场景:删除的是已关闭Case,需更新原Account的Rating else if(Trigger.isDelete && cc.IsClosed){ System.debug('rsn 4: Closed Case deleted - Case: ' + cc.Id); accountIds.add(cc.AccountId); } } } // 移除空AccountId,避免无效查询 accountIds.remove(null); if(accountIds.isEmpty()){ System.debug('rsn No accounts to process'); return; } System.debug('rsn Accounts to process: ' + accountIds); List<AggregateResult> closedCaseCounts = [ SELECT AccountId, COUNT(Id) numClosedCases FROM Case WHERE AccountId IN :accountIds AND IsClosed = true GROUP BY AccountId ]; System.debug('rsn Closed case counts: ' + closedCaseCounts); List<Account> accountsToUpdate = new List<Account>(); // 遍历聚合结果更新Rating for(AggregateResult ar : closedCaseCounts){ Id accountId = (Id)ar.get('AccountId'); Integer numClosedCases = (Integer)ar.get('numClosedCases'); String newRating; if(numClosedCases >= 2){ newRating = 'Hot'; } else if(numClosedCases == 1){ newRating = 'Cold'; } else { // 关闭Case数量为0时,可根据需求设置默认值,原需求未提及则留空 newRating = ''; } accountsToUpdate.add(new Account(Id = accountId, Rating = newRating)); } // 处理无关闭Case的Account(比如删除最后一个关闭Case的场景) Set<Id> processedAccountIds = new Set<Id>(); for(AggregateResult ar : closedCaseCounts){ processedAccountIds.add((Id)ar.get('AccountId')); } for(Id accId : accountIds){ if(!processedAccountIds.contains(accId)){ accountsToUpdate.add(new Account(Id = accId, Rating = '')); } } System.debug('rsn Accounts to update: ' + accountsToUpdate); if(!accountsToUpdate.isEmpty()){ update accountsToUpdate; System.debug('rsn Accounts updated successfully'); } } }
修正后的触发器代码
trigger AccountRatingUpdateViaCaseStatusTrigger on Case (after insert, after update, after delete, after undelete) { if(Trigger.isAfter){ if(Trigger.isUpdate){ AccountRatingUpdateViaCaseStatusClass.checkCaseStatus(Trigger.new, Trigger.oldMap); } else if(Trigger.isDelete){ AccountRatingUpdateViaCaseStatusClass.checkCaseStatus(Trigger.old, null); } else if(Trigger.isInsert || Trigger.isUndelete){ AccountRatingUpdateViaCaseStatusClass.checkCaseStatus(Trigger.new, null); } } }
关键修复点说明
- 拆分逻辑分支:将
oldMap为null和不为null的场景分开处理,确保Insert/Undelete/Delete场景能正常收集AccountId; - 严格匹配需求:仅在Case从未关闭变为关闭、插入/恢复已关闭Case、删除已关闭Case时触发更新;
- 处理边界情况:新增关闭Case数量为0的场景处理(可根据需求调整);
- 优化查询与更新:移除无效AccountId,避免空值查询,确保所有待处理Account都被覆盖;
- 修正变量命名:将
caseIDs改为accountIds,提升代码可读性。
内容的提问来源于stack exchange,提问作者rahul soni
相关产品推荐
相关产品推荐

