4

I'm receiving the following error during validation/deployment: "Methods defined as TestMethod do not support Web service callouts"

My trigger doesn't contain a callout, but from what I've read it's likely being triggered by a package or another trigger.

I've seen other posts on this subject, and I've tried all their solutions including mocking HTTP responses and callouts, but nothing seems to work. Can anyone help?

Below are the trigger and two classes being deployed:

Trigger

trigger updateContactAfterConverted on Lead (after update) {
    for(Lead lead:System.Trigger.new) {

        // was the lead converted?
        if (Lead.IsConverted) {

            // query new contact
            Contact newContact = [SELECT Id FROM Contact WHERE Contact.Id = :lead.ConvertedContactId];

            // run @future class to update contact after conversion completed
            updateContactAfterConvertedFuture.myMethod(newContact.id);

        }
    }
}

Class referenced in trigger

public class updateContactAfterConvertedFuture {

  @future 
  public static void myMethod(String newContact) {

    // Find new contact
    Contact updateContact = [SELECT Id FROM Contact WHERE Contact.Id = :newContact LIMIT 1];

    // Set field to true                                    
    updateContact.Conversion_Completed__c = TRUE;

    // Update contact               

    update updateContact;     

   }
}

Test class

@isTest
private class testUpdateContactAfterConverted {
    static testMethod void myUnitTest() {
        // Create new test lead
        Lead myLead = new Lead(LastName = 'Fry', Company='Fry And Sons', LeadSource = 'Advertising', Lead_Source_Detail__c = 'PPC');
        insert myLead;

        // Convert test lead
        Database.LeadConvert lc = new Database.LeadConvert();
        lc.setLeadId(myLead.id);

        // Check conversion
        LeadStatus convertStatus = [SELECT Id, MasterLabel FROM LeadStatus WHERE IsConverted=true LIMIT 1];
        lc.setConvertedStatus(convertStatus.MasterLabel);

        // Declare successful
        Database.LeadConvertResult lcr = Database.convertLead(lc);
        System.assert(lcr.isSuccess());
    }
}

I also tried not including the test class in the deployment, but without it I get 0% code coverage on the trigger.

EDIT

Updated the test class to below to mock an HTTP response, but I still get the same error.

@isTest
private class testUpdateContactAfterConvert2 {

    static testMethod void myUnitTest() {

        Test.startTest();       
            // Create new test lead
            Lead myLead = new Lead(LastName = 'Fry', Company='Fry And Sons', LeadSource = 'Advertising', Lead_Source_Detail__c = 'PPC');
            insert myLead;

            Test.setMock(HttpCalloutMock.class, new TestMockService());

            // Convert test lead
            Database.LeadConvert lc = new Database.LeadConvert();
            lc.setLeadId(myLead.id);

            // Check conversion
            LeadStatus convertStatus = [SELECT Id, MasterLabel FROM LeadStatus WHERE IsConverted=true LIMIT 1];
            lc.setConvertedStatus(convertStatus.MasterLabel);

            // Declare successful
            Database.LeadConvertResult lcr = Database.convertLead(lc);
            System.assert(lcr.isSuccess());

            // Run @future
            Contact newContact = [Select Id from Contact LIMIT 1];
            updateContactAfterConvertedFuture.myMethod(newContact.id);

        Test.stopTest();
    }

    //Mockup service
    private class TestMockService implements HttpCalloutMock {

        public HTTPResponse respond(HTTPRequest req) {
            String response ;
            HTTPResponse res = new HTTPResponse();
            res.setStatusCode(200);

            res.setBody(response);
            return res;
        }
    }
}
4
  • 1
    Does the error tell you what class is failing? The error description seems to indicate that you have somewhere in your code a test class that's making a callout, and it doesn't look like it's the one you posted.
    – mkorman
    Feb 14, 2016 at 22:13
  • @mkorman unfortunately it doesn't. It identifies my test class above as having failed, notes the "myUnitTest" for the method, then gives me the error and "Stack Trace: null"
    – Matt
    Feb 14, 2016 at 22:52
  • Do you have any other triggers on lead? Perhaps there is another trigger running the callout? Although I don't think that's possible either...
    – mkorman
    Feb 14, 2016 at 22:55
  • 1
    With the @future method being called in the test case my first thought would be to wrap the Database.convertLead(lc) call in a Test.startTest() and Test.stopTest(). This doesn't have a direct relationship to the error you are getting, but is good practice to make the async method run in the testing context. Feb 14, 2016 at 22:55

