You need to sign in to do that
Don't have an account?
Eli Flores, SFDC Dev
Help converting a future method with http callouts to a batch method
Hi, I have this future method that errors out for having too many callouts frequently. I'd like to wrap my head around the batch apex concepts and add it to my toolbox so this project seems as good as any. Can someone help me with converting this methods to one that works by batches. Even just a high level walk through would be very helpful.
@future (callout = true) public static void postToLCS(Map<Id, String> licenseXmlMap) { Boolean postToProd = false; String lcsEndpoint = ''; String lcsUname = ''; String lcsPwd = ''; Map<String, Environment_Variables__c> envVarMap = Environment_Variables__c.getall(); Map<Id, String> succLicRespMap = new Map<Id, String>(); Map<Id, String> failLicRespMap = new Map<Id, String>(); License__c[] licRecs = [SELECT Id, Last_Post_Date__c, Last_Post_Response__c FROM License__c WHERE Id IN: licenseXmlMap.keySet()]; // LL - Get environment variables related to license posting if (envVarMap.get('use_prod_lcs').Value__c == 'true') { // LL - Check whether to post in DEV or PROD LCS // LL - Set PROD LCS endpoint and credentials lcsEndpoint = envVarMap.get('prod_lcs_endpoint').Value__c; lcsUname = envVarMap.get('prod_lcs_uname').Value__c; lcsPwd = envVarMap.get('prod_lcs_pwd').Value__c; } else { // LL - Set DEV LCS endpoint and credentials lcsEndpoint = envVarMap.get('dev_lcs_endpoint').Value__c; lcsUname = envVarMap.get('dev_lcs_uname').Value__c; lcsPwd = envVarMap.get('dev_lcs_pwd').Value__c; } Blob headerValue = Blob.valueOf(lcsUname + ':' + lcsPwd); String authorizationHeader = 'BASIC ' + EncodingUtil.base64Encode(headerValue); for (License__c l : licRecs) { if (!licenseXmlMap.get(l.Id).contains('Error') && !licenseXmlMap.get(l.Id).contains('error')) { HttpRequest req = new HttpRequest(); String lcsResp = ''; req.setEndpoint(lcsEndpoint); req.setMethod('POST'); req.setHeader('Authorization', authorizationHeader); req.setBody(licenseXmlMap.get(l.Id)); Http http = new Http(); HTTPResponse res; try { if (!test.isRunningTest()) { res = http.send(req); } if (res != null) { lcsResp = 'Status=' + res.getStatus() + ', StatusCode=' + res.getStatusCode(); } // LL - Update LCS response fields if no exception encountered l.Last_Post_Date__c = system.now(); l.Last_Post_Response__c = lcsResp; } catch (CalloutException ex) { Util.sendErrEMail('Error encountered during license posting. Additional message: ' + ex.getMessage() + ' Generated xml: ' + licenseXmlMap.get(l.Id)); l.Last_Post_Date__c = system.now(); // LL - Inject the exception message in the Last Post Response field l.Last_Post_Response__c = string.valueOf(ex); } } else { Util.sendErrEMail('Error encountered in generating xml. License not posted to the LCS. Generated xml: ' + licenseXmlMap.get(l.Id)); l.Last_Post_Date__c = null; l.Last_Post_Response__c = 'Error encountered in generating xml. License not posted to the LCS.'; } // LL - TODO: Need to implement some logger mechanism... } // LL - Set static class to prevent recursive future calls ProcessorControl.inFutureContext = true; // Set database savepoint in event db transactions fail System.SavePoint sp = Database.setSavepoint(); try { //update licRecs; Boolean hasError = false; Database.SaveResult[] updResult = database.update(licRecs, true); // LL - Check if error/s were encountered during the update for (Integer i=0; i < updResult.size(); i++) { if (!updResult[i].isSuccess()) { // LL - Indicate that an error was encountered hasError = true; // LL - Exit the entire loop since an error was encountered break; } } if (!hasError) { updateWowzaFromLicense(); } } catch (Exception e){ // LL - Rollback transaction Database.rollback(sp); Util.sendErrEmail('Encountered an error updating license and/or wowza objects. Additional message ' + e.getMessage()); } }
batch classes has same limits as future methods for number of callouts!
Rootcause in your case is you are having a callout inside for loop. And in a transaction you can have at max 10 callouts.
Going back to your code
Whenever there are more than 10 licRecs you will get this error.
You may have to figure out a way in which the number of callouts remains inside limit that is <= 10
Sent from my iPhone
Have a look here
http://www.salesforce.com/us/developer/docs/apexcode/Content/apex_batch_interface.htm
Hmmm... i've read the documentation several times and some sample tutorials online but I'm still having a hard time wrapping my mind about what's happening conceptually. If anyone can provide some guidance, it would be much appreciated.
Sent from my iPhone