问题描述
global class OriginalOpportunityAdSourceBatch {
global Integer successCount = 0;
global Integer errorCount = 0;
global String errors = '';
global Database.QueryLocator start(Database.BatchableContext bc) {
return Database.getQueryLocator(
'Select id,AdSourceOriginalBucket__c,Ad_Source__c,isClosed,isWon from Opportunity WHERE IsClosed = TRUE AND IsWon = TRUE'
);
}
global void execute(Database.BatchableContext bc,List<Opportunity> scope){
List<Database.SaveResult> srs = Database.update(OriginalOpportunityActions.ProcessAdSource(scope),false);
for(Database.SaveResult sr:srs) {
if(sr.isSuccess()) {
successCount++;
}
else {
errorCount++;
errors += 'Opportunity Failed to Update. Record ID: ' + sr.getId();
for(Database.Error er: sr.getErrors()) {
errors += er.message;
}
errors += '<br/>';
}
}
}
global void finish(Database.BatchableContext bc){
String emailBody = 'Successful Updates: ' + successCount + ' Error Count: ' + errorCount;
if(errors!='') {
emailBody += ' -- ' + errors;
}
Messaging.SingleEmailMessage mail = new Messaging.SingleEmailMessage();
mail.setToAddresses(new String[]{UserInfo.getUserEmail()});
mail.setReplyTo(UserInfo.getUserEmail());
mail.setSubject('Batch Original Opportunity Update Completed');
mail.setHTMLBody(emailBody);
system.debug('emailBody -- ' + emailBody);
if(!Test.isRunningtest()){Messaging.sendEmail(new List<Messaging.SingleEmailmessage>{mail});}
}
}
和这个:
DB::table('orders')
->join('users','orders.user_id','=','users.id')
->groupBy('users.sponsor_id')
->selectRaw('users.sponsor_id,sum(points) as total_points_a')
->get();
我看不出如何巧妙地将它们组合在一起的方法。但是,最终需要每个DB::table('orders')
->join('users','users.id')
->join('users as leader','users.sponsor_id' = 'leader.id')
->groupBy('leader.sponsor_id')
->selectRaw('leader.sponsor_id,sum(points) as total_points_b')
->get();
的{{1}}和total_points_a
。并非每个total_points_b
都是两个查询的结果。
我设法将这两个结果与Laravel集合合并,但这很慢。是否可以以某种方式合并查询,以使一个查询的结果成为sponsor_id
?
解决方法
正如user3532758所建议的那样,subquery joins
是我所需要的。
为了真正显示所有结果,我已经修改了第一个查询以使用左联接获取所有用户。由此,我可以创建一个左联接子。
$secondQuery = DB::table('orders')
->join('users','orders.user_id','=','users.id')
->join('users as leader','users.sponsor_id' = 'leader.id')
->groupBy('leader.sponsor_id')
->selectRaw('leader.sponsor_id,sum(points) as total_points_b');
$result = DB::table('users')
->leftjoin('orders','users.id')
->groupBy('users.sponsor_id')
->selectRaw('users.sponsor_id,sum(points) as total_points_a,bonus_b.total_points_b')
->leftJoinSub($secondQuery,'bonus_b',function ($join) {
$join->on('users.sponsor_id','bonus_b.sponsor_id');
})
->get();