0

I am using trigger to update the custom field(AccountTerritory__c) in Account based on Territory values assigned in Account. I need to schedule this trigger to run on specified time. Could anyone please provide the solution?

trigger accountTerritoryAssignment on Account (After Insert, After Update) { //List

 list<Account> finalList = new list<Account>();


 //Variable
 boolean flag = false;

 if(trigger.isInsert)
 {
     flag = true;
 }

 if(trigger.isUpdate)
 {
     for(Account a:trigger.new)
     {
         if((trigger.oldMap.get(a.id).BillingCountryCode != trigger.newMap.get(a.id).BillingCountryCode) || (trigger.oldMap.get(a.id).BillingStateCode != trigger.newMap.get(a.id).BillingStateCode))
         {   

           flag = true;              

         }
     }
 }

 if(flag)
     {
        if(checkRecursiveAcc.runOnce())
        {
                for(Account a:trigger.new)
                {

                //AccountShare List
                list<AccountShare> accshareList = new list<AccountShare>();
                set<id> accshareSet = new set<id>();

                accshareList = [Select Id, UserOrGroupId from AccountShare where (RowCause='TerritoryManual' or RowCause='Territory') and AccountId=: a.id];
                system.debug('***accshareList***'+accshareList);            
                //AccountShare Set
                for(integer i=0;i<accshareList.size();i++)
                {
                    accshareSet.add(accshareList[i].UserOrGroupId);
                } 
                // Group List
                list<Group> groupList = new list<Group>();   
                set<id> groupSet= new set<id>();                       
                groupList = [Select Id, RelatedId from Group where Id IN : accshareSet];
                system.debug('***groupList***'+groupList); 
                //Group set
                for(integer i=0;i<groupList.size();i++)
                {
                    groupSet.add(groupList[i].RelatedId);
                }

                //TerritoryName List
                list<Territory> territoryList = new list<Territory>(); 
                territoryList  = [Select id, name from Territory where Id IN : groupSet];
                system.debug('***territoryList***'+territoryList);            

                  Account acc = new Account();
                  acc.id = a.id; 
                  acc.AccountTerritory__c = null;
                  for(integer j=0;j<territoryList.size();j++)
                  {
                    if(j==0)
                        {

                            acc.AccountTerritory__c = territoryList[j].name;
                            system.debug('***acc.AccountTerritory__c when j=0***'+acc.AccountTerritory__c);
                        }
                        else
                        {
                            acc.AccountTerritory__c = acc.AccountTerritory__c+','+territoryList[j].name;
                            system.debug('***acc.AccountTerritory__c when j>0***'+acc.AccountTerritory__c);
                        }
                    }     

                finalList.add(acc);      
                system.debug('***acc***'+acc); 
                groupSet.clear();
                accshareSet.clear();

           }       
               update finalList; 
               system.debug('***finelList***'+finalList);             
       }
   }               
}

4 Answers 4

3

The short answer:

You can't.

A bit longer answer:

Triggers can not be scheduled, they fire whenever there's some DML operation(insert/update/delete). If you want to schedule some piece of code you should look into schedulable interface. For example(I just copypasted it from the link, because I'm a lazy developer and I don't really feel like creating my own example):

global class MySchedulableClass implements Schedulable {
   global void execute(SchedulableContext ctx) {
      CronTrigger ct = [SELECT Id, CronExpression, TimesTriggered, NextFireTime
                FROM CronTrigger WHERE Id = :ctx.getTriggerId()];

      System.debug(ct.CronExpression);
      System.debug(ct.TimesTriggered);

      Merchandise__c m = new Merchandise__c(
                    Name='Scheduled Job Item',
                    Description__c='Created by the scheduler',
                    Price__c=1,
                    Total_Inventory__c=1000);
      insert m;
   }   
}
2

Rather than putting your logic in a trigger, place it into a class, where you can then schedule it to run whenever you want. See this doc on how to set the scheduled job up.

2
  • Is ter no way to schedule a trigger?
    – Chithra
    Commented Aug 25, 2016 at 7:03
  • No. A trigger exists to allow you hook into events as they happen, not to schedule future activity. Loading up the trigger with logic as you have in your example is not really recommended. Place the logic in a class and review the link I passed you. Commented Aug 25, 2016 at 7:11
0

You can create a Batch that launch the same logic that the trigger. To do this you need move your logic from the trigger to a class and follow the next flow:

  1. Mark(You can use a checbox field) the record in the trigger
  2. Create a batch that get the accounts that they are marked.
  3. Run the logic and mark the checbox as false -(All this is inside the batch).
0

I am not sure what you actually want but if you want that for all/particular set of account records , your trigger logic should be performed you can do this as below

  1. Create a batch class

    global class AccountBatchClass implements Database.Batchable<Account>{
    List<Account> AccountList; 
    global Iterable<Account> start(Database.BatchableContext BC)
        {
        try
        {   
            AccountList = new List<Account>([SELECT Name FROM Account ]);
            return AccountList;
    
        }
        catch(exception e)
        {
            System.debug(e.getmessage());
            return null;
        }
    }
    
    global void execute(Database.BatchableContext BC, List<Account> scope)
    {
        update scope;
    }  
    
        global void finish(Database.BatchableContext BC)
        {
    
        }
    }
    

2.Now Create a Scheduler

global class AccountBatchClassScheduler implements schedulable{
global void execute(SchedulableContext sc)
{
AccountBatchClass  batchScheduler = new AccountBatchClass (); //ur batch class
  database.executebatch(batchScheduler);
}
}

3.Schedule this Scheduler either through code or by going to apex classes and then clicking'Shedule Apex' button.

Thank you . :)

Happy Learning SFDC :) .

Please mark this as answer if it helped you :) .

Cheers,

  • Rajeev

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .