function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
Sainath VenkatSainath Venkat 

Batch apex causing an issue - "Constructor not defined: [BatchSISstagingObject].()"

Can anyone help me out in writing batch apex that will create or update records.I never worked on batch apex so struggling here I have two objects
1) SIS_Staging__c
2) Contact
Both objects are having same field Siscode__c, so on inserting records in SIS_Staging__c, I need to check if any contact records are having same Siscode__c or not, if yes then I need to update else I need to create Contact.
I tried below code but when I run batch apex in anonymous window then I am getting below error.
"Constructor not defined: [BatchSISstagingObject].()"
My code is below.
 
global class BatchSISstagingObject implements Database.Batchable<sObject>{
    List <SIS_Staging__c> mapSisobject = new List <SIS_Staging__c> ();
    List <Contact> contactlist1 = new List <Contact> ();
    
    global BatchSISstagingObject(List <SIS_Staging__c> sisobjectUpdate) {
        mapSisobject=sisobjectUpdate;
        
    }
    
    global Database.QueryLocator start(Database.BatchableContext BC) {
        return DataBase.getQueryLocator([SELECT Id, SIS_Student_ID__c
                                         FROM Contact
                                        ]);
    }
    global void execute(Database.BatchableContext BC , List <Contact> contactlist) {
        for (SIS_Staging__c acct : mapSisobject){ 
            for (Contact con : contactList){
                if (con.SIS_Student_ID__c == acct.Name){
                        contactlist1.add(new Contact(
                            Id = con.Id,
                            FirstName = acct.First_Name__c,
                            LastName = acct.Last_Name__c
                           ));
                    }
            }   
        }
        
         update contactlist1;
    } 
    global void finish(Database.BatchableContext BC){
        
    }

}

 
Best Answer chosen by Sainath Venkat
Amol Rokade 26Amol Rokade 26
global class BatchSISstagingObject implements Database.Batchable<sObject>{
   
    
    
    
    global Database.QueryLocator start(Database.BatchableContext BC) {
        return DataBase.getQueryLocator([SELECT Id, Name
                                         FROM SIS_Staging__c
                                        ]);
    }
    global void execute(Database.BatchableContext BC , List <SIS_Staging__c> contactlist) {
		Set<String> uniquekeySet = new Set<String>();
		for(SIS_Staging__c stagingObj : contactlist){
			uniquekeySet.add(stagingObj.Name);
		}
		List<Contact> contactToUpdate = new List<Contact>();
		List<Contact> contactToInsert = new List<Contact>();
		Map<String,Contact> studentIdTOContact = new Map<String,Contact>();
		List<Contact> conList2 = [SELECT ID,SIS_Student_ID__c FROM CONTACT WHERE SIS_Student_ID__c IN:uniquekeySet];
		for(Contact conObj : conList2){
			studentIdTOContact.put(conObj.SIS_Student_ID__c,conObj);
			
		}
        for (SIS_Staging__c acct : contactlist){ 
              if(studentIdTOContact.containsKey(acct.Name)){
				 Contact con = studentIdTOContact.get(acct.Name);
				 con.FirstName = acct.First_Name__c;
                 con.LastName = acct.Last_Name__c;
				 contactToUpdate.add(con);

			  }else{
				  //Add your logic when contact not exist related to StagingObject
				  //Create New Contact in this case
				  Contact con = new Contact();
				 con.FirstName = acct.First_Name__c;
                 con.LastName = acct.Last_Name__c;
				 contactToInsert.add(con);
				  
			  }
        }
		
		
		if(!contactToInsert.isEmpty()){
			Insert contactToInsert;
		}
		if(!contactToUpdate.isEmpty()){
			
			Update contactToUpdate;
		}
        
         
    } 
    global void finish(Database.BatchableContext BC){
        
    }

}

Will this work?

All Answers

Amol Rokade 26Amol Rokade 26
Can you please post code snippet how you have ran batch class from  anonymous window ?
 
Sainath VenkatSainath Venkat
@amol, below is the snipppet that I ran in anonymous window
BatchSISstagingObject objClass = new BatchSISstagingObject();
Database.executeBatch(objClass);

 
Amol Rokade 26Amol Rokade 26
Hi,

As you can see in your code you have parameterised constructor:
global BatchSISstagingObject(List <SIS_Staging__c> sisobjectUpdate) {
mapSisobject=sisobjectUpdate;
}
and you are not passing any parameter while running batch class.
This is reason you are getting error.
Either you need to pass List <SIS_Staging__c> of this object  while running your batch class from anonymous window
List<SIS_Staging__c> stagingList;
BatchSISstagingObject objClass = new BatchSISstagingObject(stagingList);
Database.executeBatch(objClass);
------------------------------------
or you need to remove this parameterised constructor.
 
Sainath VenkatSainath Venkat
@amol, this is the first time I am working on batch, can you help me how can I remove parameterised constructor here.

My requirement is I need to run this batch everyday at 11 PM, for all the records in staging object, I need to check whether contact exists or not, if exists I need to update contact else I need to create contact
Amol Rokade 26Amol Rokade 26
Yes I can but first let me know what is relationship between contact and and staging object?
Sainath VenkatSainath Venkat
@Amol, there is no relationship between Contact and Staging object,

