+ Start a Discussion
vickim1.396005552708281E12vickim1.396005552708281E12 

Unit testing coverage issue!

Hi Guys,

I have created 1 trigger and one class in sandbox, I have written 2 test classes for this, one test for the trigger and one test for the class.

When I run the 'test run' in Sandbox it say Class have 100% coverage, however when trying to deploy the code in prod I get errors saying coverage is only 50%

Code Below

Trigger :
trigger myTrigger on Opportunity (after update) {
    string prams;
	
    // partner portal auth details
    prams = 'userkey=salesforce';
    prams = prams + '&passkey=password';
    
    // action occured in saledforce
    prams = prams + '&action=OpportunityUpdated';
    
    for (Opportunity op: trigger.new) {
        Opportunity oldOpportunity = Trigger.oldMap.get(op.Id);
        
        prams = prams + '&id[]=' + op.Id; // Opportunity ID
        prams = prams + '&name[]=' + op.Name;
        prams = prams + '&oldName[]=' + oldOpportunity.Name; // previous Name
        prams = prams + '&stageName[]=' + op.StageName;
        prams = prams + '&oldStageName[]=' + oldOpportunity.StageName; // previous stage
        prams = prams + '&closeDate[]=' + op.CloseDate;
        prams = prams + '&oldCloseDate[]=' + oldOpportunity.CloseDate; // previous close date
        prams = prams + '&closeLostReason[]=' + op.Closed_Lost_Reason__c;
        prams = prams + '&ownerId[]=' + op.OwnerId;
       	
    }
    
    Sync.invokeUrlWithPost('http://myurl.com', prams); 
}

My class 
public class Sync{
    
    //Future annotation to mark the method as async.
    @Future(callout=true)
    public static void invokeUrlWithPost(string url, string prams){ 
        if(url.length() > 0 && prams.length() > 0){
            HttpRequest req = new HttpRequest();
            req.setMethod('POST');
            req.setEndpoint(url);
            req.setHeader('Content-Type', 'application/x-www-form-urlencoded'); 
            req.setBody(prams);
        
            Http http = new Http();
        
            try {
                HttpResponse res = http.send(req);
                system.debug('B:STATUS:'+res.getStatus());
            } catch(system.Exception e) {
                system.debug('B:Callout error:'+e);
            }
        }
        
    }
}

TEST CLASSES

testSync()
@isTest
public class testSync{

    static testMethod void testInvokeUrlWithPost(){
		String url = 'http://myurl.com';
        String prams;
            
        // partner portal auth details
        prams = 'userkey=salesforce';
        prams = prams + '&passkey=password';
        
        // action occured in saledforce
        prams = prams + '&action=testInvokeUrlWithPost&Name=test';
        
        test.startTest();
        System.assertEquals(url, 'http://myurl.com');
        
        Sync.invokeUrlWithPost(url, prams); 
        test.stopTest();
    }
    
    static testMethod void testInvokeUrlWithPost_noPrams(){
		String url = 'http://myurl.com';
        String prams = '';
                 
        test.startTest();
        Sync.invokeUrlWithPost(url, prams); 
        test.stopTest();
    }
    
    static testMethod void testInvokeUrlWithPost_invalidUrl(){
		String url = '';
        String prams;
        
        // partner portal auth details
        prams = 'userkey=salesforce';
        prams = prams + '&passkey=password';
        
        // action occured in saledforce
        prams = prams + '&action=testInvokeUrlWithPost&Name=test';
        
        test.startTest();
        Sync.invokeUrlWithPost(url, prams); 
        test.stopTest();
    }
    
}

test for my trigger
@isTest
public class testMyTrigger{

    static testMethod void testPurplePortalUpdate(){
		// create a new Opportunity
        Opportunity testOpp = new Opportunity( Name = 'My Test Opp', StageName = 'Qualification', CloseDate = System.today().addDays(4));
      	// insert it to the db
        insert  testOpp;
        
        // get the inserted Opportunity to edit it
        Opportunity oldOpp = [SELECT Name, StageName, CloseDate FROM Opportunity WHERE id = :testOpp.Id];
		
        // error if the Opportunity did not add
        System.assert(testOpp.Id != null, 'The Test opportunities did not insert properly, please check validation rules and other mechanisms');
        
        // change its name
        oldOpp.Name = 'Updated';
        System.assertEquals(oldOpp.Name, 'Updated');
        System.assertEquals(oldOpp.StageName, 'Qualification');

        // Start the test, this changes governor limit context to
    	// that of trigger rather than test.
        test.startTest();
        
        // update the Opportunity
        update oldOpp;

        // Stop the test, this changes limit context back to test from trigger
        test.stopTest();

    }   
    
    
}




Best Answer chosen by vickim1.396005552708281E12
Daniel B ProbertDaniel B Probert
hmm someone must have as this is autogenerated - anyway try this - it should give you some coverage i think