2 Answers 2

2

Update:

I suspect the root cause is a managed package that is present/active in the production org but not in the Sandbox org. It will likely have a trigger on Contact (maybe Lead) that is attempting to make a callout. You can't create a Mock for another namespace (see Getting “TestMethod does not support Web service callouts”, callout is in managed trigger).

Firstly, have a look at all the triggers on Contact in production. Look for ones in another namespace. They see if that package has a custom setting that could be used to disable the trigger. Disabling the managed package could become part of the test case. Maybe also check the Remote Site settings for any likely suspects.


The @future annotation on myMethod makes it asynchronous. To test this you need to wrap calls to it in Test.startTest() and Test.stopTest() respectively.

In your case you will what to wrap the start/stop around the statement.

Test.startTest();
Database.LeadConvertResult lcr = Database.convertLead(lc);
Test.stopTest();

If you are still getting the error, try commenting out lines from the end of the test case and working backwards until the line that is causing the error becomes apparent.

17
  • No dice... I still get the same error. I'll try commenting out and working backwards like you mentioned.
    – Matt
    Feb 15, 2016 at 1:30
  • It might be occurring with something on the Lead insertion. If you can get the full Apex Debug log it might also help indicate where the callout is being attempted. Feb 15, 2016 at 2:09
  • Are you able to get the debug log while validating? Or would I need to turn on the log and insert a lead to just see what's already happening in production?
    – Matt
    Feb 15, 2016 at 2:52
  • Ah, interesting. I missed the part that this is only occurring on deployment to production. Try running the body of the test case in the developer console in production as anonymous Apex. That should make it easy to capture the debug log. The log should show what callout is occurring. You will of course need to clean up the records afterwards. Or add a System.assert(false, 'Boom'); to the end of the anonymous apex. Feb 15, 2016 at 19:00
  • I ran the anonymous apex and got the log, but I'm not totally sure what I'm looking for. Is it a specific Event or would it be in the Details? The only reference to callouts I found was on LIMIT_USAGE_FOR_NS events, but each time it was Number of callouts: 0 out of 100
    – Matt
    Feb 15, 2016 at 22:35
0

Salesforce doesn't allow to execute callouts in test classes. Therefore you will have to implement a mockup and include that snippet in "Test.startTest" and "Test.stopTest" blocks.

Try this.

@isTest
private class testUpdateContactAfterConverted {

    static testMethod void myUnitTest() {

        Test.startTest();       
            // Create new test lead
            Lead myLead = new Lead(LastName = 'Fry', Company='Fry And Sons', LeadSource = 'Advertising', Lead_Source_Detail__c = 'PPC');
            insert myLead;

            Test.setMock(HttpCalloutMock.class, new TestMockService());

            // Convert test lead
            Database.LeadConvert lc = new Database.LeadConvert();
            lc.setLeadId(myLead.id);

            // Check conversion
            LeadStatus convertStatus = [SELECT Id, MasterLabel FROM LeadStatus WHERE IsConverted=true LIMIT 1];
            lc.setConvertedStatus(convertStatus.MasterLabel);

            // Declare successful
            Database.LeadConvertResult lcr = Database.convertLead(lc);
            System.assert(lcr.isSuccess());
        Test.stopTest();
    }

    //Mockup service
    private class TestMockService implements HttpCalloutMock {

        public HTTPResponse respond(HTTPRequest req) {
            String response ;
            HTTPResponse res = new HTTPResponse();
            res.setStatusCode(200);

            res.setBody(response);
            return res;
        }
    }
}
5
  • Tried adding that and it didn't seem to help. I still get the same error.
    – Matt
    Feb 15, 2016 at 1:30
  • Did you also included the setMock as well? Feb 15, 2016 at 1:36
  • I used the code snippet you had above. How do I incude the setMock?
    – Matt
    Feb 15, 2016 at 2:03
  • I have updated my answer to include a sample mock class. Hope it helps. Otherwise share your code where its making a callout. Feb 15, 2016 at 6:28
  • I tried using your updated class, but I still get the same error, "Methods defined as TestMethod do not support Web service callouts Stack Trace: null" -- I even tried to validate against just the test class, but it still gave me the same error. All the other Lead triggers in my org are managed packages, so I can't see their code and they should have been ignored during validation?
    – Matt
    Feb 15, 2016 at 16:52

You must log in to answer this question.

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