本文介绍了有未提交的工作待处理.请在调用前提交或回滚的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我有一个批处理类
public class BatchCreateGCalendars implements Database.Batchable<SObject>, Database.Stateful, Database.AllowsCallouts {
private String query;
private String pageToken ;
private String accessToken;
private String CalendarId;
public BatchCreateGCalendars(){
this.query = 'Select Id, Name, CalendarId__c from CalendarSettings__c'; // Query to get the CalendardID (Google ID)
}
public Database.Querylocator start(Database.BatchableContext BC){
return Database.getQueryLocator(query);
}
public void execute(Database.BatchableContext BC, List<sObject> scope){
GoogleForce__c gApp = GoogleForce__c.getAll().values()[0];
GCalendarUtil.Calendar cal = new GCalendarUtil.Calendar();
GCalendarUtil.GResponse gResp = new GCalendarUtil.GResponse();
String endPoint = GCalendarUtil.CALENDAR_BASE + GCalendarUtil.CAL_URL; // Calendar Endpoint
// Iterate over the records, delete each calendar and create the calendar again.
for(CalendarSettings__c c : (List<CalendarSettings__c>)scope){
String delEndpoint = endpoint + '/' + c.CalendarId__c;
if(gApp.ExpiresIn__c < system.now()){
gResp = GCalendarUtil.getNewToken(gApp);
accessToken = gResp.access_token;
gApp.AccessToken__c = gResp.access_token;
gApp.ExpiresIn__c = System.now().addSeconds(gResp.expires_in);
}else{
accessToken = gApp.AccessToken__c;
System.debug('Calendar Id is '+ c.CalendarId__c);
}
String re= GCalendarUtil.doApiCall(null,'GET','https://www.googleapis.com/calendar/v3/calendars/'+c.CalendarId__c+'/events',accessToken);
re = re.replaceAll('"end":','"end1":');
re = re.replaceAll('"dateTime":','"dateTime1":');
System.debug('response is' +re);
JSON2Apex1 aa = JSON2Apex1.parse(re);
List<JSON2Apex1.Items> ii = aa.items ;
System.debug('next token is'+ aa.nextPageToken);
List<String> event_id =new List<String>();
if(ii!= null){
for(JSON2Apex1.Items i: ii){
event_id.add(i.id);
}
}
for(String s:event_id)
{GCalendarUtil.doApiCall(null,'DELETE','https://www.googleapis.com/calendar/v3/calendars/'+c.CalendarId__c+'/events/'+s,accessToken);
}
pageToken = aa.nextPageToken;
CalendarId=c.CalendarId__c;
if(pageToken!=null)
deleteEvents(accessToken , pageToken,c.CalendarId__c);
}
update gApp;
}
/*
After the batch job is finished, trigger the other batch jobs where the Campaigns are sent as Events to the calendars.
Use the CalendarQuery field on the each calendarSettings record.
*/
public void finish(Database.BatchableContext BC){
BatchDeleteEvents bjob1 = new BatchDeleteEvents(CalendarId,accessToken);
Database.executeBatch(bjob1,9);
for(CalendarSettings__c c : [Select Id, Name, CalendarQuery__c, CalendarId__c,FieldToDisplay__c from CalendarSettings__c WHERE Name IN ('Public Calendar', 'Internal marketing Calendar')]){
BatchPublicCampaignsToGoogle bjob = new BatchPublicCampaignsToGoogle(c.CalendarQuery__c,c.CalendarId__c,c.FieldToDisplay__c);
Database.executeBatch(bjob,9); // This is set to process 9 records, allowing 1 extra callout for refresh token in case needed.
}
}
public static void deleteEvents(String accessToken,String pageToken,String CalendarId){
List<Event__c> event_id =new List<Event__c>();
while(pageToken != null)
{ String re = GCalendarUtil.doApiCall(null,'GET','https://www.googleapis.com/calendar/v3/calendars/'+CalendarId+'/events?pageToken='+pageToken,accessToken);
System.debug('next page response is'+ re);
re = re.replaceAll('"end":','"end1":');
re = re.replaceAll('"dateTime":','"dateTime1":');
JSON2Apex1 aa = JSON2Apex1.parse(re);
List<JSON2Apex1.Items> ii = aa.items ;
System.debug('size of ii'+ii.size());
pageToken = aa.nextPageToken ;
if(ii!= null){
for(JSON2Apex1.Items i: ii){
event_id.add(new Event__c(name = i.id));
}
}
}
insert event_id;
}
}
在这段代码中,我在这一行出现错误
in this code i am getting error at this line
String re= GCalendarUtil.doApiCall(null,'GET','https://www.googleapis.com/calendar/v3/calendars/'+c.CalendarId__c+'/events',accessToken);
错误是
You have uncommitted work pending. Please commit or rollback before calling out
为什么我会遇到这个错误,请帮忙,还有一个疑问是当我在完成方法中调用此代码时
why i am facing this error please help and one more doubt is when i call this code in finish method
BatchDeleteEvents bjob1 = new BatchDeleteEvents(CalendarId,accessToken);
Database.executeBatch(bjob1,9);
它将同步执行此代码 na 表示处理 9 个批次中的所有对象,然后控制将在此代码上执行
it will execute this code synchronously na means all objects in batch of 9 processed and then control will come on this code
BatchPublicCampaignsToGoogle bjob = new BatchPublicCampaignsToGoogle(c.CalendarQuery__c,c.CalendarId__c,c.FieldToDisplay__c);
Database.executeBatch(bjob,9);
推荐答案
您不能在 Salesforce/Apex 中制作标注以及 DML 语句.
you can't make Callouts in Salesforce/Apex along with DML statements.
您可以首先根据可以调用 DML 语句的 Callout 状态执行 CallOut.
You could first perform CallOut based on the Callout Status you can invoke DML Statments.
这篇关于有未提交的工作待处理.请在调用前提交或回滚的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!