@isTest
private class StandardUserRegistrationHandlerTest {
static testMethod void testCreateAndUpdateUser() {
    StandardUserRegistrationHandler handler = new StandardUserRegistrationHandler();
    Auth.UserData sampleData = new Auth.UserData('testId', 'testFirst', 'testLast',
        'testFirst testLast', 'testuser@example.org', null, 'testuserlong', 'en_US', 'facebook',
        null, new Map<String, String>{'language' => 'en_US'});
    User u = handler.createUser(null, sampleData);
    System.assertEquals('testuserlong@salesforce.com', u.userName);
    System.assertEquals('testuser@example.org', u.email);
    System.assertEquals('testLast', u.lastName);
    System.assertEquals('testFirst', u.firstName);
    System.assertEquals('testuser', u.alias);
    insert(u);
    String uid = u.id;
    
    sampleData = new Auth.UserData('testNewId', 'testNewFirst', 'testNewLast',
        'testNewFirst testNewLast', 'testnewuser@example.org', null, 'testnewuserlong', 'en_US', 'facebook',
        null, new Map<String, String>{});
    handler.updateUser(uid, null, sampleData);
    
    User updatedUser = [SELECT userName, email, firstName, lastName, alias FROM user WHERE id=:uid];
    System.assertEquals('testnewuserlong@salesforce.com', updatedUser.userName);
    System.assertEquals('testnewuser@example.org', updatedUser.email);
    System.assertEquals('testNewLast', updatedUser.lastName);
    System.assertEquals('testNewFirst', updatedUser.firstName);
    System.assertEquals('testnewu', updatedUser.alias);
}
}


All Answers

Daniel B ProbertDaniel B Probert
pre-deployment can you perform a run all tests then check the org code coverage - the error sounds like it's referring to the code coverage within your org not the deployment itself - if your org code coverage is below 75% you can't deploy - apart from test classes to improve the code coverage..
Daniel B ProbertDaniel B Probert
that is the right place but you need to do this in your live environment not your sandbox..

you can also do it through the ui.

Setup > Develop > Classes > Run All Tests
Then go to the same page and click to view code coverage


vickim1.396005552708281E12vickim1.396005552708281E12
Ahh I followed that directory and clicked on code coverage and got the following

"Code Coverage: 0%
Your overall code coverage is currently 0%. To deploy code to production, you must have at least 75%."

How would I fix this as I have not coded or added any manuall code in the prod myself? 

Daniel B ProbertDaniel B Probert
ok first up this may not be a correct number so don't panic.

open your developer console in production environment - click test - clear test data

then click test - run all

in the bottom window you should see on the test tag the test kick off - once it's finished check the overall code coverage window on the right and take a look at what code coverage is.

then go back to the UI and check the code coverage for the org again.

hopefully after you've done this it won't be 0% anymore.

if it is you'll need some help to get your code coverage back up to a decent level.




vickim1.396005552708281E12vickim1.396005552708281E12
Just ran the test, unfortunately it is 0%

Is there a way I can bypass this, as I need my new code to get to prod

0%
Daniel B ProbertDaniel B Probert
by the looks of it you need to get a test class for the class AutocreatedRegHandler1391697059641 - until that has more than 75% you can't deploy - this is a salesforce limit to provide all of us. Salesforce is a multitenant environment so they want to ensure all code is tested..

it's only 27 lines of code so it might be an easy one to fix.

if you post a copy of the code i can take a look for you..it might just need a couple of records creating..

vickim1.396005552708281E12vickim1.396005552708281E12
The code is below.

One issue I did find is, this code/class (AutocreatedRegHandler1391697059641)  does not exist in my sandbox env, I am guessing I will just need to create this class in the sandbox?


Cheers,
//TODO:This autogenerated class includes the basics for a Registration
//Handler class. You will need to customize it to ensure it meets your needs and
//the data provided by the third party.

global class AutocreatedRegHandler1391697059641 implements Auth.RegistrationHandler{
global boolean canCreateUser(Auth.UserData data) {
	//TODO: Check whether we want to allow creation of a user with this data
	//Set<String> s = new Set<String>{'usernamea', 'usernameb', 'usernamec'};
	//if(s.contains(data.username)) {
		//return true;
	//}
	return false;
}

global User createUser(Id portalId, Auth.UserData data){
	if(!canCreateUser(data)) {
		//Returning null or throwing an exception fails the SSO flow
		return null;
	}
	//The user is authorized, so create their Salesforce user
	User u = new User();
	Profile p = [SELECT Id FROM profile WHERE name='Standard User'];
	//TODO: Customize the username. Also check that the username doesn't already exist and
	//possibly ensure there are enough org licenses to create a user. Must be 80 characters
	//or less.
	u.username = data.username + '@myorg.com';
	u.email = data.email;
	u.lastName = data.lastName;
	u.firstName = data.firstName;
	String alias = data.username;
	//Alias must be 8 characters or less
	if(alias.length() > 8) {
		alias = alias.substring(0, 8);
	}
	u.alias = alias;
	u.languagelocalekey = UserInfo.getLocale();
	u.localesidkey = UserInfo.getLocale();
	u.emailEncodingKey = 'UTF-8';
	u.timeZoneSidKey = 'America/Los_Angeles';
	u.profileId = p.Id;
	return u;
}

global void updateUser(Id userId, Id portalId, Auth.UserData data){
	User u = new User(id=userId);
	//TODO: Customize the username. Must be 80 characters or less.
	//u.username = data.username + '@myorg.com';
	u.email = data.email;
	u.lastName = data.lastName;
	u.firstName = data.firstName;
	//String alias = data.username;
	//Alias must be 8 characters or less
	//if(alias.length() > 8) {
		//alias = alias.substring(0, 8);
	//}
	//u.alias = alias;
	update(u);
}
}