On Staging object, I have a field "Name", and on Contact I have field "SIS_Student_ID__c", so when my batch runs, I need to check for each staging record I have matching contacts or not
Condition is "Stagingobject.Name = Contact.SIS_Student_ID__c", if it matches then I need to update the contact, if it does not match then I need to insert the contact.
Amol Rokade 26Amol Rokade 26
global class BatchSISstagingObject implements Database.Batchable<sObject>{
   
    
    
    
    global Database.QueryLocator start(Database.BatchableContext BC) {
        return DataBase.getQueryLocator([SELECT Id, Name
                                         FROM SIS_Staging__c
                                        ]);
    }
    global void execute(Database.BatchableContext BC , List <SIS_Staging__c> contactlist) {
		Set<String> uniquekeySet = new Set<String>();
		for(SIS_Staging__c stagingObj : contactlist){
			uniquekeySet.add(stagingObj.Name);
		}
		
		Map<String,Contact> studentIdTOContact = new Map<String,Contact>();
		List<Contact> conList2 = [SELECT ID,SIS_Student_ID__c FROM CONTACT WHERE SIS_Student_ID__c IN:uniquekeySet];
		for(Contact conObj : conList2){
			studentIdTOContact.put(conObj.SIS_Student_ID__c,conObj);
			
		}
        for (SIS_Staging__c acct : contactlist){ 
              if(studentIdTOContact.containsKey(acct.Name)){
				  //Add your logic when contact exist related to StagingObject
			  }else{
				  //Add your logic when contact not exist related to StagingObject
				  //Create New Contact in this case
				  
			  }
        }
        
         
    } 
    global void finish(Database.BatchableContext BC){
        
    }

}
Please check above code and add logic instead of comment as per your requirement
 
Sainath VenkatSainath Venkat
@Amol, if contact exists then I just need to update firstname, lastName and Email on contact else I need to create contact with those three fields only
Amol Rokade 26Amol Rokade 26
global class BatchSISstagingObject implements Database.Batchable<sObject>{
   
    
    
    
    global Database.QueryLocator start(Database.BatchableContext BC) {
        return DataBase.getQueryLocator([SELECT Id, Name
                                         FROM SIS_Staging__c
                                        ]);
    }
    global void execute(Database.BatchableContext BC , List <SIS_Staging__c> contactlist) {
		Set<String> uniquekeySet = new Set<String>();
		for(SIS_Staging__c stagingObj : contactlist){
			uniquekeySet.add(stagingObj.Name);
		}
		List<Contact> contactToUpdate = new List<Contact>();
		List<Contact> contactToInsert = new List<Contact>();
		Map<String,Contact> studentIdTOContact = new Map<String,Contact>();
		List<Contact> conList2 = [SELECT ID,SIS_Student_ID__c FROM CONTACT WHERE SIS_Student_ID__c IN:uniquekeySet];
		for(Contact conObj : conList2){
			studentIdTOContact.put(conObj.SIS_Student_ID__c,conObj);
			
		}
        for (SIS_Staging__c acct : contactlist){ 
              if(studentIdTOContact.containsKey(acct.Name)){
				 Contact con = studentIdTOContact.get(acct.Name);
				 con.FirstName = acct.First_Name__c;
                 con.LastName = acct.Last_Name__c;
				 contactToUpdate.add(con);

			  }else{
				  //Add your logic when contact not exist related to StagingObject
				  //Create New Contact in this case
				  Contact con = new Contact();
				 con.FirstName = acct.First_Name__c;
                 con.LastName = acct.Last_Name__c;
				 contactToInsert.add(con);
				  
			  }
        }
		
		
		if(!contactToInsert.isEmpty()){
			Insert contactToInsert;
		}
		if(!contactToUpdate.isEmpty()){
			
			Update contactToUpdate;
		}
        
         
    } 
    global void finish(Database.BatchableContext BC){
        
    }

}

Will this work?
This was selected as the best answer
Sainath VenkatSainath Venkat
@Amol, I just run the command in anonymous window using below line
Id batchJobId = Database.executeBatch(new SISstagingupsertbatch(), 200);
but no records were inserted, I just created one record in SIS Staging object then record does not got created in Contact object
 
Amol Rokade 26Amol Rokade 26
I am not able to understand your issue completely.Can you send me your contact number on rokadeamol25@gmail.com then we can have call?
 
Sainath VenkatSainath Venkat
Sure, I will email you but the thing is lets say I will insert 10 records in SIS_Staging__c in a day, it has field First_Name__c, Last_Name__c,Name fields then at night I need to have a batch apex which will do the below things.

