+ Start a Discussion
miguelguerreiro@live.commiguelguerreiro@live.com 

Trigger on Case Comment

Hello,

 

I'm trying to create a trigger on Case Comments so that my Customer Portal users are not able to add comments to closed cases.

 

 

trigger CloseComment on CaseComment (before insert) {

for (CaseComment t: Trigger.new)
{
	Case c = new Case(Id = t.ParentId);
	c = [SELECT Status FROM Case WHERE Id = :c.Id];

	if(c.Status == 'Closed' && System.Userinfo.getUserType()!= 'Standard')
		{
		t.addError('You cannot add comments to closed cases.');
		}
	}

 

but it fails with bulk import. any ideas?

 

Best Answer chosen by Admin (Salesforce Developers) 
b-Forceb-Force

your code was not written by considering BULK load,

 

Try below code

trigger CloseComment on CaseComment (before insert) 
{
Set<Id> parentCase=new Set<Id>();
Map<Id,Case> mapCase=new Map<Id,Case>();
for (CaseComment t: Trigger.new)
{
parentCase.add(t.ParentId);
}
List<Case> lstCase=[Select Id,Status from case where Id in :parentCase ];
for(case c in :lstCase)
{
mapCase.put(c.Id,c);
}

for (CaseComment t: Trigger.new)
{
if(mapCase.containskey(t.ParentId))
{
if(mapCase.get(t.ParentId).Status=='Closed' && System.Userinfo.getUserType()!= 'Standard')
	{
		t.addError('You cannot add comments to closed cases.');		
	}
}
}
}

 

 

Let me know does It rock for you :)

 

Cheers,

Bala

 

All Answers

mikefmikef

It fails on bulk inserts because you have a query in the for loop of the trigger.

 

Read this post.

 

Reply if you need further help.

b-Forceb-Force

your code was not written by considering BULK load,

 

Try below code

trigger CloseComment on CaseComment (before insert) 
{
Set<Id> parentCase=new Set<Id>();
Map<Id,Case> mapCase=new Map<Id,Case>();
for (CaseComment t: Trigger.new)
{
parentCase.add(t.ParentId);
}
List<Case> lstCase=[Select Id,Status from case where Id in :parentCase ];
for(case c in :lstCase)
{
mapCase.put(c.Id,c);
}

for (CaseComment t: Trigger.new)
{
if(mapCase.containskey(t.ParentId))
{
if(mapCase.get(t.ParentId).Status=='Closed' && System.Userinfo.getUserType()!= 'Standard')
	{
		t.addError('You cannot add comments to closed cases.');		
	}
}
}
}

 

 

Let me know does It rock for you :)

 

Cheers,

Bala

 

This was selected as the best answer
miguelguerreiro@live.commiguelguerreiro@live.com

Thanks Bala, your code working fine fine :)

 

I also had tried the following code but it failed with BULK import:

 

 

trigger CloseComment on CaseComment (before insert) {
Map<Id,CaseComment> cMap = new Map<Id,CaseComment>();
for (CaseComment t: Trigger.new){
	cMap.put(t.ParentId,t);
}
Set<Id> idSet = cMap.keySet();
for(Case c:[select Id,Status,Process__c from Case where Id in :idSet]) {
if(c.Status == 'Closed' && c.Process__c == 'Payroll'){
CaseComment cm = (CaseComment)cMap.get(c.Id);
cm.addError(c.Process__c + 'case closed' + c.Status);
}
}
} 

 Here's the error message:

 

 

"CASE NUMBER","CASE ID","CASE COMMENTS","ERROR"
"00599865","500T0000002GrvS","sdfsdfsd","Too many retries of batch save in the presence of Apex triggers with failures: when triggers are present partial save requires that some subset of rows save without any errors in order to avoid inconsistent side effects from those triggers. Number of retries: 2"
"00599865","500T0000002GrvS","sdfsdfsd","Too many retries of batch save in the presence of Apex triggers with failures: when triggers are present partial save requires that some subset of rows save without any errors in order to avoid inconsistent side effects from those triggers. Number of retries: 2"

 Any idea why it's failing? I believe it follows the same logic as your code. 

 

Thanks! 

 

 

Force.comForce.com

Hello, you are quering a SOQL inside the second for loop. Plz avoid any SOQL query in the loop.

 

Use maps or list for holding all Cases having ids in idSet and then iterate through all cases inside the list.

you can frame your code as:

 

 

List<Case> allCases = [select Id,Status,Process__c from Case where Id in :idSet];

for(integer i=0;i<allCases.size();i++){
    if(allCases[i].Status == 'Closed' && allCases[i].Process__c == 'Payroll'){
        CaseComment cm = (CaseComment)cMap.get(allCases[i].Id);
        cm.addError(allCases[i].Process__c + 'case closed' + allCases[i].Status);
    }
}

 Try this