Daniel B ProbertDaniel B Probert
have you setup any auth providers in salesforce?

that code is autogenerated..
vickim1.396005552708281E12vickim1.396005552708281E12
No I have not setup any auth providers, the company has never done any coding before in salesforce, I only started because we needed some triggers to make calls in our portal system, and the only code I have written is in the 1st post
Daniel B ProbertDaniel B Probert
hmm someone must have as this is autogenerated - anyway try this - it should give you some coverage i think

@isTest
private class StandardUserRegistrationHandlerTest {
static testMethod void testCreateAndUpdateUser() {
    StandardUserRegistrationHandler handler = new StandardUserRegistrationHandler();
    Auth.UserData sampleData = new Auth.UserData('testId', 'testFirst', 'testLast',
        'testFirst testLast', 'testuser@example.org', null, 'testuserlong', 'en_US', 'facebook',
        null, new Map<String, String>{'language' => 'en_US'});
    User u = handler.createUser(null, sampleData);
    System.assertEquals('testuserlong@salesforce.com', u.userName);
    System.assertEquals('testuser@example.org', u.email);
    System.assertEquals('testLast', u.lastName);
    System.assertEquals('testFirst', u.firstName);
    System.assertEquals('testuser', u.alias);
    insert(u);
    String uid = u.id;
    
    sampleData = new Auth.UserData('testNewId', 'testNewFirst', 'testNewLast',
        'testNewFirst testNewLast', 'testnewuser@example.org', null, 'testnewuserlong', 'en_US', 'facebook',
        null, new Map<String, String>{});
    handler.updateUser(uid, null, sampleData);
    
    User updatedUser = [SELECT userName, email, firstName, lastName, alias FROM user WHERE id=:uid];
    System.assertEquals('testnewuserlong@salesforce.com', updatedUser.userName);
    System.assertEquals('testnewuser@example.org', updatedUser.email);
    System.assertEquals('testNewLast', updatedUser.lastName);
    System.assertEquals('testNewFirst', updatedUser.firstName);
    System.assertEquals('testnewu', updatedUser.alias);
}
}


This was selected as the best answer
vickim1.396005552708281E12vickim1.396005552708281E12
I had to change this line 

StandardUserRegistrationHandler handler = new StandardUserRegistrationHandler();

too

AutocreatedRegHandler1391697059641 handler = new AutocreatedRegHandler1391697059641();

to remove problems, the because the class is auto generated, it wont changes names etc will it?
Daniel B ProbertDaniel B Probert
yes sorry thats right you'll need to create the test class in your sandbox - possible worth copying over the generatedclass so you can test for your coverage level.

cheers
dan
vickim1.396005552708281E12vickim1.396005552708281E12
Thank you for your support.

I have managed to deploy my changes, my new issue is, although everything is deployed the changes are not taking effect in prod, so for example the invoke method I had in sandbox was calling my url and I could track this on my server, however in prod when I make changes to oportunities, my url is not invoked, seems like my deployed changes have not taken affect? anything I need to lookout for?


Thank you
Daniel B ProbertDaniel B Probert
is the url in the remote sites in your admin page?
vickim1.396005552708281E12vickim1.396005552708281E12
the url is an open to all incoming connections url, not hidden behind any admin auth.

i have not made any code changes in salesforce sandbox or prod code, migrated the 100% same code
Daniel B ProbertDaniel B Probert
i mean within Salesforce i believe you need to add in setup an external site weather their open or not.

Setup > Security Controls > Remote Sites

Make sure your URL in added in there - if I remember rightly in a sandbox you don't need to add the URL.

thanks
dan
vickim1.396005552708281E12vickim1.396005552708281E12
Ahh yes I did have to enable this for sandbox, I have enabled this in prod also,

I am guessing I will need to wait for few hours for my changes to take affect? its been 3 hours since my changes went live
Daniel B ProbertDaniel B Probert
in theory it should now be working - i don't know of a delay once you have enabled the remote site it's always work pretty much straight away for me.

the other thing to do is enable debugging on your account and then try and see what's going on with the apex - if there is a callout problem or any kind of problem it will be flagged in there.

my concern is considering you had code in production that wasn't in your sandbox there might be something else that is in production(required field) that wasn't in your sandbox and so hopefully the debugging will pick that up.

cheers
dan
vickim1.396005552708281E12vickim1.396005552708281E12
Cheers for all your help Dan, how can I enable debugging in prod
Daniel B ProbertDaniel B Probert
no worries Setup > Monitor > Debug Logs

then new
Find your account and go through the process that you believe should fire the trigger - as it happens you'll see some logs appears in debug logs windows.

thanks
dan