Batch apex will look into existing Contacts for Contact.SIS_Student_ID__c == SIS_Staging__c.Name, if records matches then I need to update Contacts else I need to create a Contact.
Amol Rokade 26Amol Rokade 26
If your logic as explained in last reply then code that i have shared with you should work
Sainath VenkatSainath Venkat
yeah that is what I was thinking, logic make sense but I don't know some how records are not either getting created in contact not update
Amol Rokade 26Amol Rokade 26
Is it working because i can see u have marked question as solved?
Sainath VenkatSainath Venkat
yes it is, I don't know why it caused issue, I just logged out from org and logged in again ten it worked🤣🤣🤣🤣
Amol Rokade 26Amol Rokade 26
Oh nice to hear that!
Sainath VenkatSainath Venkat
@amol, sorry for asking you this but is it possible to create or update opportunity in a same way.

now I have relationship between Contact and opportunity, ie lookup relationship, so for the contacts which I inserted or updated in above code, I need to see whether opportunity exists or not if exists then i need to update opportunity else I need to create opportunity
Amol Rokade 26Amol Rokade 26
Do you want to achieve in same transaction meaning in same batch class?If yes ,you can achieve.
Sainath VenkatSainath Venkat
yeah, now for all contacts I need to check whether opportunities exists ot not, if exists then I need to update few opportunity field from SIS STAGING OBJECT else I need to create opportunities
Amol Rokade 26Amol Rokade 26
Create two map like belw:

Map<ContactId,Opportunity> and one for Map<ContactId,StagingObject>.
Iterate over first Map,see whether it has opportunity or not if yes then update that oppty using using second Map because you will get related staging object using second map other wise create new oppty
 
Sainath VenkatSainath Venkat
@amol, can you guide me on this, I just want to check opportunities available or not for those contacts which I inserted or updated in above code, if exists then I need to update else create opportunities
Amol Rokade 26Amol Rokade 26
Yes same thing I have explained to you in my earlier reply
Sainath VenkatSainath Venkat
can you help me out with sample code if possibel please
Sainath VenkatSainath Venkat
@amol, I tried below code but the for loop iteration for SIS_Staging__c is causing issue here which is creating multiple opportunities for each contact
 
List<Contact> allcontacts = [SELECT Id, Name,AccountId,SIS_Student_ID__c,FirstName,LastName from Contact];
        List<SIS_Staging__c> allstages = [select Id,Name,SIS_Application_Id__c,AdmTyp__c,Resident_Tuition__c,ActnRsn__c,Admit_Term__c,Email__c,Home_Country__c,Plan__c,Prog1__c,Prog__c,
                                          ProgActn__c from SIS_Staging__c];
        set<Id> contactId = new set<Id>();
        set<string> studentId = new set<string>();
        for(Contact contactall : allcontacts){
            contactId.add(contactall.Id);
            studentId.add(contactall.SIS_Student_ID__c);
        }
        List<Opportunity> oppUpdate = new List<Opportunity>();
        List<Opportunity> oppInsert = new List<Opportunity>();
        Map<Id,Opportunity> opptoContact = new Map<Id,Opportunity>();
        Map<Id,SIS_Staging__c> sistoopp = new Map<Id,SIS_Staging__c>();
        List<Opportunity> opp2 = [SELECT Id,Student__c,Name from Opportunity where Student__c IN: contactId];
        for(Opportunity oppObj: opp2){
            opptoContact.put(oppObj.Student__c,oppObj);
        }
        List<SIS_Staging__c> stages = [select Id,Name from SIS_Staging__c where Name IN: studentId];
        for(SIS_Staging__c sisobj: stages){
            sistoopp.put(sisObj.Id ,sisobj);
        }
        for(Contact cont1: allcontacts){
            for(SIS_Staging__c sist1: allstages){
            if(opptoContact.containsKey(cont1.Id)){
                Opportunity opp = opptoContact.get(cont1.Id);
                opp.Name = cont1.FirstName +''+ cont1.LastName + '-' +  'sist1.SIS_Application_Id__c';
                opp.AccountId = cont1.AccountId;
                opp.Student__c = cont1.Id;
                opp.CloseDate = system.today()+60;
                opp.StageName = 'New';
                //opp.SIS_Application_Id__c = sist1.SIS_Application_Id__c;
                //opp.Admit_Type__c = sist1.AdmTyp__c;
                //opp.Resident_Tuition__c = sist1.Resident_Tuition__c;
                oppUpdate.add(opp);
            }
            else{
                Opportunity opp = new Opportunity();
                opp.Name = cont1.FirstName + cont1.LastName + 'sist1.SIS_Application_Id__c';
                opp.AccountId = cont1.AccountId;
                opp.Student__c = cont1.Id;
                opp.CloseDate = system.today()+60;
                Opp.StageName = 'New';
                //opp.SIS_Application_Id__c = sist1.SIS_Application_Id__c;
                //opp.Admit_Type__c = sist1.AdmTyp__c;
                //opp.Resident_Tuition__c = sist1.Resident_Tuition__c;
                oppInsert.add(opp);
            }
        }
        }
        if(!oppInsert.IsEmpty()){
            insert oppInsert;
        }
        if(!oppUpdate.IsEmpty()){
            update oppUpdate;
        }

 
Jyothi Priya JarangJyothi Priya Jarang
Hi @amol@sainath,
I have a similar requirement. Can you please help
From the staging object, putting the data into 2 differnet objects having M-D relationship.Then checking for duplciates in Master object and if no duplciates create master and child record.